Skip to main content
← Back to list
01Issue
FeatureOpenExtensionsPublic
AssigneesNone

Relationships

#3395 Datastore rework Phase 4 G: S3 and GCS implement the writable datastore-wide control plane and keep _control/writer/ at the bucket root

Opened by stack72 · 10/13/2026

Background

swamp-club#3364 (datastore rework Phase 4 E) gives core a writable datastore-wide control plane so the v3 fenced writer lease (swamp-club#3359) can live at _control/writer/ at the datastore root, outside every namespace. Core side: datastoreControlPlaneStore() may now return a WritableDatastoreControlPlaneStore (get, put, create-only putIfAbsent, delete, list, all at the root _control/, binding no namespace), and @swamp-club/swamp-testing ships assertWritableDatastoreControlPlaneStoreConformance. Core's datastoreWriterLeaseStore refuses a provider without a writable one.

This is Phase 4 G: the S3 and GCS extensions' side (swamp-extensions has GitHub issues disabled, so it is tracked here). Tracking: swamp-club#2865.

What is needed (S3 and GCS)

  1. Implement datastoreControlPlaneStore() on both providers, returning a writable store keyed at <prefix>/_control/<key>. Neither extension implements even the read-only hook today. Cheap to build: no sync service, no namespace binding, no request until a call, one request per call, no HeadBucket preflight. get returns null only for a missing record and rejects on any other failure (access denied included) and when its signal aborts. putIfAbsent uses the conditional put the sync service's control plane already uses (S3 If-None-Match, GCS ifGenerationMatch=0).
  2. Skip _control/writer/ in migrateRootControlPlaneToNamespace (S3 s3_cache_sync.ts, GCS gcs_cache_sync.ts). Today a namespaced push into a namespace that has the legacy index <namespace>/.datastore-index.json (one a solo datastore was upgraded to) copies every root _control/* record into <namespace>/_control/ and deletes the original. It runs on push only; a namespace with only the current _index/ layout triggers nothing. Checked on ministack with @swamp/s3-datastore 2026.10.13.1: with the legacy index planted, a root writer/ record moved on the first namespaced push; a copy that skips _control/writer/ passes. A fence key moved under a live writer looks like a lost lease or lets a second writer take a fence already in use. Consider skipping _control/datastore-format too (today the marker writer avoids it by leaving no legacy namespaced index behind).
  3. Run assertWritableDatastoreControlPlaneStoreConformance against ministack and fake-gcs-server, passing openNamespacedSyncFixture and markNamespaceUpgradedFromSolo (write an empty legacy v1 index, {"version":1,"lastPulled":...,"entries":{}}, at <prefix>/<namespace>/.datastore-index.json; a bare {} makes the push throw), against an empty bucket or prefix (the case skips when the root already holds records, since the move takes all of them) so the namespaced-push case runs; without both it is skipped. It checks a writer/ record stays at the root after a namespaced push into the upgraded namespace. Red-check it against the current migration.

Acceptance

  • On S3 and GCS, the lease's records live at _control/writer/ at the datastore root, whatever namespace a checkout uses.
  • A namespaced pull or push never moves or copies them.
  • Both extensions pass the writable datastore-wide conformance suite, namespaced-push case included.
  • The Phase 4 bucket v3 opt-in must require an extension version that has this change, so v3 is never enabled on a bucket against an older extension that would move the lease.
02Bog Flow
◉OPEN○TRIAGED○IN PROGRESS○SHIPPED

Open

10/13/2026, 8:37:51 PM

No activity in this phase yet.

03Sludge Pulse
Editable. Press Enter to edit.

system commented 10/13/2026, 8:37:52 PM

Classified automatically when this issue was filed.

  • Source: Extensions

If you feel this classification is incorrect, add a ripple to tell us so.

stack72 commented 10/13/2026, 11:04:45 PM

Core now refuses the v3 writer lease unless the provider declares datastoreWideLease: true (swamp-club#3414, swamp-club/swamp#3088). Ship that declaration on the S3 and GCS providers in the same release as the _control/writer/ skip in migrateRootControlPlaneToNamespace. In that release's assertWritableDatastoreControlPlaneStoreConformance test, also assert result.namespacedPushSkipped === undefined, so the namespaced-push case is known to have run.

Sign in to post a ripple.