Commit graph

4 commits

Author SHA1 Message Date
Claude
0c995f9a0a
feat: HTTP git push with API key auth
Replaces SSH as the primary git push path — no key generation needed.

  # Admin UI: Users → Generate key (shown once)
  git remote add hiy http://hiy:API_KEY@myserver/git/myapp
  git push hiy main

What was added:

- api_keys DB table (id, user_id, label, key_hash/SHA-256, created_at)
  Keys are stored as SHA-256 hashes; the plaintext is shown once on
  creation and never stored.

- routes/api_keys.rs
  GET/POST /api/users/:id/api-keys  — list / generate
  DELETE   /api/api-keys/:key_id    — revoke

- HTTP Smart Protocol endpoints (public, auth via Basic + API key)
    GET  /git/:app/info/refs        — ref advertisement
    POST /git/:app/git-receive-pack — receive pack, runs post-receive hook

  Authentication: HTTP Basic where the password is the API key.
  git prompts once and caches via the OS credential store.
  post-receive hook fires as normal and queues the build.

- Admin UI: API keys section per user with generate/revoke and a
  one-time reveal box showing the ready-to-use git remote command.

SSH path (git-shell + authorized_keys) is still functional for users
who prefer it; both paths feed the same build queue.

https://claude.ai/code/session_01FKCW3FDjNFj6jve4niMFXH
2026-03-23 12:59:02 +00:00
Claude
2cdbf270f6
Add multi-user security service with per-app authorization
Control plane:
- Users and app grants stored in SQLite (users + user_apps tables)
- bcrypt password hashing
- Sessions: HashMap<token, user_id> (in-memory, cleared on restart)
- Bootstrap: first admin auto-created from HIY_ADMIN_USER/HIY_ADMIN_PASS if DB is empty
- /admin/users page: create/delete users, toggle admin, grant/revoke app access
- /api/users + /api/users/:id/apps/:app_id REST endpoints (admin-only)

Deployed apps:
- Every app route now uses Caddy forward_auth pointing at /auth/verify
- /auth/verify checks session cookie + user_apps grant (admins have access to all apps)
- Unauthenticated -> 302 to /login?next=<original URL>
- Authorised but not granted -> /denied page
- Session cookie set with Domain=.DOMAIN_SUFFIX for cross-subdomain auth

Other:
- /denied page for "logged in but not granted" case
- Login page skips re-auth if already logged in
- Cookie uses SameSite=Lax (required for cross-subdomain redirect flows)

https://claude.ai/code/session_01FKCW3FDjNFj6jve4niMFXH
2026-03-20 14:22:57 +00:00
Shautvast
fd7d417471 latest rust slim 2026-03-19 12:33:08 +01:00
Claude
8f5bb158cb
M1: Rust control plane, builder, dashboard, and infra
- Cargo workspace with hiy-server (axum 0.7 + sqlx SQLite + tokio)
- SQLite schema: apps, deploys, env_vars (inline migrations, no daemon)
- Background build worker: sequential queue, streams stdout/stderr to DB
- REST API: CRUD for apps, deploys, env vars; GitHub webhook with HMAC-SHA256
- SSE endpoint for live build log streaming
- Monospace HTMX-free dashboard: app list + per-app detail, log viewer, env editor
- builder/build.sh: clone/pull → detect strategy (Dockerfile/buildpack/static)
  → docker build → swap container → update Caddy via admin API → prune images
- infra/docker-compose.yml + Dockerfile.server for local dev (no Pi needed)
- proxy/Caddyfile: auto-HTTPS off for local, comment removed for production
- .env.example

Compiles clean (zero warnings). Run locally:
  cp .env.example .env && cargo run --bin hiy-server

https://claude.ai/code/session_01FKCW3FDjNFj6jve4niMFXH
2026-03-19 08:25:59 +00:00