Files
mesh-catalog/modules/mesh-mail-reader
jochen 0e9004664c issue 1858: write correct's line in its own transaction, and guard who writes the log (1858.6)
ADR 0517 §5: correct keeps the entry's change, its reading lesson and one corrected line together, or none
of them; a test reads the source to prove only the acts write the action log, and each new verb refuses an
ungranted caller. The README and the callers setting name the twelve verbs.
2026-10-22 19:56:16 +02:00
..

mesh-mail-reader — the default holder of mail-reading

Design 59, milestone 2 (mail reading); built from mesh-mail's own source, like mesh-mail-web and mesh-mail-notifier (novox/hq ADR 0459). One instance, held once for the mesh, on the machine mesh-mail runs on, under its own account (runs-as) — it hears mesh-mail's restricted stream MAIL, which the operator account never does. It reads mail; it moves, flags, deletes and sends nothing (ADR 0459 §11).

What it does

  • Claims mail-reading (held once for the mesh), declared in mesh-mail's own manifest beside its three mail seats, serving twelve verbs (ADR 0459 §2, ADR 0517 §4). Each answers only a caller the trusted setting callers names (default ["mesh-mail-web"]); any other caller is refused, naming why.
  • Hears mesh-mail's added events and judges a batch of up to 6 at a time (ADR 0516 §3) against a question put to claude_code_judge, keeping one entry per message — never its body — in its own database: one Gmail message in INBOX and All Mail is one entry, by its Message-ID, else its folder and UID (issue 1849).
  • Notes what each mail asks (ADR 0516, issue 1857): at most 3 tasks (a line and a due date), 3 promises (you promised, waiting on others, on its way; who and a date) and whether it is read later, each line the model's own words of at most 120 characters; a line sharing 8 words in a row with the mail fails the batch.
  • Reads the last 14 days once more after delivery (ADR 0516 §5): the inbox mail of each granted account, in ordinary batches after any mail just heard; kept as done, and the journal says its start, end and count.
  • Keeps the operator's handling and an action log (ADR 0517, issue 1858): an item (a task, a promise or the mail itself) handled, undone until the day ends, or reminded until the next day (Europe/Brussels); one line per act — what, mail id, item, mode, when, never mail text — kept 365 days, removed each night.
  • Keeps a health of its own, mail_reader_health: unhealthy once a judgement is refused, times out or answers out of shape; healthy once one succeeds, saying when, or that no batch has run yet (issue 1580).
  • Tells the operator at most once a batch when a mail matters, and corrects itself at once, keeping a reading lesson, when the operator says it judged wrong (issue 1428, 1429, 1522).

Its database

Its own postgres-database: mail entries with their tasks and promises, mail groups, reading lessons, the mails heard but not yet read, its health state, whether the 14-day re-reading was done, each item's handling and the action log. No column holds a mail body or text taken from one. The schema is numbered migrations (migrations/) and the consolidated schema.sql; a unit test proves the two agree.

Tools

tool does
mail-reading.entries every mail entry: headers, mail group, summary, mark and why, due date. Read-only
mail-reading.groups every mail group a batch has made, largest first. Read-only
mail-reading.correct correct one entry's mark, mail group, why or due date, say a task is not one, remove a promise, set or clear read later; kept at once as a reading lesson, with one corrected line
mail-reading.lessons the reading lessons kept, at most 40. Read-only
mail-reading.undo undo one reading lesson
mail-reading.status healthy or not, when a batch last succeeded (or that none has run yet), lessons per 100 mails read each week. Read-only
mail-reading.list the operator's list for a mode: today, this week, later, the promises by kind, good to know, read later, handled today, scam warnings, and when the operator last looked. Read-only
mail-reading.handle mark an item handled (the mail itself handles all its items); one handled line
mail-reading.unhandle undo a handling of today; one undone line
mail-reading.remind hide an item until the next day, when it is under today; one reminded line
mail-reading.record one line for an act that changes no entry: opened, mode, page opened
mail-reading.actions the action log, newest first. Read-only
mail_reader_health how mesh-mail-reader is: unhealthy once a judgement is refused, times out or answers out of shape, naming which and since when; healthy, saying when the last batch succeeded or that none has run yet. Read-only

Where it runs

Its own account (runs-as), because it hears mesh-mail's restricted stream MAIL (novox/hq ADR 0376 §2). Held once for the mesh, on the machine mesh-mail runs on; it is granted reading only, after issue 1227's split of mesh-mail's grants is delivered (ADR 0472: that split is won't-fix — mesh-mail's grants stays one list per account, and mesh-mail-reader is put on it after delivery, never asking to send).