Skip to content

feat(notifications): idempotent per-period recap claim + generation audit trail - #4470

Merged
JSONbored merged 3 commits into
JSONbored:mainfrom
oktofeesh1:feat-maintainer-recap-claim-audit-2249-2251-v2
Jul 9, 2026
Merged

feat(notifications): idempotent per-period recap claim + generation audit trail#4470
JSONbored merged 3 commits into
JSONbored:mainfrom
oktofeesh1:feat-maintainer-recap-claim-audit-2249-2251-v2

Conversation

@oktofeesh1

Copy link
Copy Markdown
Contributor

Summary

Resubmission of #4459 (closed due to a merge conflict with #4457, which landed while this PR was open and refactored runMaintainerRecapJob's delivery path to the new dual-channel runMaintainerRecap/RunMaintainerRecapResult shape). Same feature content, rebased onto current main and adapted to the new shape.

Scope

  • The PR title follows type(scope): short summary Conventional Commit format.
  • This PR bundles two small, closely-related deliverables (both non-conflicting edits inside the same runMaintainerRecapJob orchestrator, both "Part of Maintainer review recap digest (Discord / Slack) #1963") rather than splitting into two PRs that would each touch the exact same lines.
  • This follows CONTRIBUTING.md and does not reintroduce GitHub Pages, VitePress, site/, or CNAME.
  • I linked currently open issues this PR resolves — Closes #2249, Closes #2251.

Validation

  • git diff --check
  • npm run db:migrations:check — contiguous, next free 0130
  • npm run db:schema-drift:checkglobal_agent_controls stays raw-SQL-only (allowlisted)
  • npm run typecheck
  • npm run test:coverage locally — 654 test files / 12,796 tests green; 100% branch coverage on every changed line, verified against lcov.info
  • npm audit --audit-level=moderate — 0 vulnerabilities
  • Rebased cleanly onto current main (post-test(notifications): maintainer recap end-to-end orchestration #4457, post-feat(miner-manage): add maintainer-gate verdict poller (read-only) #4464) with no conflicts after the initial adaptation to the new dual-channel result shape
  • New or changed behavior has unit/integration tests for new branches, fallback paths, and sanitizer boundaries — see below.

Test coverage added/updated:

  • test/unit/db-parsers.test.ts: claimMaintainerRecapPeriod — first claim for a period wins, a retry for the same period loses, a different period wins again; fails open on a DB error.
  • test/unit/maintainer-recap-wire.test.ts: a retried tick within the same UTC date is a no-op (no repo scan, no second Discord post); a tick on a different UTC date gets its own fresh claim and sends again; the maintainer_recap_generated audit event's full metadata shape; a present manifest cadence override is reflected in the audit metadata over the env value. Existing tests updated for test(notifications): maintainer recap end-to-end orchestration #4457's delivery.discord/delivery.slack split shape.

Safety

  • No secrets, wallet details, hotkeys, coldkeys, user PATs, private keys, raw trust scores, private rankings, or private maintainer evidence are exposed.
  • Public GitHub text stays sanitized, low-noise, and does not imply compensation guarantees or optimization tactics.
  • Auth, cookie, CORS, GitHub App, Cloudflare, or session changes include negative-path tests. (N/A — no auth/CORS/session surface touched.)
  • API/OpenAPI/MCP behavior is updated and tested where needed. (N/A — no API/OpenAPI/MCP surface changed; internal job orchestration + a D1 column only.)
  • UI changes use live API data or real empty/error/loading states, not production mock/demo fallbacks. (N/A — no UI changes.)
  • Visible UI changes include a UI Evidence section. (N/A — no visible UI changes; backend-only.)
  • Public docs/changelogs are updated where needed; changelogs are only edited for release-prep PRs. (No changelog edit.)

UI Evidence

N/A — backend-only change (D1 migration + queue orchestrator), no UI surface touched.

Notes

  • The claim key is the UTC calendar date alone (not cadence-specific): daily fires at most once per date, and weekly fires on only ONE designated date per week, so date-only keying is correct for both cadences without needing to encode which cadence produced the tick.

…udit trail

Adds a per-UTC-date claim (migration 0129, mirroring
claimRegateFanoutSlot's atomic conditional-UPDATE pattern) so a
retried cron tick or redelivered queue message never re-scans repos
or re-sends the maintainer recap digest for a period already sent.
Also records a maintainer_recap_generated audit event once the
report is built, giving operators a ledger trail independent of the
per-channel delivery-outcome event.
…ip shape

Resolves the merge conflict with the JSONbored#4457 e2e-test refactor (which
introduced the dual-channel runMaintainerRecap/RunMaintainerRecapResult
shape): ranRecap now accepts the union of that result type and the
job-level MaintainerRecapJobSkipped ("already_sent_this_period") case.
@oktofeesh1
oktofeesh1 requested a review from JSONbored as a code owner July 9, 2026 20:24
@superagent-security

Copy link
Copy Markdown
Contributor

Superagent didn't find any vulnerabilities or security issues in this PR.

@codecov

codecov Bot commented Jul 9, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 94.02%. Comparing base (6020670) to head (cd00d00).
⚠️ Report is 2 commits behind head on main.

Additional details and impacted files
@@           Coverage Diff           @@
##             main    #4470   +/-   ##
=======================================
  Coverage   94.02%   94.02%           
=======================================
  Files         420      420           
  Lines       37479    37491   +12     
  Branches    13692    13694    +2     
=======================================
+ Hits        35240    35252   +12     
  Misses       1583     1583           
  Partials      656      656           
Files with missing lines Coverage Δ
src/db/repositories.ts 96.72% <100.00%> (+<0.01%) ⬆️
src/queue/processors.ts 95.39% <100.00%> (ø)
src/review/maintainer-recap-wire.ts 100.00% <100.00%> (ø)
🚀 New features to boost your workflow:
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@oktofeesh1
oktofeesh1 marked this pull request as draft July 9, 2026 20:37
…coverage

runMaintainerRecapJob never passes enabled:false to runMaintainerRecap
(the enable/disable decision already happened via isRecapEnabled
before this function is ever invoked), so the skipped:true branch is
unreachable from this call site -- mirrors the codebase's existing
v8-ignore-else convention for the same class of defensive narrowing.
@loopover-orb loopover-orb Bot added gittensor:feature Gittensor-scored feature linked to a feature issue — scores a 0.25x multiplier. gittensor:priority Maintainer-selected Gittensor priority — scores a 1.5x multiplier. labels Jul 9, 2026
@oktofeesh1
oktofeesh1 marked this pull request as ready for review July 9, 2026 20:54
@loopover-orb

loopover-orb Bot commented Jul 9, 2026

Copy link
Copy Markdown
Contributor

Warning

🟨🟨🟨🟨🟨🟨🟨🟨🟨🟨🟨🟨

⏸️ Gittensory review result - manual review recommended

Review updated: 2026-07-09 20:59:38 UTC

6 files · no blockers · readiness 96/100 · CI green · clean

⏸️ Suggested Action - Manual Review

  • Touches a guarded path — held for manual review: This PR changes guardrail-protected path(s): src/queue/processors.ts (matched src/queue/**).
Nits — 1 non-blocking
  • Touches a guarded path — held for manual review — A maintainer must review and merge this change.
Signal Result Evidence
Code review ✅ No blockers No AI review summary
Linked issue ✅ Linked #2249, #2251
Related work ✅ No active overlap found No same-issue or scoped active PR overlap found.
Change scope ✅ 20/20 Low review scope from cached public metadata (draft PR; 2 linked issues).
Validation posture ✅ 25/25 PR body includes validation/test evidence.
Contributor workload ✅ 10/10 Author activity: 32 registered-repo PR(s), 25 merged, 0 issue(s).
Contributor context ✅ Confirmed Gittensor contributor oktofeesh1; Gittensor profile; 32 PR(s), 0 issue(s).
Gate result ⚠️ Not blocking Advisory; not blocking this PR.
Linked issue satisfaction

Partially addressed
This diff delivers the per-period idempotency claim (claimMaintainerRecapPeriod, migration, audit event) and tests for the duplicate-tick no-op and claim-taken/already-claimed branches, but the PR's own description states the MaintenanceJob union entry and the gated processor case (this issue's other two explicit deliverables) were completed in a separate prior PR (#4418) and are not present in th

Review context
  • Author: oktofeesh1
  • Role context: outside_contributor
  • Public audience mode: oss maintainer
  • Lane context: Repository is configured for direct PR review.
  • Public profile languages: not available
  • Official Gittensor activity: 32 PR(s), 0 issue(s).
  • PR-specific overlap: none found.
Contributor next steps
  • Mark ready when done.
Signal definitions
  • Related work = same linked issue, overlapping active PRs, or title/path similarity.
  • Change scope = cached public metadata such as size labels, draft state, and review-burden hints.
  • Validation posture = whether the PR provides enough public validation/test evidence for maintainer review.
  • Contributor workload = public contributor activity and cleanup pressure, not a repo-wide quality failure.
  • Contributor context = public GitHub/Gittensor identity context; non-Gittensor status is not a blocker.

🟩 Safe / merged · 🟦 Advisory · 🟨 Held for review · 🟥 Blocked / closed


💰 Earn for open-source contributions like this. Gittensor lets GitHub contributors earn for the work they already do — register to start earning →.

Checked by Gittensory, a quiet PR intelligence layer for OSS maintainers.

  • Re-run Gittensory review

@JSONbored
JSONbored merged commit 8fafbdd into JSONbored:main Jul 9, 2026
10 checks passed
@loopover-orb loopover-orb Bot added gittensor:bug Gittensor-scored bug fix — scores a 0.05x multiplier. and removed gittensor:feature Gittensor-scored feature linked to a feature issue — scores a 0.25x multiplier. gittensor:priority Maintainer-selected Gittensor priority — scores a 1.5x multiplier. labels Jul 9, 2026
@JSONbored JSONbored added gittensor:feature Gittensor-scored feature linked to a feature issue — scores a 0.25x multiplier. gittensor:priority Maintainer-selected Gittensor priority — scores a 1.5x multiplier. and removed gittensor:bug Gittensor-scored bug fix — scores a 0.05x multiplier. labels Jul 9, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

gittensor:feature Gittensor-scored feature linked to a feature issue — scores a 0.25x multiplier. gittensor:priority Maintainer-selected Gittensor priority — scores a 1.5x multiplier.

2 participants