fluid-telegram/docs/seeding-runbook.md
tegwick f06be1f949 Add the operator seeding runbook and enforce the presence schema
Loosen the all-or-nothing stance on provisioning: where a platform has no
API to seed access, a guided runbook is the right answer. docs/seeding-runbook.md
covers the three Telegram steps that cannot be automated, and each carries a
"why not automated" line so the judgement can be revisited rather than
inherited. Telegram's steps resist automation incidentally -- nobody built
the endpoints -- unlike a control such as KYC, which resists by design and
where a weak component would be a defect rather than an opening.

Fix the schema's $id, which was a relative path and broke $ref resolution in
ordinary validators, and add the visibility/username constraint the field
descriptions already claimed. Both specs now validate, and the rejections are
tested.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_0172sgCZEEDJcnQmr4SGDvKa

Assistant: claude-code
Assistant-Model: opus
Assistant-Process: 1361245@bnt-lap001
Assistant-Session: b3b428ef-f3e6-4688-b091-01f71461d66a
2026-09-04 19:30:54 +02:00

149 lines
5.9 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Operator runbook — seeding platform access
Some platform access cannot be provisioned from a specification. Telegram will
not let software create the *first* credential: an account needs a phone and a
device, and `api_id` / `api_hash` come from a web form behind a login. No API
exists for either, and none is coming, because their purpose is to establish that
a person is on the other end.
This runbook is what we do instead. It is not a lowering of the bar. **A manual
step is acceptable when it is guided, repeatable, and bounded — and unacceptable
when it is merely undocumented.** The test each step below has to pass is that
an operator who has never done it can follow it once, get the same result as
anyone else, and hand the outcome to a tool that takes over from there.
## The rule this runbook operates under
> Automate everything that has an interface. Where a step exists specifically to
> prove a human is present, guide it — and record why it resisted automation, so
> the judgement can be revisited rather than inherited.
Every manual step below carries a **Why not automated** line. That line is the
thing to re-read when the platform changes. Some of them will stop being true;
the sooner that is noticed, the smaller the runbook gets.
There is a real distinction here worth keeping. A KYC identity check resists
automation *by design* — automating it would defeat what it is for, and a
component weak enough to allow it is a defect, not an opportunity. A web form
that mints an API key resists automation only *incidentally*, because nobody
built the endpoint. The first stays manual on principle. The second is a
candidate the moment anything changes.
Telegram's steps are all the second kind. None of them is a fraud control; they
are just interfaces that were never built.
---
## Before you start
Have these ready. Stopping halfway through to find one is how the session
becomes irreproducible.
- [ ] A phone number that can receive SMS, **not** a personal one
- [ ] A device with Telegram installed, to complete the first login
- [ ] Access to OpenBao (`bao.coulomb.social`) with write on the interface's path
- [ ] The campaign's presence spec merged (`pr-hall-of-helix/presence/telegram.yaml`)
- [ ] The avatar asset committed and referenced by the spec
Roughly 20 minutes, once.
---
## Step 1 — Register the operator account
**Why not automated:** Telegram requires a phone number and an SMS round trip.
There is no registration API at any tier. This is the step whose whole purpose
is to prove a person is present.
1. Install Telegram on the device and register with the operator phone number.
2. Set a display name that reads as an operator account, not a person.
3. Enable two-factor authentication and put the password in OpenBao at
`<interface-path>/telegram/operator-2fa` immediately.
**Do not use a personal account.** If it is rate-limited or restricted — which
automation can cause — the loss should be a throwaway account, not someone's
messages.
**Record:** the phone number, in OpenBao at `<interface-path>/telegram/operator-phone`.
---
## Step 2 — Obtain `api_id` and `api_hash`
**Why not automated:** issued by a web form at my.telegram.org behind a login
code. No API. This one is incidental rather than principled — if Telegram ever
exposes it, Step 2 disappears.
1. Go to <https://my.telegram.org>, log in with the operator number.
2. **API development tools** → create an application.
- App title: `helixforge-provisioner`
- Platform: Other
3. Copy `api_id` and `api_hash`.
**Record:** both, in OpenBao at `<interface-path>/telegram/operator-app`.
They are shown once per application. Losing them means creating another.
---
## Step 3 — Mint the MTProto session
**Why not automated:** the login code arrives out of band, on the device. The
command is interactive by necessity — but *only this command*, and only once.
```bash
provision session bootstrap --campaign hall-of-helix
```
It prompts for the phone number, the login code, and the 2FA password, then
writes the session string to OpenBao at
`<interface-path>/telegram/operator-session`.
The session string is a **full-account credential** — it can do anything the
account can. It never leaves OpenBao, is never given to the adapter, and is used
only by the provisioner. Treat losing it as losing the account.
**Verify:**
```bash
provision session check --campaign hall-of-helix # prints the account, no secrets
```
---
## Step 4 — Hand over to the provisioner
From here nothing is manual. The remaining work is `FT-WP-0002` T03T06:
```bash
provision plan --spec ../pr-hall-of-helix/presence/telegram.yaml # read the diff
provision apply --spec ../pr-hall-of-helix/presence/telegram.yaml # execute it
```
`apply` registers the bot through BotFather, sets its name, about text,
description and avatar, creates both channels, adds the bot as administrator with
`post_messages` only, generates the redaction salt if it is absent, and writes
`presence/resolved/hall-of-helix.yaml`.
**Read the plan before approving it.** That is the human judgement this design
keeps — not clicking through BotFather, but deciding whether the diff is what
was intended.
---
## Re-running this
Steps 12 are once per operator account, ever. Step 3 repeats only if the session
is revoked — by a password change, an explicit sign-out, or Telegram invalidating
it. When that happens, re-run Step 3 alone; nothing else is affected, because
resolved state and the bot token do not depend on the session that created them.
Step 4 is safe to repeat at any time. It is a converging reconciler, and a second
apply over an unchanged spec does nothing.
## When a step stops being necessary
Re-read the **Why not automated** lines whenever Telegram changes its API surface,
and delete the step if the reason has expired. A runbook nobody prunes becomes a
description of how things used to work, and the manual steps in it start looking
like requirements rather than gaps.