managarten/services/mana-ai/src
Till JS b297f68ee4 fix(articles, mana-ai): rollout-block hardening for sync_changes projections
Four cross-cutting fixes that make the bulk-import worker safe to run
under real production load. All four were called out as live-rollout
risks in the post-ship review of docs/plans/articles-bulk-import.md.

#1 — Same fieldMetaTime bug fixed in mana-ai
   The articles fix in 054b9e5be hoists the helper to its own file
   `apps/api/src/modules/articles/field-meta.ts`. The same naive
   `rowFM[k] >= localTime` LWW comparison existed in three more
   projections under services/mana-ai (missions-projection,
   snapshot-refresh, agents-projection). Once any F3 stamp lands
   beside a legacy-string stamp, the comparison evaluates
   `'[object Object]' >= 'ISO-…'` (false) and the older value wins.
   New `services/mana-ai/src/db/field-meta.ts` — same helper,
   deliberately duplicated (each service treats sync_changes as a
   read-only event log; sharing infra across services is out of
   scope here). All 61 mana-ai bun tests still pass.

#2 — Stale 'extracting' items recycle
   If the worker dies mid-fetch (OOM, pod restart), items stay in
   state='extracting' forever and the job never completes. New sweep
   at the start of `processOneJob`: items whose lastAttemptAt is
   older than 5 minutes get bounced back to 'pending' so the next
   tick re-claims them. STALE_EXTRACTING_MS tuned for the 15s
   shared-rss fetch + JSDOM-parse worst case.

#3 — Pickup-row GC
   Every 30 ticks (~once per minute) the worker hard-deletes
   articleExtractPickup rows older than 24h. Without this a stuck
   pickup-consumer (all tabs closed, Web-Lock mismatch) would let
   sync_changes accumulate without bound. Logs the row count when
   non-zero so we can spot stuck consumers in the wild.

#4 — DRY consent-wall heuristic
   Identical CONSENT_KEYWORDS + threshold lived in routes.ts AND
   import-extractor.ts. Hoisted to
   `apps/api/src/modules/articles/consent-wall.ts`; both call sites
   now share one heuristic.

Plan: docs/plans/articles-bulk-import.md.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-29 00:53:39 +02:00
..
clients feat(mana-ai): v0.7 — cross-tick Deep Research Max pre-planning 2026-04-22 17:56:06 +02:00
cron feat(llm-aliases): M5 — migrate consumers to MANA_LLM aliases 2026-04-26 21:26:03 +02:00
crypto feat(mana-ai): encrypted resolver + tick uses Mission Grant to decrypt scoped inputs 2026-04-15 13:42:31 +02:00
db fix(articles, mana-ai): rollout-block hardening for sync_changes projections 2026-04-29 00:53:39 +02:00
middleware feat(mana-ai): scaffold server-side Mission Runner (v0.1) 2026-04-14 23:48:30 +02:00
planner feat(llm-aliases): M5 — migrate consumers to MANA_LLM aliases 2026-04-26 21:26:03 +02:00
config.ts feat(mana-ai): wire context-window compactor into mission runner (M2.3) 2026-04-23 15:28:20 +02:00
index.ts feat(ai): Mission Grant consent UI + Workbench audit tab 2026-04-15 13:53:11 +02:00
metrics.ts feat(mana-ai): wire context-window compactor into mission runner (M2.3) 2026-04-23 15:28:20 +02:00
tracing.ts feat(mana-ai): OpenTelemetry tracing + Grafana Tempo backend 2026-04-16 15:21:23 +02:00