Skip to content

Changelog

Changelog

All notable changes to fdb-record-layer-go are recorded here. Format: Keep a Changelog; versioning per RELEASE.md (pre-1.0 v0.MINOR.PATCH).

This project is pre-1.0. The Go API may change across minor versions; the FDB wire format stays compatible with Java fdb-record-layer-core 4.12.11.0 across every release (the shared-cluster hard line — see RELEASE.md). Every entry’s Compatibility block answers the four questions a user upgrading between two refs needs: wire format, SQL behaviour, FDB client option semantics, and required dependency versions.

This changelog starts 2026-06-20; earlier history is in git log. There are no tagged releases yet — cutting the first v0.x tag is the maintainer’s decision (RELEASE.md §Versioning).

[Unreleased]

Added

  • Statement-wide memory byte budget for the SQL executor: opt-in OptMaxStatementMemoryBytes bounds every cardinality-growing buffer by bytes (not just the 100k-row MaterializationLimit); breach → SQLSTATE 54F01. Default 0 = unlimited (RFC-130).
  • A documentation-consistency CI guard (pkg/docscheck) that fails the build if a living doc drifts from the MODULE.bazel / go.mod version pins or reintroduces a known contradiction (RFC-131/132).
  • A public FDB client option matrix (pkg/fdbgo/fdb/OPTIONS.md) classifying every Set* option as honored / UnsupportedOptionError / safe no-op, each with its libfdb_c 7.3.77 reference, plus a completeness guard that fails CI if an option is added without a matrix row (RFC-133).
  • A panic-boundary release gate (RFC-134): a norecover nogo analyzer fails the build if a recover() is added outside the documented panic→error boundary allowlist (docs/panic-audit.md §2), plus docscheck guards that keep the four input-boundary fuzz nets wired and the doc in lockstep with the allowlist. Makes the “untrusted input → error, never crash” discipline self-enforcing.

Changed

  • FDB C++ wire-protocol baseline bumped 7.3.75 → 7.3.77 (RFC-152). Patch bump within the 7.3 line: no wire-format, error-code, ClientKnobs, RYW, or serialization change (regenerated pkg/fdbgo/wire/types/*_generated.go differ only in the version-string header comment). The only client-relevant upstream delta is PR #12935 (a peer->disconnect arm in waitValueOrSignal so loadBalance fails an in-flight request immediately on peer disconnect instead of waiting out the failure-monitor lag); the pure-Go client already has this structurally (single-owner connection: readLoop EOF → failConnectionfailAllPending), pinned by TestPeerDisconnect_FailsInFlightReplyImmediately. No production-code behaviour change.
  • SQL LIMIT/OFFSET now flows through a single uniform RecordQueryLimitPlan + continuation envelope, including for nested derived tables (RFC-128).

Fixed

  • Legacy Java store layouts are now fully readable, writable, and auto-upgraded — closes the FormatVersion < 6 / omit_unsplit_record_suffix wire-compatibility gap that was previously a silent data-correctness bug (Go accepted an old-format store header but only understood the modern inline layout, so it would silently fail to see a legacy store’s record versions and unsplit records). Go now mirrors Java’s FDBRecordStore.useOldVersionFormat() end-to-end: record versions are read/written in the separate RecordVersionKey(8) subspace for stores below SAVE_VERSION_WITH_RECORD (format 6), and unsplit records are read/written at the bare primary key (no 0 suffix) when omit_unsplit_record_suffix is set — across load, scan, scanRecordKeys, recordExists, save, update, delete, and deleteRecordsWhere. On open, Go also performs Java’s transactional format upgrade (checkRebuild/addConvertRecordVersions): it bumps the stored FormatVersion, sets omit_unsplit_record_suffix for a non-splitting store created before format 5, and moves versions from subspace 8 to their inline pk + -1 location when upgrading a splitting store past format 6. Pinned by FDB integration tests that lay down each legacy layout and assert byte-level read/write/scan/delete and migration parity with Java. (Closes the TODO.md “no read path for format-version-<6 record versions / unsplit records” gap surfaced by the RFC-131 audit.)
  • SQL pagination no longer treats a non-terminal StartContinuation as end-of-results (a latent early-truncation bug); exhaustion is decided off IsEnd(), not byte-emptiness (RFC-127).
  • Pure-Go FDB client: Get/GetRange read-conflict ranges are clamped to the data actually returned and filtered through the RYW overlay, matching libfdb_c (no under-conflict; RFC-121).
  • go test ./... is clean from a fresh checkout: the Bazel-runfiles-only suites are build-tagged so a plain go test no longer panics (RFC-129), and the heavy million-row stress benchmarks under pkg/relational/sqldriver/stress now carry a stress build tag, so a plain go test ./... skips them instead of spinning up million/ten-million-row FDB workloads (they still run via Bazel’s manual stress target and the nightly stress workflow).
  • Pure-Go FDB client: three database-level transaction defaults that change read semantics are now honored instead of silently dropped — SetSnapshotRywDisable/Enable (a cumulative counter, matching libfdb_c), SetTransactionBypassUnreadable, and SetTransactionCausalReadRisky. They propagate to each new transaction via applyTxDefaults and are replayed idempotently across retries (RFC-133).

Compatibility

  • Wire format: unchanged for modern stores — records, indexes, versions, continuations, and split records remain byte-identical to Java fdb-record-layer-core 4.12.11.0. Newly closed gap: Go now reads and writes legacy Java store layouts (FormatVersion < 6 record versions in the RecordVersionKey(8) subspace, and omit_unsplit_record_suffix bare-key unsplit records) and performs Java’s on-open format upgrade — previously a silent read gap (see Fixed). A Go client can now safely share a cluster with legacy Java stores in either direction.
  • SQL behaviour: net additions only (memory-budget option; the LIMIT-envelope and pagination fixes correct latent bugs, they don’t change correct-query results).
  • FDB client option semantics: now documented option-by-option in pkg/fdbgo/fdb/OPTIONS.md (honored / UnsupportedOptionError / safe no-op, vs libfdb_c 7.3.77). One behavioural change: three database-level defaults (snapshot_ryw_disable/enable, transaction_bypass_unreadable, transaction_causal_read_risky) that were previously silent no-ops now take effect on each new transaction — a caller that set them and relied on them being ignored will now see them applied (this is the faithful libfdb_c behaviour). The unsafe access/auth/quota family still fails loud with UnsupportedOptionError; no option’s wire behaviour changed (RFC-133).
  • Required versions: Java fdb-record-layer-core 4.12.11.0, FDB C++ client 7.3.77, Go 1.26.x (the MODULE.bazel / go.mod pins; the CI doc-guard enforces docs match them).