# Update Server - Implementation Strategy ## 1. Recommended stack ### Backend - Go 1.24+ - Router: `chi` or `gin` - HTML templates for admin UI, or server-rendered pages first - Database: `SQLite` - ORM/query layer: `sqlc`, `bun`, `gorm`, or plain `database/sql` - Migrations: `golang-migrate` or `goose` - Auth: - web admin via secure cookie session - client API via bearer API key ### My recommendation For this project, a pragmatic Go stack would be: - `chi` for routing; - `database/sql` + `sqlc` or `bun`; - `SQLite` with `modernc.org/sqlite` or `mattn/go-sqlite3`; - server-rendered HTML templates for admin pages; - `goose` for migrations. Why this stack: - simple to deploy; - less JS and frontend complexity; - good fit for an internal admin panel; - easier to keep maintainable for a small self-hosted tool. ## 2. Quick glossary `GUI` - graphical user interface; - here it simply means the admin web panel in a browser. `chi` - a small and fast HTTP router for Go; - this is not `CI`; - it helps map routes like `/api/v1/projects/{id}` to handlers. `CI` - continuous integration; - automated checks that run on commits, for example tests, linting, or building Docker images. `server-rendered HTML` - the Go server itself generates HTML pages and returns them to the browser; - this keeps the admin panel simpler than building a separate frontend app. ## 3. Architecture proposal Suggested project structure: ```text /cmd/server /internal/app /internal/http /internal/auth /internal/projects /internal/releases /internal/apikeys /internal/users /internal/tags /internal/storage /internal/db /internal/config /web/templates /web/static /migrations /data ``` ### Main modules `projects` - create/update/list/archive projects - manage project tags `releases` - upload artifact - compute checksum - store metadata - provide release lookup and download `apikeys` - generate secure random API keys - hash and persist - enforce permissions and project scope `tags` - CRUD for tags - attach tags to projects - resolve tag-based access rules `users` - admin authentication - password hashing - role checks `storage` - local filesystem storage abstraction - future option to swap to S3-compatible storage ## 4. Suggested data model Core tables: - `users` - `projects` - `tags` - `project_tags` - `releases` - `api_keys` - `api_key_project_access` - `api_key_tag_access` - `sessions` if server-side sessions are used - optionally `audit_logs` ### Example relations - one `project` has many `releases` - one `user` uploads many `releases` - one `project` has many tags through `project_tags` - one `api_key` can reference many projects through `api_key_project_access` - one `api_key` can reference many tags through `api_key_tag_access` Suggested key columns in `api_keys`: - `scope_mode` with values: - `all_projects` - `project_allow_list` - `project_deny_list` - `tag_allow_list` - `tag_deny_list` ## 5. Permission strategy Recommended first implementation: - API key has boolean flags: - `can_download` - `can_upload` - `can_delete` - `can_manage_projects` - API key has access mode: - `all_projects` - `project_allow_list` - `project_deny_list` - `tag_allow_list` - `tag_deny_list` - linked projects stored in `api_key_project_access` - linked tags stored in `api_key_tag_access` Recommended evaluation rules: - `all_projects`: allow every active project - `project_allow_list`: allow only linked projects - `project_deny_list`: allow every active project except linked projects - `tag_allow_list`: allow projects matching at least one linked tag - `tag_deny_list`: allow every active project except projects matching blocked tags Recommended constraint for v1: - each key uses exactly one scope mode at a time. This supports whitelist, blacklist, and future grouping without building a full RBAC engine upfront. ## 6. API design strategy Split API into two logical areas: ### Client API Used by application clients: - authenticate by bearer API key - list accessible projects - query latest release - download release artifact ### Admin API Used by web UI and optionally automation: - manage projects - manage tags - manage releases - manage API keys - manage users Keep both under `/api/v1`, but separate middleware and handlers clearly. ## 7. File upload strategy Recommended upload flow: 1. admin uploads file; 2. backend stores temporary stream; 3. checksum is calculated; 4. file is moved into final artifact path; 5. release metadata is inserted into DB; 6. transaction/state is finalized. Important safeguards: - limit file size; - sanitize filenames; - prevent path traversal; - avoid duplicate version collisions unless explicitly replacing; - validate project exists before storing; - store uploads outside any static web root; - never execute or unpack uploaded files. ## 8. Security checklist - hash passwords with `bcrypt` or `argon2id` - hash API keys before storing - show full API key only once - secure cookies with `HttpOnly`, `Secure`, `SameSite` - CSRF protection for admin forms - upload size limits - permission checks on every API endpoint - request logging without leaking secrets - rate limiting for login and API key endpoints - store artifacts outside the web root - serve downloads only after auth and permission checks - set server timeouts: read, write, idle, header - add security headers such as `Content-Security-Policy`, `X-Frame-Options`, `X-Content-Type-Options` - terminate TLS at Caddy or Nginx - optionally restrict admin UI by IP allow-list or VPN - avoid shelling out to external tools for file processing - keep dependencies updated and scan them periodically ## 9. Internet-facing deployment posture If the server will be visible on the internet, this is the safe baseline: - app listens only behind a reverse proxy; - reverse proxy handles HTTPS certificates; - admin UI uses strong password and optionally IP allow-list; - SQLite file and artifacts live on a mounted persistent volume; - no public directory listing for artifacts; - uploads never become directly executable server-side content; - logs and backups are stored separately from app code. ## 10. Development strategy Recommended approach: - develop locally on your Mac first; - keep everything in one project directory; - run the Go server natively for fast iteration; - add Docker packaging once the core flows work locally; - deploy to Proxmox only after the first end-to-end flow is stable. Why local-first is better here: - faster feedback loop; - easier debugging; - easier file upload testing; - no need to fight remote networking while core logic is still changing. Good compromise: - write code locally on Mac; - keep deployment target from day one in mind; - periodically verify that the Docker image still builds. ## 11. Deployment strategy Single container is realistic. Recommended runtime layout: - app binary in container - reverse proxy in front of container - mounted `/data` volume - SQLite DB in `/data/db.sqlite` - artifacts in `/data/artifacts` ### Environment variables - `APP_ADDR` - `APP_BASE_URL` - `DATA_DIR` - `SQLITE_PATH` - `ADMIN_EMAIL` - `ADMIN_PASSWORD` - `SESSION_SECRET` Recommended deployment target: - Proxmox VM or LXC with Docker or Podman; - app container plus reverse proxy; - mounted volume for `/data`; - regular backup of `/data`. ## 12. Delivery phases ### Phase 1 - Skeleton - initialize Go module - wire config - HTTP server - health endpoint - migrations setup - SQLite connection - basic template rendering ### Phase 2 - Auth and admin bootstrap - user table - create initial admin user - login/logout - session middleware ### Phase 3 - Projects and releases - projects CRUD - project tags CRUD - release upload - release list/detail - local artifact storage ### Phase 4 - API keys and access control - API key generation - hashed storage - project white-list and black-list - tag-based schema and access checks - permission middleware ### Phase 5 - Client update API - latest release endpoint - release metadata endpoint - download endpoint - audit of last key usage ### Phase 6 - Hardening - validation - CSRF - logging - soft deletes - basic audit logs - reverse proxy config - rate limiting - Docker image and compose setup ## 13. Agent execution plan If multiple AI agents or contributors will implement this, split work by vertical ownership. ### Agent 1 - Core platform Owns: - Go module setup - config - server bootstrap - middleware skeleton - Docker setup ### Agent 2 - Data layer Owns: - migrations - schema - repositories/queries - SQLite integration - tags and access-rule tables ### Agent 3 - Auth and users Owns: - admin login - sessions - password handling - user management basics ### Agent 4 - Projects and releases Owns: - project CRUD - tag assignment to projects - release upload flow - artifact storage abstraction - checksum logic ### Agent 5 - API keys and client API Owns: - API key generation - permission model - whitelist/blacklist evaluation - tag-based access evaluation - client-facing release lookup and download endpoints ### Agent 6 - Admin UI Owns: - HTML templates - forms - tables/pages for projects, releases, keys, users, tags ### Agent 7 - Security and deployment hardening Owns: - secure headers - rate limiting - reverse proxy templates - deployment hardening review ## 14. Recommended implementation order for agents 1. Agent 1 sets up application skeleton and app wiring. 2. Agent 2 defines schema and migrations. 3. Agent 3 implements admin auth. 4. Agent 4 implements projects, tags, and release storage. 5. Agent 5 implements API key model and client endpoints. 6. Agent 6 builds the admin UI on top of completed flows. 7. Agent 7 hardens internet-facing deployment paths. 8. Final pass integrates validation, tests, and Docker packaging. ## 15. Testing strategy ### Unit tests - version selection logic - permission checks - API key hashing/lookup - checksum generation - tag scope matching ### Integration tests - login flow - create project - attach tags to project - upload release - create API key - fetch latest release via API key - reject unauthorized project access - reject blacklisted project or tag access ### Manual sanity tests - upload file from admin UI - download via curl using bearer API key - restart container and verify persistence - verify admin login rate limits - verify artifacts are not directly exposed by URL guessing ## 16. My recommendations on product scope To avoid overbuilding too early, I would start with: - SQLite - local filesystem storage - server-rendered admin UI - one file per release - one admin role first, but schema ready for more users - one scope mode per key - project whitelist and blacklist in v1 - project tags in schema from day one This version will already be useful and can stay very small operationally. ## 17. Nice first concrete milestone The first milestone should be: "Admin can log in, create a tagged project, upload a versioned file, create an API key with project or tag-based access, and a client can download the latest file using that key." If that works end-to-end, the rest can be layered on safely.