The api and web tsconfig.json files both extend ../../tsconfig.base.json,
but the previous Dockerfile didn't COPY that file into /app. `tsc` then
fails to resolve the extends and exits with code 2 during the
`pnpm --filter @gashboard/api build` stage. Adding the file to the
COPY in the deps stage — both build stages inherit FROM deps, so this
fixes both api and web builds.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Node 22's bundled Corepack strict-validates pnpm package signatures, and
the Portainer build host couldn't complete `corepack prepare pnpm@9.12.3
--activate` (exit 1). Reproducible failure mode behind networks that
can't reach Corepack's signing-key host or against pinned pnpm versions
whose signatures aren't yet shipped in Corepack's known list.
Switch all three stages to install pnpm via plain `npm i -g pnpm@9.12.3`,
which has none of those constraints. Also copy pnpm-lock.yaml in so
`--frozen-lockfile` actually does what it says (was previously running
`--frozen-lockfile=false` because the lockfile wasn't being copied).
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Two-app pnpm workspace for the gashboard (mining dashboard) project:
@gashboard/api (Express 5 + TS) and @gashboard/web (Vue 3 + Vite + TS).
Shared tsconfig.base.json. Multi-stage Dockerfile (node:22.12-alpine,
non-root, healthchecked) and docker-compose.yml ready to deploy as a
Portainer Stack on Umbrel — joins umbrel_main_network so it can reach
the Datum container directly. .env.example documents every var; README
covers the Portainer deploy flow and the security posture.
Note: Dockerfile has a TODO marker to SHA256-pin the base image before
shipping to production.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>