Prd/README.md
Lucy Doupalů be9f14ce34 Helpdesk - operator console + patched GrapheneOS Dialer for call handling
A small helpdesk system: an office Pixel running a patched GrapheneOS Dialer
answers technician calls, records both call legs as separate channels, and a
Ruby backend transcribes them through Whisper and files an AI summary against
the caller.

Squashed to a single commit for sharing. No credentials are included; secrets
live outside the repo in /etc/helpdesk/env on the server or a gitignored
.claude/env.local locally. See .claude/env.local.example for the shape.

Start at README.md, then docs/architecture.md.
2026-07-27 18:50:32 +02:00

69 lines
3.5 KiB
Markdown

# Helpdesk
A phone helpdesk for field technicians. A technician calls a stationary GrapheneOS Pixel in the office;
before the operator picks up, the caller's card pops up on the operator's screen. The call is recorded,
transcribed, and summarised, and filed against the caller as an event. Operators work in a web console;
the phone talks to the backend over its own signed channel.
The backend is one Ruby process: WEBrick and the standard library, plus the pg and sequel gems when it
runs on PostgreSQL. In production it runs on `moje.al.army` - operators reach the console over mutual
TLS on 443, the phone posts to its own TLS door on 8443.
## Run it locally
Ruby 3.2+ and nothing else. The default mode stores everything in a JSON file, so there is no database
to set up:
```
ruby components/backend/server.rb
```
That starts the console and the device API on http://127.0.0.1:4000 in dev mode: operator auth off, a
few demo contacts seeded. Open http://127.0.0.1:4000 for the console.
To run on PostgreSQL instead, point `HELPDESK_DATABASE_URL` at a database and the backend switches
stores:
```
createdb helpdesk_dev
psql helpdesk_dev -f components/backend/db/migrate/001_init.sql
HELPDESK_DATABASE_URL=postgres://localhost/helpdesk_dev ruby components/backend/server.rb
```
Tests run from `components/backend`: `make test`, or any file directly (`ruby test/test_domain.rb`).
To watch a whole call go through without a phone, start the server and run `ruby sim/simulator.rb`.
## Layout
- `components/backend` - the deployed service: operator console, operator API, device API, storage,
the AI pipeline. Start reading at `server.rb`.
- `components/backend/lib/helpdesk` - the domain core: `domain.rb` (the Store seam and the Service,
including the call state machine), `pg_store.rb` (PostgreSQL), `ledger.rb` (the resolutions ledger),
`business_hours.rb`, `reporting.rb`.
- `components/backend/wiki` - wiki grounding for summaries: GraphQL client, embedder, cosine index,
build script.
- `components/transcription-worker` - recording to speaker-tagged transcript: `remote_transcriber.rb`
(hosted Whisper, what production uses) and `transcriber.rb` (local WhisperX fallback).
- `components/dialer-patch` - the GrapheneOS Dialer patch: a Java overlay plus nine source patches.
Built only on the build box (see `docs/runbooks/`), never in CI.
- `components/sepolicy-patch` - one SELinux patch so the patched Dialer can read its
`*.helpdesk.*` config properties.
- `deploy/` - reference copies of the production config: systemd units, nginx vhosts, the deploy and
backup scripts.
- `ci/` - the end-to-end script the pipeline runs.
- `docs/` - the human docs, listed below.
- `resources/` - fetch scripts for the (huge, git-ignored) GrapheneOS sources, and the local Whisper
CLI the fallback transcriber drives.
## Docs
- `docs/architecture.md` - how the pieces fit: the two auth planes, a call's path through the system,
storage, the AI subsystem.
- `docs/operations.md` - the production server: deploy, roll back, logs, backups, secrets, CI.
- `docs/device-api.md` - the wire contract between the phone and the backend.
- `docs/phone-connectivity.md` - how the patched Dialer finds, authenticates to, and talks to the
backend, with troubleshooting.
- `docs/onboarding.md` - accounts, certificates, SSH, first run.
- `docs/runbooks/` - building and flashing the Pixel: `graphene-build.md`,
`pixel10a-flash-manual.md`, `windows-wsl2-build.md`. Plus `cert-renewal.md`, for the vmin
certificates, which do not renew themselves.