Skip to content

fix(api): persist attestation timestamps for Hosted campaigns (#32) - #133

Merged
CodewithJha merged 1 commit into
CodewithJha:mainfrom
BasilZafar11:codex/issue-32-attestation-metadata
Nov 1, 2026
Merged

CodewithJha merged 1 commit into
CodewithJha:mainfrom
BasilZafar11:codex/issue-32-attestation-metadata

Conversation

@BasilZafar11

@BasilZafar11 BasilZafar11 commented Oct 22, 2026 •

Copy link
Copy Markdown
Contributor

Summary

Fixes #32

Accepted demo campaign starts persist a server-generated UTC attested_at in the attestation.accepted event. Observe-only ingestion persists it alongside attestation: true in campaign config. Uploaded timestamps cannot override the server value; idempotent retries retain the original timestamp, while conflicting configuration still returns 409.

This implements the issue's timestamp option. The metadata stores neither an operator note nor a token fingerprint. Single-tenant authorization remains possession of the configured shared token; timestamps do not identify an individual. Existing records are not backfilled. SECURITY.md and PRODUCTION_READINESS document these boundaries.

The branch is rebased onto upstream main e704396. SECURITY.md retains both the upstream Container deployment section and the Attestation audit metadata section. The redundant font commit is dropped because its contents are already in main. The PR contains one attestation commit and exactly six changed files: the two API implementation files, two integration test files, SECURITY.md, and PRODUCTION_READINESS.md. There are no apps/web changes.

Type of change

  • Bug fix
  • Tests
  • Hosted API / UI (secondary surface)

Checklist

  • Read CONTRIBUTING.md and repository policies
  • Linked related issue
  • Core stays free of framework SDK imports
  • Tests updated for behavioral changes
  • Documentation matches implementation
  • One attestation concern per PR
  • Authorized local testing only

Test plan

After rebasing:

  • MUTINY_SAMPLE_OFFLINE=1 uv run --locked pytest tests/integration -q --tb=short: 183 passed.
  • uv run --locked ruff check: passed.
  • git diff --check upstream/main...HEAD: passed.
  • Compared the two API implementation files and two integration test files with reviewed commit 2acff06: unchanged.
  • Verified the PR diff contains no apps/web changes; SECURITY.md preserves both sections.

Regression coverage checks persisted timestamps with and without authentication, false-attestation rejection, forged ingest timestamps, retry stability, and absence of the request bearer token from database contents and captured logs. Existing Hosted execution/filesystem isolation tests pass.

Full unit/reliability, container, CLI, web and isolated artifact gates are left to CI for this mechanical rebase. Vercel deployment authorization remains a maintainer action.

@vercel

vercel Bot commented Oct 22, 2026

Copy link
Copy Markdown

@BasilZafar11 is attempting to deploy a commit to the priyanshu's projects Team on Vercel.

A member of the Team first needs to authorize it.

@BasilZafar11

Copy link
Copy Markdown
Contributor Author

Fixed the web-build failure by bundling fonts locally. All six CI checks now pass. Vercel deployment still requires team authorization.

@CodewithJha CodewithJha left a comment

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for working on this. I reviewed the implementation against #32 (P1-1) and the fix itself is in good shape. The remaining blocker is mechanical.

What is working

  • Accepted starts now persist attestation: true and a server-generated UTC attested_at in the attestation.accepted event. Ingest persists the same fields in the campaign config. Client-supplied timestamps cannot override it.
  • attested_at is excluded from the config-fingerprint comparison, so an idempotent retry keeps the original value instead of causing a spurious 409. Conflicting config still returns 409.
  • The tests are real regression tests. On this branch the auth and ingest integration files give 64 passed. With ingest.py and supervisor.py reverted to main and your tests kept, 3 fail: test_start_persists_attestation_timestamp[client], test_start_persists_attestation_timestamp[client_no_auth] and test_attestation_timestamp_is_server_owned_and_stable.
  • The SECURITY.md and PRODUCTION_READINESS wording is honest. It says attestation is an operator acknowledgment and not authorization, that this is server receipt time and not local execution time, and that old records are not backfilled.

What still needs to change

  1. Resolve the conflict with main in SECURITY.md. #135 merged a "Container deployment (MUT-012 / #63)" section at the same place as your "Attestation audit metadata (P1-1)" section. Keep both sections. They are independent.
  2. Drop the font commit when you rebase. fix(web): bundle fonts... is now redundant. The same fonts and layout.tsx landed in main through #135, and I checked that the files are byte-identical. After rebasing onto main, this PR should touch only apps/api, the two integration test files, SECURITY.md and docs/PRODUCTION_READINESS.md. Please make sure the diff shows no apps/web changes.

Important

Please don't force-push over anything I haven't reviewed. A normal rebase onto main is fine. Once the diff is down to the API change, the fix and its tests don't need changes.

Suggested direction

git fetch origin && git rebase origin/main, skip the font commit when git reports it empty or already applied, resolve SECURITY.md by keeping both sections, rerun uv run pytest tests/integration, and push.

Once addressed, push the updates and I'll re-review.

@BasilZafar11
BasilZafar11 force-pushed the codex/issue-32-attestation-metadata branch from 3102aea to 706b0c0 Compare October 29, 2026 04:59
@BasilZafar11

Copy link
Copy Markdown
Contributor Author

Rebased onto current main, preserved both SECURITY sections, and dropped the redundant font commit. The diff now contains only the six requested files. Reviewed API code and tests are unchanged. All 183 integration tests and seven CI checks pass. Ready for re-review.

@CodewithJha
CodewithJha self-requested a review November 1, 2026 11:27

@CodewithJha CodewithJha left a comment

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @BasilZafar11, this is exactly what I asked for. (To clear up my earlier wording: a rebase plus a force-push to your own branch was fine, and that's what you did.)

Re-review of 706b0c0

  • ✓ Diff is now the six expected files. No apps/web changes, and both SECURITY.md sections (container deployment and attestation audit metadata) are kept.
  • ✓ attestation.accepted start events carry a server UTC attested_at. Ingest stores the server receipt time in campaign config. attested_at is excluded from the idempotency fingerprint, so a retry keeps the original value instead of returning a spurious 409.
  • ✓ Client-supplied timestamps cannot override it, and no bearer token or token fingerprint is stored.
  • ✓ Regression tests bite: with ingest.py/supervisor.py reverted to main, test_start_persists_attestation_timestamp[client], [client_no_auth] and test_attestation_timestamp_is_server_owned_and_stable fail. With the fix, 64/64 pass.
  • ✓ Full suite: 762 passed locally, and ruff check is clean. All seven CI jobs are green (the Vercel check fails on fork PRs for authorization reasons and is unrelated).
  • ✓ The docs are honest that attestation is still acknowledgment, not authorization.

Approving and merging.

@CodewithJha
CodewithJha merged commit 50b3555 into CodewithJha:main Nov 1, 2026
7 of 8 checks passed

Copy link
Copy Markdown
Owner

Merged. Thanks for the contribution.

You handled the idempotency side of this well. Leaving attested_at out of the config fingerprint is the detail that keeps retried ingests from turning into false 409s, and the test proves the original timestamp survives a retry. The clean rebase with both SECURITY.md sections kept made the final review easy.

This closes #32.

If you'd like to continue working on Mutiny, these would be good related areas to look at:

No pressure at all.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

hosted: persist attestation metadata beyond boolean checkbox (P1-1)

2 participants