Skip to content

feat(server): add bounded retention cursor windows#63

Merged
khaliqgant merged 1 commit into
mainfrom
codex/relayauth-bounded-gc-v2
Jul 22, 2026
Merged

feat(server): add bounded retention cursor windows#63
khaliqgant merged 1 commit into
mainfrom
codex/relayauth-bounded-gc-v2

Conversation

@khaliqgant

@khaliqgant khaliqgant commented Jul 22, 2026

Copy link
Copy Markdown
Member

Summary

  • add platform-neutral rowid cursor scans capped at 1,000 existing rows
  • count and delete expired tokens/audit entries only inside the proven closed rowid window
  • preserve the existing batch APIs and their executor type
  • expose D1 scan metadata for scheduler observability
  • bump @relayauth/server to 0.2.21

The implementation has no Cloudflare imports, no MATERIALIZED planner-hint dependency, and uses 3 binds for token operations / 6 for audit operations (well below D1s 100-parameter limit). The 90-day audit default is unchanged.

Safety

  • scan statement: intrinsic rowid range seek + ORDER BY rowid LIMIT <= 1000
  • mutation statement: rowid > cursorBefore AND rowid <= cursorAfter
  • sparse rowid gaps are skipped without scanning deleted rows
  • inserts after a closed scan cannot enlarge the range while its upper row still exists; concurrent deletes only shrink it
  • empty/exhausted windows do not advance or delete

Verification

  • npm --workspace @relayauth/server run typecheck
  • npm --workspace @relayauth/server test (407 passed)
  • npm --workspace @relayauth/server run build
  • npm pack --workspace @relayauth/server --dry-run
  • query-plan regression asserts no temporary B-tree and INTEGER PRIMARY KEY rowid range searches

Release gate

Owner merge and npm publish are required. Do not self-publish.

Review in cubic

@gemini-code-assist

Copy link
Copy Markdown

Caution

The consumer version of Gemini Code Assist on GitHub has been sunset. All code review activity has officially ceased.

@cursor

cursor Bot commented Jul 22, 2026

Copy link
Copy Markdown

Bugbot is not enabled for your account, so this pull request was not reviewed.

Enable Bugbot in the Cursor dashboard to get automatic reviews on future PRs.

@coderabbitai

coderabbitai Bot commented Jul 22, 2026

Copy link
Copy Markdown

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 053ed74e-5cae-4a44-8855-10c103b1b6f1

📥 Commits

Reviewing files that changed from the base of the PR and between ae6c795 and e55e85f.

⛔ Files ignored due to path filters (1)
  • package-lock.json is excluded by !**/package-lock.json
📒 Files selected for processing (4)
  • packages/server/package.json
  • packages/server/src/__tests__/exports.test.ts
  • packages/server/src/__tests__/retention-gc.test.ts
  • packages/server/src/engine/retention-gc.ts

📝 Walkthrough

Walkthrough

Changes

Retention GC windowing

Layer / File(s) Summary
Bounded window APIs and execution
packages/server/src/engine/retention-gc.ts, packages/server/src/__tests__/exports.test.ts, packages/server/package.json
Adds cursor/window contracts and APIs for scanning and pruning token and audit rows within bounded rowid ranges, validates window invariants, verifies exports, and increments the package version.
Window behavior and query-plan validation
packages/server/src/__tests__/retention-gc.test.ts
Tests sparse rowid handling, closed-window deletion, exhaustion, retention settings, size limits, cursor execution, and SQLite query plans.

Estimated code review effort: 4 (Complex) | ~45 minutes

Sequence Diagram(s)

sequenceDiagram
  participant RetentionGcApi
  participant scanRowidWindow
  participant SQLite
  RetentionGcApi->>scanRowidWindow: request bounded rowid window
  scanRowidWindow->>SQLite: ordered rowid seek query
  SQLite-->>scanRowidWindow: rowids and window metadata
  scanRowidWindow-->>RetentionGcApi: closed window and cursor
  RetentionGcApi->>SQLite: prune or purge within closed window
  SQLite-->>RetentionGcApi: deletion result
Loading

Poem

I’m a bunny with a cursor, hopping row by row,
Skipping every rowid hole where empty burrows grow.
Windows close, new rows wait,
Audit trails meet tidy fate.
Tests guard the path with cheer—
Fresh releases thump their feet! 🐇

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 28.57% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly summarizes the main change: adding bounded retention cursor windows in the server package.
Description check ✅ Passed The description is directly related to the changeset and accurately describes the new windowed retention GC behavior and version bump.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codex/relayauth-bounded-gc-v2

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 Checkov (3.3.8)
packages/server/package.json

Traceback (most recent call last):
File "/usr/local/bin/checkov", line 2, in
from checkov.main import Checkov
ModuleNotFoundError: No module named 'checkov'


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: e55e85fc3f

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +49 to +52
export type RetentionGcWindowScanResult = RetentionGcWindow & {
expiredCount: number;
/** D1 query metadata for the bounded rowid scan, when supplied by the executor. */
meta?: RetentionGcRunMeta;

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P1 Badge Keep the published scan result Node-neutral

RetentionGcWindowScanResult now explicitly exposes D1 query metadata from a published @relayauth/server API. This reintroduces a Cloudflare-shaped contract into the OSS package; keep the interface expressed in plain Node/SQL terms and put any D1-specific adapter behavior in the cloud repository instead.

AGENTS.md reference: AGENTS.md:L191-L193

Useful? React with 👍 / 👎.

Comment on lines +185 to +188
* The first statement is a rowid B-tree range seek. It efficiently crosses
* sparse rowid gaps without evaluating expiry predicates outside the returned
* window. Once cursorAfter is fixed, later inserts receive higher rowids and
* cannot enlarge the range; concurrent deletes can only shrink it.

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P2 Badge Prevent rowid reuse from reopening closed windows

The claimed closed-range guarantee does not hold for these tables because their implicit SQLite rowids are not AUTOINCREMENT. If a concurrently running cleanup deletes the highest scanned row before another writer inserts, SQLite can assign that new row an id at or below cursorAfter; the later range delete can then remove an unscanned expired/backfilled row, and a live replacement can be skipped by subsequent cursors. Preserve candidate identities or use a transaction/snapshot rather than treating a rowid range as immutable.

Useful? React with 👍 / 👎.

@khaliqgant
khaliqgant merged commit 09ae69d into main Jul 22, 2026
4 checks passed
@khaliqgant
khaliqgant deleted the codex/relayauth-bounded-gc-v2 branch July 22, 2026 13:43
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.

1 participant