julie-extract v2.37.2
julie-extract v2.37.2
classification: compatible
This release fixes a race in the store request contract. A consumer
enumerates a delta, then submits one store update per added or changed
file. When the file was deleted between that enumeration and julie-extract's
read, the whole request failed with source file could not be read, and the
consumer's delta failed with it. Field evidence: three failed incremental
scans plus backoff in one workspace during branch-switch churn on
2026-08-26.
Vanished source files commit as deletions
store update: when the planning read fails withNotFound, the request
now records a delete for the file under the same request id and
idempotency key, commits, and reportsoperation: updatewith
state: committed. The manifest disposition iscreatedwhen the file
was indexed andreusedwhen it never was.store updatereplay: a retry whose idempotency key maps to a delete row
adopts that row when it names exactly the update's file in the same
family, root, and view. Any other cross-kind match stays
idempotency_conflict. The old blanket conflict made the fallback
unretryable after a crash.store import: a file that vanishes between discovery and the planning
read is left out of the plan instead of failing the import.- Only
NotFoundgets this treatment. Permission, I/O, and decode errors
still fail the request.
Decision record: docs/decisions/2026-08-27-vanished-file-delta-semantics.md.
Compatibility
Artifacts stay schema 7, JSONL stays contract v5, family stores stay store
schema 2, store format epoch stays 1, and extraction identity epoch stays 7.
The report shape is unchanged; only the outcome for a vanished file moves
from a failed request to a committed one. Consumers that treated that
failure as fatal now see the committed delete they would have requested one
enumeration later.