Skip to content

P2: lastInsertId string|number union loses 64-bit ids -- narrow to string #6

Description

@ssilvius

Severity: P2. Reviewed at 82b715c. Same data-loss class as the response-side tagged-value finding, not merely an ergonomics wart.

SPEC.md:120:

lastInsertId (OPTIONAL, string, number, or null)

last_row_id in SQLite is a 64-bit INTEGER. It can exceed the JS-safe integer range, and when it does, the number arm of the union rounds it. A client cannot tell a rounded id from an exact one.

The union also forces every client to branch on the type for a field that has exactly one semantic.

Fix: string or null

Encode as a decimal string, matching how S5 already encodes bigint ("decimal integer encoded as a JSON string"). Consistent with the existing type table, and lossless.

Cost today: near zero

The union is exercised by nothing in the repo. Verified at 82b715c:

  • The D1 worker projects whatever D1 returns, and D1 always returns a number.
  • The Durable Object hardcodes lastInsertId: null.

So no reference server relies on the number arm. Changing it now is cheap; changing it after third-party servers ship is not.

Acceptance

  • SPEC.md:120 narrows lastInsertId to string-or-null.
  • D1 worker example stringifies.
  • Conformance "nice to have" entry for lastInsertId expects the string form.

Origin: codex spec review (filed as ergonomics); reclassified as data-loss by smugglr.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions