Страницы · Health Debug
M7 — Contraceptive Security — Session Card
Planning artifact. A future build session opens this file to know exactly what to build for the Contraceptive Security module, in what order, with what entry dependencies and done criteria. No production code lives here. Read alongside
docs/plan/13-execution-modules-and-sessions.md(the execution framework),docs/plan/03-protocol-engines.md§7 (the engine spec), anddocs/plan/04-backend-togo.md(schema/migration/plugin rules).
Purpose
The Contraceptive Security engine tracks contraceptive-method adherence with per-method state machines, because a daily pill, a monthly injection, and a long-term implant have fundamentally different schedules and failure modes. Like every Health Debug engine it lives only in the ToGO backend (the Single Source of Truth); every client renders server state and submits log intents. The engine is strictly categorical — it branches on what the method is, never on hormone dosage or brand pharmacology — and it never states protection status ("you are/aren't protected"): every consequence-shaped question terminates in "Consult your doctor." This module ships on backend, web, mcp, apple, android, desktop — no chrome surface (a browser popup is the wrong place for contraceptive tracking; matches M6 Cycle).
Engine parameters (exact — from 03-protocol-engines.md §7 / shared context)
| Parameter | Value | Notes |
|---|---|---|
| Differentiated method types | daily pills, monthly injections, implants | Closed enum: daily_pill | monthly_injection | implant. The engine's logic branches on the method type (categorical), never on dosage. |
| Per-type schedule / validity rules | UNDEFINED BY SPEC — OPEN QUESTION | Pill day-window/grace, injection due-date tolerance, implant validity duration + expiry-reminder lead time are not in the spec. Do not invent numbers. See Notes & gotchas / 03 §7.2, §11 Q7. |
| Cycle Engine (M6) interaction | UNDEFINED BY SPEC — OPEN QUESTION | Whether an active method suspends Cycle Engine predictions is not in the spec. Fail-safe posture suggests suspension, but this is a product/clinical decision, never an engine guess. |
| Guidance on any missed/overdue/expiring state | "Consult your doctor." | The engine reports the logging fact only. It never states protection status, never advises doubling/skipping. (Core Opinion 2.) |
| Fail-safe | Report unconfigured/ambiguous and ask the user | When due-date math is ambiguous (e.g. missing injection date) the engine never assumes protection continuity. |
Note on "constants": unlike Hydration (250ml/5000ml/30s) or Caffeine (90min), M7 has no spec-fixed numeric protocol constant. The only fixed protocol facts are the three method-type enum values and the fail-safe/no-certainty posture. The per-type windows that would be the numeric constants are exactly the OPEN QUESTIONS above — so the SSOT/thin-client audit for M7 targets due-date math, protection-status logic, and local schedule computation, not literal magic numbers.
Proposed REST surface (names only — from 03 §7.6; reconcile against the frozen Phase 1 contract)
| Endpoint | Purpose |
|---|---|
POST /v1/engines/contraceptive/methods | Register a method (typed) |
GET /v1/engines/contraceptive/state | Current per-method snapshot |
POST /v1/engines/contraceptive/events | Log dose / injection / replacement |
GET /v1/engines/contraceptive/history | Adherence-to-logging history |
Session table
Surfaces are executed in the fixed order backend → web → mcp → apple → android → desktop (chrome omitted). The backend session MUST land before any client session. <date> = ISO build date; NN = zero-padded sequence — leave both as placeholders until the session runs.
| Session ID | Surface | Scope (what this one session builds) | Entry deps | Done criteria (doc 13 §5) | Plan docs to read |
|---|---|---|---|---|---|
S-<date>-M7-backend-NN | backend | The contraceptive ToGO plugin: pure core/ state machine with the three per-method sub-machines (DailyTrack / MonthlyTrack / LongTermTrack per 03 §7.3); plugin.go kernel registration (routes, config, hook subscriptions, migration manifest); expand-contract migration for method + event tables; the four endpoints returning computed per-method state; fail-safe unconfigured/ambiguous handling; engine unit tests encoding the categorical differentiation as executable spec; integration test against real Postgres. Rule sets are read through the Microkernel config/hook layer (future doctor "Medical Restrictions" overlay), never hardcoded. Per-type window rules and Cycle-suspension behavior land as explicitly-flagged sentinels/config, not invented numbers (see gotchas). | M0.1–M0.4 (kernel, TOGO auth, plugin framework, migration harness); coordinate with S-<date>-M6-backend (Cycle) — the "does an active method suspend Cycle predictions?" open question spans both engines, so M6 backend should exist first or the decision be recorded jointly | Backend-engine template: plugin registered on the kernel; migration is expand-contract and every column NOT NULL with a defined default (unconfigured/ambiguous modeled as a sentinel enum state, never SQL NULL); endpoints return computed state; engine unit tests encode the spec facts literally (daily pill vs monthly injection vs implant follow distinct machines; missed/overdue reports logging fact only; no protection-status output) and pass; integration test against real Postgres passes (idempotency replay on events, concurrent-log race); no protocol/schedule constant appears outside the engine's core/ package | 13 (§3, §5, §6); 03 §7 + §0 + §9.2 + §10; 04 §4 (NOT NULL rule), §5 (expand-contract), §8 (plugin purity), §9 (testing) |
S-<date>-M7-web-NN | web | Contraceptive tracking screen at /engines/contraceptive: register a typed method, log dose/injection/replacement events, and render the server's per-method snapshot + upcoming due items + missed/late history verbatim. All three method-type UIs render from server state; the screen computes no schedule and shows no protection verdict. Categorical method picker only. | M0.5–M0.7 (web shell, theme engine, i18n/RTL); S-<date>-M7-backend; M1 web as the reference-engine pattern to copy | Client-engine template: the screen renders /v1/engines/contraceptive/state (+ history) and submits register/log intents only; thin-client/SSOT audit passes — no due-date math, no schedule computation, no "protected/not protected" logic in client code (grep finds no per-type window logic); both dark-glow and light-flat themes render per the strict color spec; Arabic RTL mirrors correctly (incl. any progress/countdown for an expiring implant); all strings ICU, none concatenated; every AI-adjacent/consequence surface carries "Consult your doctor." | 13 (§3, §5); 05 §1, §3.1 (/engines/contraceptive route), §3.2 (['engine','contraceptive'] query), §4 (theme), §5/§5b (i18n/RTL), §7 (Log Entry Controls); 03 §7 |
S-<date>-M7-mcp-NN | mcp | A read-only status tool (e.g. contraceptive_status) that calls GET /v1/engines/contraceptive/state and returns the server snapshot verbatim (per method: type, upcoming due, missed/late — no protection claim). Register the CLI equivalent (healthdebug contraceptive status). Logging/write tools are out of M7 mcp scope (brief = "status read"). | M0.8 (MCP server + CLI skeleton); S-<date>-M7-backend | MCP template: the tool calls the real API with personal-access-token auth, returns server state verbatim, holds no protocol logic and no AI keys; it adds no interpretation and emits no medical-certainty text; deliberately-excluded surfaces stay excluded (no prediction/diagnosis passthrough). Whether MCP should also allow logging contraceptive events is flagged PENDING DESIGN, not built here | 13 (§5); 11 (Architecture, Planned tools table, Core Opinions, "Tool list grows with the engines"); 03 §7 |
S-<date>-M7-apple-NN | apple | iOS Contraceptive Security screen (part of Divergence #1 "Meds & Cycle Tracking on iOS"): render the server's differentiation of daily pills / monthly injections / implants and log adherence events against it. Reminder scheduling fires at server-provided instants only. Privacy-discreet presentation (lock-screen / complication discretion) is a first-class concern here. No HealthKit cycle-tracking data is used as input or output. | S-<date>-M7-backend; M1 apple (workspace + HDAPIClient/HDDesignSystem/HDLocalization scaffold); logically grouped with S-<date>-M6-apple (Cycle) under Divergence #1 | Client-engine template: iOS surface renders API state and logs intents only; SSOT audit — no regimen/schedule math on device (no per-type window constants embedded); both themes exact per §10.1 color spec (glow vs flat); full Arabic RTL mirroring incl. progress/ring direction; ICU strings, no concatenation; medical-certainty copy audit passes ("Consult your doctor.", no protection claims) | 13 (§5); 07 §1, §3.1 (client/backend line), §4 (Contraceptive row), §10 (theming/RTL), §11 (Closing Divergence #1 — Meds & Cycle); 03 §7 |
S-<date>-M7-android-NN | android | Handheld Kotlin/Compose Contraceptive Security screen: collect method + log intents, render the server's regimen differentiation and history. Reminders fire at server-scheduled instants via core/notifications (Divergence #3 layer); channel taxonomy includes cycle/contraceptive reminders. Wear/Auto/Glance parity for this engine is not required (it is not a companion-surface engine like Hydration/Pomodoro) unless design says otherwise. | S-<date>-M7-backend; M1 android (core/network, core/model, core/designsystem, core/i18n scaffold); logically alongside S-<date>-M6-android (Cycle) | Client-engine template: the screen POSTs method/log intents and renders API state only; thin-client architecture test — core/model stays data-only, no engine outcome computed anywhere (no per-type window rules in Kotlin); both palettes exact per §7.1; full LayoutDirection.Rtl Arabic pass incl. mirrored progress; ICU/values-ar, no concatenation; behavioral-only copy, "Consult your doctor." | 13 (§5); 08 §2 (thin-client matrix, Contraceptive row), §3 (layout), §7.1 (theme), §8 (notifications), §9 (RTL); 03 §7 |
S-<date>-M7-desktop-NN | desktop | Electron desktop Contraceptive Security view: reuse the shared packages/ui React components from the M7 web session inside the desktop shell; render server state, log via the same packages/api-client. No desktop-specific protocol logic; tray/quick-action involvement is optional and PENDING DESIGN (contraceptive logging may be intentionally kept to the full window for privacy). | S-<date>-M7-backend; S-<date>-M7-web (shared components + api-client hooks); M1 desktop (Electron shell scaffold, Phases 1–2 stable) | Client-engine template: renderer reuses shared components and renders API state only; SSOT conformance gate — no protocol/schedule constants in apps/desktop or packages/* (only server-provided display strings); both themes exact per §9 palette; Arabic RTL incl. mirrored progress across window/popover; ICU catalogs shared, no concatenation; AI/consequence copy defers to "Consult your doctor." | 13 (§5); 09 §3 (architectural rules), §4 (code sharing with web), §9 (theme), §11 (i18n/RTL); 05 (shared component contracts); 03 §7 |
Notes & gotchas
- Reuse the reference-engine pattern. M1 (Hydration) is built end-to-end first as the reference; every M7 per-surface session should copy its established shape (plugin
core/+plugin.golayout, web engine-card/route pattern, MCP tool wiring, native screen scaffold) so these sessions go faster. M6 (Cycle) is the closest sibling — same "not on chrome," same Divergence #1 grouping on Apple, same fail-safe/no-certainty posture — reuse its decisions where they transfer. - No invented numbers — this is the headline liability. Per-type window/validity rules (pill day-window/grace, injection due tolerance, implant validity duration, expiry-reminder lead time) are PENDING DESIGN / OPEN QUESTION (
03§7.2, §11 Q7). The backend must model these as loaded config/sentinels behind the Microkernel config-hook layer (so a future doctor "Medical Restrictions" overlay can set them without an engine rewrite —03§10,04§8), not as constants baked intocore/. If a session needs a concrete window to proceed, it stops and records the open question — it does not guess. - Cycle interaction is cross-engine and clinical (PENDING DESIGN). "Does an active contraceptive method suspend Cycle Engine (M6) predictions?" is unresolved (
03§7.7, §11 Q7). Fail-safe posture suggests suspension, but it must be a product/clinical decision. Coordinate the M7 and M6 backend sessions; whichever lands second must reconcile the interaction and record the decision as a classifiedarchitecture-decision/open-questionmemory and (if it changes behavior) an edit to03. - Never emit protection status. On any missed/overdue/expiring state the engine reports only the logging fact; it must never render "you are protected / not protected," efficacy percentages, or dosing advice. Every such surface terminates in "Consult your doctor." (Core Opinion 2 — strict here.) Copy audits are a client-session done-criterion.
- Privacy/discretion is a real requirement, and PENDING DESIGN. Reminder surfaces and privacy presentation — lock-screen discretion, watch complications, whether contraceptive logging appears in tray/widgets at all — are PENDING DESIGN (
03§7.4). Treat contraceptive data as sensitive; default to discreet. - Method switching / archival. Overlap semantics when switching method (pill → injection: archive old machine, instantiate new) are an open question (
03§7.7). Model archival explicitly; do not silently drop history. - Schema discipline (backend). Every column NOT NULL with a defined default; the
unconfigured/ambiguousfail-safe is a sentinel enum state, never SQL NULL; all changes strictly expand-contract withatlas migrate lintas the CI gate (04§4, §5). Method type is a closed enum; events are append-only with an idempotency key (04§7) so an AI/watch retry cannot double-log. - MCP is read-only for M7. The brief scopes MCP to a status read. No
log/write tool and no prediction/diagnosis passthrough. Keep the deliberately-excluded posture; revisit only if a later product decision opens it (PENDING DESIGN). - No chrome cell exists for M7. Do not create one; the module grid intentionally has no
chromecolumn here (matches M6).
Handoff reminder
At session end, follow the Brain Handoff Protocol (docs/plan/13-execution-modules-and-sessions.md §6): write one session-handoff memory to the healthdebug cabrain brain — retain the content in the §6 structure, then memory/edit to attach metadata — with a unique source_ref: handoff/M7-contraceptive-security/<surface>/<n> (never reuse a ref) and metadata {project:"healthdebug", category:"session-handoff", era:"greenfield", status:"current", surface:"<surface>", module:"M7", title:"Handoff <session-id>", tags:[...], next:"<module+surface>"}. Then update the single build-ledger memory (source_ref: build-ledger, edited in place) so one recall shows the whole frontier and the recommended next session. Any new architectural decision or open question (e.g. the Cycle-suspension resolution, a chosen per-type window rule) also gets its own classified memory and, if it changes the plan, an edit to the relevant plan doc.