diff --git a/CHANGELOG.md b/CHANGELOG.md index a0f5049..ae3b433 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ - Begin using a new SQLite database file in `/var/lib/headplane/hp_persist.db`. - The database is created automatically if it does not exist. - It currently stores SSH connection details and will migrate older data. +- The docker container now runs in a non-root, distroless image (closes [#255](https://github.com/tale/headplane/issues/255)) ### 0.6.0 (May 25, 2025) - Headplane 0.6.0 now requires **Headscale 0.26.0** or newer. diff --git a/Dockerfile b/Dockerfile index 30b76a0..9baccb9 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,35 +1,35 @@ -FROM golang:1.24 AS agent-build -WORKDIR /app +FROM jdxcode/mise:latest AS mise-context +COPY mise.toml . +RUN mise install + +FROM mise-context AS go-build +WORKDIR /build/ COPY go.mod go.sum ./ -RUN go mod download +COPY cmd/ ./cmd/ +COPY internal/ ./internal/ +RUN mkdir -p /build/app/ && mise run wasm ::: agent +RUN chmod +x /build/build/hp_agent -COPY agent/ ./agent -RUN CGO_ENABLED=0 GOOS=linux go build \ - -trimpath \ - -ldflags "-s -w" \ - -o /app/hp_agent ./agent/cmd/hp_agent - -FROM node:22-alpine AS build -WORKDIR /app - -RUN npm install -g pnpm@10 -RUN apk add --no-cache git -COPY package.json pnpm-lock.yaml ./ +FROM mise-context AS js-build +WORKDIR /build COPY patches ./patches +COPY package.json pnpm-lock.yaml ./ RUN pnpm install --frozen-lockfile COPY . . +RUN mise trust +COPY --from=go-build /build/app/hp_ssh.wasm /build/app/hp_ssh.wasm +COPY --from=go-build /build/app/wasm_exec.js /build/app/wasm_exec.js RUN pnpm run build - -FROM node:22-alpine -RUN apk add --no-cache ca-certificates -RUN mkdir -p /var/lib/headplane -RUN mkdir -p /usr/libexec/headplane RUN mkdir -p /var/lib/headplane/agent +FROM gcr.io/distroless/nodejs22-debian12:nonroot +COPY --from=js-build --chown=nonroot:nonroot /build/build/ /app/build/ +COPY --from=js-build --chown=nonroot:nonroot /build/drizzle /app/drizzle/ +COPY --from=js-build --chown=nonroot:nonroot /var/lib/headplane /var/lib/headplane +COPY --from=js-build --chown=nonroot:nonroot /build/node_modules/ /app/node_modules/ +COPY --from=go-build --chown=nonroot:nonroot /build/build/hp_agent /usr/libexec/headplane/agent + WORKDIR /app -COPY --from=build /app/build /app/build -COPY --from=agent-build /app/hp_agent /usr/libexec/headplane/agent -RUN chmod +x /usr/libexec/headplane/agent -CMD [ "node", "./build/server/index.js" ] +CMD [ "/app/build/server/index.js" ] diff --git a/app/server/db/client.ts b/app/server/db/client.server.ts similarity index 93% rename from app/server/db/client.ts rename to app/server/db/client.server.ts index f816a6b..c364b1d 100644 --- a/app/server/db/client.ts +++ b/app/server/db/client.server.ts @@ -1,7 +1,7 @@ import { mkdir } from 'node:fs/promises'; import { dirname, resolve } from 'node:path'; -import { drizzle } from 'drizzle-orm/libsql'; import { migrate } from 'drizzle-orm/libsql/migrator'; +import { drizzle } from 'drizzle-orm/libsql/sqlite3'; import log from '~/utils/log'; export async function createDbClient(path: string) { diff --git a/app/server/index.ts b/app/server/index.ts index ed4fea6..1235b12 100644 --- a/app/server/index.ts +++ b/app/server/index.ts @@ -5,7 +5,7 @@ import log from '~/utils/log'; import { configureConfig, configureLogger, envVariables } from './config/env'; import { loadIntegration } from './config/integration'; import { loadConfig } from './config/loader'; -import { createDbClient } from './db/client'; +import { createDbClient } from './db/client.server'; import { createApiClient } from './headscale/api-client'; import { loadHeadscaleConfig } from './headscale/config-loader'; import { loadAgentSocket } from './web/agent'; diff --git a/mise.toml b/mise.toml index cc54c04..71e70c3 100644 --- a/mise.toml +++ b/mise.toml @@ -1,6 +1,7 @@ [tools] "go" = "1.24.4" "node" = "22" +"pnpm" = "10" [tasks.copy-wasm-shim] alias = ["gojs"] diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 133e653..002e709 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -2517,7 +2517,6 @@ packages: libsql@0.5.13: resolution: {integrity: sha512-5Bwoa/CqzgkTwySgqHA5TsaUDRrdLIbdM4egdPcaAnqO3aC+qAgS6BwdzuZwARA5digXwiskogZ8H7Yy4XfdOg==} - cpu: [x64, arm64, wasm32, arm] os: [darwin, linux, win32] lightningcss-darwin-arm64@1.30.1: diff --git a/vite.config.ts b/vite.config.ts index 9a8899e..d10ecb5 100644 --- a/vite.config.ts +++ b/vite.config.ts @@ -36,7 +36,10 @@ export default defineConfig(({ isSsrBuild }) => ({ }, ssr: { target: 'node', - noExternal: isSsrBuild ? true : undefined, + noExternal: isSsrBuild ? ['@libsql/client'] : undefined, + }, + optimizeDeps: { + include: ['@libsql/client'], }, define: { __VERSION__: JSON.stringify(version),