Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Move labels to a single function #24

Merged
merged 1 commit into from
Jul 27, 2021
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 5 additions & 22 deletions internal/room/containers.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,34 +13,17 @@ import (
)

func (manager *RoomManagerCtx) containerToEntry(container dockerTypes.Container) (*types.RoomEntry, error) {
roomName, ok := container.Labels["m1k1o.neko_rooms.name"]
if !ok {
return nil, fmt.Errorf("damaged container labels: name not found")
}

nekoImage, ok := container.Labels["m1k1o.neko_rooms.neko_image"]
if !ok {
// Backward compatibility.
nekoImage = container.Image
//return nil, fmt.Errorf("Damaged container labels: neko_image not found.")
}

URL, ok := container.Labels["m1k1o.neko_rooms.url"]
if !ok {
return nil, fmt.Errorf("damaged container labels: url not found")
}

epr, err := manager.getEprFromLabels(container.Labels)
labels, err := manager.extractLabels(container.Labels)
if err != nil {
return nil, err
}

return &types.RoomEntry{
ID: container.ID,
URL: URL,
Name: roomName,
NekoImage: nekoImage,
MaxConnections: epr.Max - epr.Min + 1,
URL: labels.URL,
Name: labels.Name,
NekoImage: labels.NekoImage,
MaxConnections: labels.Epr.Max - labels.Epr.Min + 1,
Running: container.State == "running",
Status: container.Status,
Created: time.Unix(container.Created, 0),
Expand Down
71 changes: 71 additions & 0 deletions internal/room/labels.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
package room

import (
"fmt"
"strconv"
)

type RoomLabels struct {
Name string
URL string
Epr EprPorts
NekoImage string
}

func (manager *RoomManagerCtx) extractLabels(labels map[string]string) (*RoomLabels, error) {
name, ok := labels["m1k1o.neko_rooms.name"]
if !ok {
return nil, fmt.Errorf("damaged container labels: name not found")
}

url, ok := labels["m1k1o.neko_rooms.url"]
if !ok {
return nil, fmt.Errorf("damaged container labels: url not found")
}

nekoImage, ok := labels["m1k1o.neko_rooms.neko_image"]
if !ok {
return nil, fmt.Errorf("damaged container labels: neko_image not found")
}

eprMinStr, ok := labels["m1k1o.neko_rooms.epr.min"]
if !ok {
return nil, fmt.Errorf("damaged container labels: epr.min not found")
}

eprMin, err := strconv.ParseUint(eprMinStr, 10, 16)
if err != nil {
return nil, err
}

eprMaxStr, ok := labels["m1k1o.neko_rooms.epr.max"]
if !ok {
return nil, fmt.Errorf("damaged container labels: epr.max not found")
}

eprMax, err := strconv.ParseUint(eprMaxStr, 10, 16)
if err != nil {
return nil, err
}

return &RoomLabels{
Name: name,
URL: url,
NekoImage: nekoImage,
Epr: EprPorts{
Min: uint16(eprMin),
Max: uint16(eprMax),
},
}, nil
}

func (manager *RoomManagerCtx) serializeLabels(labels RoomLabels) map[string]string {
return map[string]string{
"m1k1o.neko_rooms.name": labels.Name,
"m1k1o.neko_rooms.url": labels.URL,
"m1k1o.neko_rooms.instance": manager.config.InstanceName,
"m1k1o.neko_rooms.epr.min": fmt.Sprintf("%d", labels.Epr.Min),
"m1k1o.neko_rooms.epr.max": fmt.Sprintf("%d", labels.Epr.Max),
"m1k1o.neko_rooms.neko_image": labels.NekoImage,
}
}
90 changes: 53 additions & 37 deletions internal/room/manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -114,6 +114,10 @@ func (manager *RoomManagerCtx) Create(settings types.RoomSettings) (string, erro
}
}

//
// Allocate ports
//

epr, err := manager.allocatePorts(settings.MaxConnections)
if err != nil {
return "", err
Expand All @@ -137,8 +141,33 @@ func (manager *RoomManagerCtx) Create(settings types.RoomSettings) (string, erro
exposedPorts[portKey] = struct{}{}
}

//
// Set traefik labels
//

containerName := manager.config.InstanceName + "-" + roomName

traefikLabels := map[string]string{
"traefik.enable": "true",
"traefik.http.services." + containerName + "-frontend.loadbalancer.server.port": fmt.Sprintf("%d", frontendPort),
"traefik.http.routers." + containerName + ".entrypoints": manager.config.TraefikEntrypoint,
"traefik.http.routers." + containerName + ".rule": "Host(`" + manager.config.TraefikDomain + "`) && PathPrefix(`/" + roomName + "`)",
"traefik.http.middlewares." + containerName + "-rdr.redirectregex.regex": "/" + roomName + "$$",
"traefik.http.middlewares." + containerName + "-rdr.redirectregex.replacement": "/" + roomName + "/",
"traefik.http.middlewares." + containerName + "-prf.stripprefix.prefixes": "/" + roomName + "/",
"traefik.http.routers." + containerName + ".middlewares": containerName + "-rdr," + containerName + "-prf",
}

// optional HTTPS
if manager.config.TraefikCertresolver != "" {
traefikLabels["traefik.http.routers."+containerName+".tls"] = "true"
traefikLabels["traefik.http.routers."+containerName+".tls.certresolver"] = manager.config.TraefikCertresolver
}

//
// Set internal labels
//

instanceUrl := manager.config.InstanceUrl
if instanceUrl == "" {
urlProto := "http"
Expand All @@ -157,31 +186,20 @@ func (manager *RoomManagerCtx) Create(settings types.RoomSettings) (string, erro
instanceUrl = instanceUrl + "/"
}

labels := map[string]string{
// Set internal labels
"m1k1o.neko_rooms.name": roomName,
"m1k1o.neko_rooms.url": instanceUrl + roomName + "/",
"m1k1o.neko_rooms.instance": manager.config.InstanceName,
"m1k1o.neko_rooms.epr.min": fmt.Sprintf("%d", epr.Min),
"m1k1o.neko_rooms.epr.max": fmt.Sprintf("%d", epr.Max),
"m1k1o.neko_rooms.neko_image": settings.NekoImage,
labels := manager.serializeLabels(RoomLabels{
Name: roomName,
URL: instanceUrl + roomName + "/",
Epr: epr,
NekoImage: settings.NekoImage,
})

// Set traefik labels
"traefik.enable": "true",
"traefik.http.services." + containerName + "-frontend.loadbalancer.server.port": fmt.Sprintf("%d", frontendPort),
"traefik.http.routers." + containerName + ".entrypoints": manager.config.TraefikEntrypoint,
"traefik.http.routers." + containerName + ".rule": "Host(`" + manager.config.TraefikDomain + "`) && PathPrefix(`/" + roomName + "`)",
"traefik.http.middlewares." + containerName + "-rdr.redirectregex.regex": "/" + roomName + "$$",
"traefik.http.middlewares." + containerName + "-rdr.redirectregex.replacement": "/" + roomName + "/",
"traefik.http.middlewares." + containerName + "-prf.stripprefix.prefixes": "/" + roomName + "/",
"traefik.http.routers." + containerName + ".middlewares": containerName + "-rdr," + containerName + "-prf",
for k, v := range traefikLabels {
labels[k] = v
}

// optional HTTPS
if manager.config.TraefikCertresolver != "" {
labels["traefik.http.routers."+containerName+".tls"] = "true"
labels["traefik.http.routers."+containerName+".tls.certresolver"] = manager.config.TraefikCertresolver
}
//
// Set environment variables
//

env := []string{
fmt.Sprintf("NEKO_BIND=:%d", frontendPort),
Expand All @@ -194,6 +212,10 @@ func (manager *RoomManagerCtx) Create(settings types.RoomSettings) (string, erro
env = append(env, fmt.Sprintf("NEKO_NAT1TO1=%s", strings.Join(manager.config.NAT1To1IPs, ",")))
}

//
// Set container mounts
//

mounts := []dockerMount.Mount{}
for _, mount := range settings.Mounts {
readOnly := false
Expand Down Expand Up @@ -260,6 +282,10 @@ func (manager *RoomManagerCtx) Create(settings types.RoomSettings) (string, erro
)
}

//
// Set container configs
//

config := &container.Config{
// Hostname
Hostname: containerName,
Expand Down Expand Up @@ -358,22 +384,12 @@ func (manager *RoomManagerCtx) GetSettings(id string) (*types.RoomSettings, erro
return nil, err
}

roomName, ok := container.Config.Labels["m1k1o.neko_rooms.name"]
if !ok {
return nil, fmt.Errorf("damaged container labels: name not found")
}

nekoImage, ok := container.Config.Labels["m1k1o.neko_rooms.neko_image"]
if !ok {
return nil, fmt.Errorf("damaged container labels: neko_image not found")
}

epr, err := manager.getEprFromLabels(container.Config.Labels)
labels, err := manager.extractLabels(container.Config.Labels)
if err != nil {
return nil, err
}

privateStorageRoot := path.Join(manager.config.StorageExternal, privateStoragePath, roomName)
privateStorageRoot := path.Join(manager.config.StorageExternal, privateStoragePath, labels.Name)
templateStorageRoot := path.Join(manager.config.StorageExternal, templateStoragePath)

mounts := []types.RoomMount{}
Expand All @@ -397,9 +413,9 @@ func (manager *RoomManagerCtx) GetSettings(id string) (*types.RoomSettings, erro
}

settings := types.RoomSettings{
Name: roomName,
NekoImage: nekoImage,
MaxConnections: epr.Max - epr.Min + 1,
Name: labels.Name,
NekoImage: labels.NekoImage,
MaxConnections: labels.Epr.Max - labels.Epr.Min + 1,
Mounts: mounts,
}

Expand Down
34 changes: 2 additions & 32 deletions internal/room/ports.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ package room
import (
"fmt"
"sort"
"strconv"
)

type EprPorts struct {
Expand Down Expand Up @@ -51,12 +50,12 @@ func (manager *RoomManagerCtx) getUsedPorts() ([]EprPorts, error) {

result := []EprPorts{}
for _, container := range containers {
epr, err := manager.getEprFromLabels(container.Labels)
labels, err := manager.extractLabels(container.Labels)
if err != nil {
return nil, err
}

result = append(result, epr)
result = append(result, labels.Epr)
}

sort.SliceStable(result, func(i, j int) bool {
Expand All @@ -65,32 +64,3 @@ func (manager *RoomManagerCtx) getUsedPorts() ([]EprPorts, error) {

return result, nil
}

func (manager *RoomManagerCtx) getEprFromLabels(labels map[string]string) (EprPorts, error) {
var err error
epr := EprPorts{}

eprMinStr, ok := labels["m1k1o.neko_rooms.epr.min"]
if !ok {
return epr, fmt.Errorf("damaged container labels: epr.min not found")
}

eprMin, err := strconv.ParseUint(eprMinStr, 10, 16)
if err != nil {
return epr, err
}

eprMaxStr, ok := labels["m1k1o.neko_rooms.epr.max"]
if !ok {
return epr, fmt.Errorf("damaged container labels: epr.max not found")
}

eprMax, err := strconv.ParseUint(eprMaxStr, 10, 16)
if err != nil {
return epr, err
}

epr.Min = uint16(eprMin)
epr.Max = uint16(eprMax)
return epr, nil
}