diff --git a/.dockerignore b/.dockerignore new file mode 100644 index 0000000..8362dd4 --- /dev/null +++ b/.dockerignore @@ -0,0 +1,10 @@ +c4 +c4.db +data/ +deploy/ +.env +.git +.gitignore +assets/css/output.css +c4-deploy-*.tar.gz +c4-deploy-*_b64*.txt diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..08261c3 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,29 @@ +FROM golang:1.25.4-bookworm AS build + +WORKDIR /src +COPY go.mod go.sum ./ +RUN go mod download + +COPY . . +RUN go tool gotailwind -i assets/css/input.css -o assets/css/output.css --minify +RUN CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o /c4 . + +FROM debian:bookworm-slim + +RUN apt-get update && \ + apt-get install -y --no-install-recommends ca-certificates wget && \ + rm -rf /var/lib/apt/lists/* + +COPY --from=build /c4 /usr/local/bin/c4 + +WORKDIR /app +RUN mkdir data && chown games:games data + +USER games + +EXPOSE 8080 + +HEALTHCHECK --interval=30s --timeout=5s --start-period=5s --retries=3 \ + CMD wget -qO /dev/null http://localhost:8080/ + +CMD ["c4"] diff --git a/docker-compose.yml b/docker-compose.yml new file mode 100644 index 0000000..a5cac93 --- /dev/null +++ b/docker-compose.yml @@ -0,0 +1,17 @@ +services: + c4: + build: . + container_name: c4 + restart: unless-stopped + ports: + - "8080:8080" + env_file: + - path: .env + required: false + environment: + - PORT=8080 + volumes: + - c4-data:/app/data + +volumes: + c4-data: diff --git a/main.go b/main.go index a7de4a3..f037b32 100644 --- a/main.go +++ b/main.go @@ -4,11 +4,11 @@ import ( "context" "crypto/md5" "database/sql" - _ "embed" + "embed" "encoding/hex" "encoding/json" + "io/fs" "log" - "net/http" "os" "sync" "time" @@ -32,17 +32,14 @@ var ( queries *gen.Queries ) -//go:embed assets/css/output.css -var daisyUICSS []byte +//go:embed assets +var assets embed.FS func DaisyUIPlugin(v *via.V) { - sum := md5.Sum(daisyUICSS) + css, _ := fs.ReadFile(assets, "assets/css/output.css") + sum := md5.Sum(css) version := hex.EncodeToString(sum[:4]) - v.HTTPServeMux().HandleFunc("GET /_plugins/daisyui/style.css", func(w http.ResponseWriter, r *http.Request) { - w.Header().Set("Content-Type", "text/css") - _, _ = w.Write(daisyUICSS) - }) - v.AppendToHead(h.Link(h.Rel("stylesheet"), h.Href("/_plugins/daisyui/style.css?v="+version))) + v.AppendToHead(h.Link(h.Rel("stylesheet"), h.Href("/assets/css/output.css?v="+version))) } func port() string { @@ -55,7 +52,10 @@ func port() string { func main() { _ = godotenv.Load() - if err := db.Init("c4.db"); err != nil { + if err := os.MkdirAll("data", 0o755); err != nil { + log.Fatal(err) + } + if err := db.Init("data/c4.db"); err != nil { log.Fatal(err) } queries = gen.New(db.DB) @@ -76,6 +76,9 @@ func main() { Plugins: []via.Plugin{DaisyUIPlugin}, }) + subFS, _ := fs.Sub(assets, "assets") + v.StaticFS("/assets/", subFS) + store.SetPubSub(v.PubSub()) snakeStore.SetPubSub(v.PubSub())