ADR-010: Send the link only after the pack is verified; never reuse a pack name
Who is this for
Section titled “Who is this for”Developers and operators — read this before touching delivery, pack naming or the “pack is ready” message.
- The link is sent only when the Bot API reports 12 stickers and the public
t.me/addstickers/<name>page confirms the pack twice in a row. - Pack names are
pack<N>_<telegram_user_id>_by_<bot_username>; a name is never deleted, recreated or reused. - Status: accepted.
Context
Section titled “Context”Right after a sticker set is created, the link can open to “Sticker set not found” for some seconds. A guest who taps a dead link at an event walks away without a pack. Telegram clients also cache pack names, so a pack deleted and recreated under the same name stays “not found” on devices that saw the old one.
A second trap: the public page always answers HTTP 200, whether the pack exists or not. Only the page’s title differs. One test request also returned an empty body because of a network glitch.
Decision
Section titled “Decision”- After
createNewStickerSetthe job moves todeliveringand the worker slot is released. - A background check polls every 2 seconds for the first 90 seconds, then every 10 seconds
(
bot/delivery.py). - “Ready” means:
getStickerSetreturns 12 stickers, and the public page shows the “pack exists” title on two consecutive requests with a short pause. Anything else — missing title, network error, non-200 — counts as “not ready” (bot/services/telegram_stickers.py). Real captured pages are test fixtures. - The link is sent exactly once (
jobs.link_sent_at). - Names are numbered per account. The next number follows every pack the account ever had, including packs from reset accounts and interrupted attempts. If a name is taken, the next number is used.
- Telegram’s naming rules (length, first character, no double underscore, the
_by_<bot>suffix) are checked in code. The actual name is stored injobs.pack_nameandusers.pack_name; links are built only from it.
Alternatives considered
Section titled “Alternatives considered”| Alternative | Why not |
|---|---|
| Send the link immediately with a “wait 10–15 seconds” hint | Guests tap at once; a dead first impression. The hint text still exists in the code, unused. |
| Trust the HTTP status of the public page | It is always 200. |
| Delete a broken pack and recreate it with the same name | Client-side caches keep it “not found”. |
Consequences
Section titled “Consequences”- Delivery adds a couple of seconds: the load test measured about 2 seconds for the link check (LOAD_TEST_REPORT.md).
- The check depends on the wording of a public Telegram page. If Telegram changes it, every pack will look “not ready” and fail at the 15-minute deadline — the first thing to suspect when all deliveries stall.
- Orphan packs from interrupted attempts stay in Telegram forever; this is accepted.
tools/check_pack.pyruns the same two checks by hand.
Evidence
Section titled “Evidence”HANDOFF.md, “Pack names” and “The ‘pack exists’ signal on t.me”; fixturestests/fixtures/tme_pack_*.html.- Commits
914f47f,9fca59c,ac2a366.
Where to go next
Section titled “Where to go next”Last verified: 2026-11-13 against ai-sticker-pack@b715418 and ai-stickers-landing@e350ff5.