Repository navigation
sandbox-store: move the wake path's writes of the sandboxes row into a wake module - #1336
Merged
Merged
Conversation
|
Thanks for opening this pull request! A SPACE maintainer will take a look. CONTRIBUTING.md explains how we review outside contributions. |
ac-pplx
force-pushed
the
ac/lifecycle-move-wake
branch
from
November 2, 2026 21:06
c6098b7 to
1560388
Compare
ac-pplx
force-pushed
the
ac/lifecycle-move-wake
branch
from
November 2, 2026 23:25
1560388 to
1b40b1f
Compare
This was referenced Nov 3, 2026
Merged
Merged
ac-pplx
marked this pull request as ready for review
November 3, 2026 03:51
ac-pplx
marked this pull request as draft
November 3, 2026 03:52
ac-pplx
force-pushed
the
ac/lifecycle-move-wake
branch
from
November 3, 2026 06:00
1b40b1f to
7cfd3c8
Compare
ac-pplx
marked this pull request as ready for review
November 3, 2026 06:29
kumarpallav-pplx
requested review from
kumarpallav-pplx and
nikhilbirmiwal-pplx
November 3, 2026 06:30
nikhilbirmiwal-pplx
approved these changes
Nov 3, 2026
…a wake module Five sandboxes writes that finish bringing a sandbox up were still inline in the api and internal-api crates: the wake-completion CAS, the cancelled-wake redrive's fenced completion, the command-ready clear (written twice, once per access path), the restore-lease renewal while claiming the active Kubernetes execution, and the pod node placement, which cold creates record too. They move into pplx-space-sandbox-store's new wake module, one function per transition, each documented with the kind of fact it writes. The SQL text is unchanged except that the internal-api command-ready clear now issues the substrate copy's whitespace; both callers share one function. Locking reads and transactions stay with the callers. The sql! locators of the moved statements now name the store module. The pooled post-wake update in responses.rs stays: it returns the api's joined Sandbox response row, built from api-owned column and join fragments, which the store cannot own or decode. The sandbox_writes ratchet drops the six files whose only write moved, and lifecycle.rs's file_size cap falls to 1777.
ac-pplx
force-pushed
the
ac/lifecycle-move-wake
branch
from
November 3, 2026 21:23
7cfd3c8 to
e0b4d25
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Moves the wake path's writes of the
sandboxesrow from the api and internal-api crates into a newwakemodule ofpplx-space-sandbox-store. One executor-generic function per transition; each doc comment names the fact it writes. Behaviour is unchanged. Callers keep theirFOR UPDATEreads, transactions and error mapping. The SQL is byte-identical except for one whitespace change, noted below.Moved (
old → sandbox_store::wake::*):sandbox/lifecycle.rscomplete_wake_lifecycleCAS →complete_wake(operation step)sandbox/wake_completion.rsfenced_completion_cas+ itsredrive_loopcall →fenced_completion_cas(private) +complete_redriven_wake(operation step)kubernetes/store/activation_fence.rsK8sStore::clear_command_ready_pending→clear_command_ready_pending(observed projection)data_plane_sessions/service_route.rsclear_sandbox_command_ready_pending→ the sameclear_command_ready_pendingkubernetes/store/execution_rows.rslease renewal inensure_active_execution_claim_for_lifecycle→renew_restore_lease_for_execution_claim(operation step)kubernetes/store/pod_placement.rswrite inpersist_pod_node_placement→record_pod_node_placement(observed projection)The two command-ready clears were one statement indented differently; they now share one function with the substrate copy's text, so the internal-api copy changes only in leading whitespace. The guards are documented on each function:
complete_wakechecks no lease, generation or owner, and no locking read precedes it;record_pod_node_placementhas no lifecycle predicate and relies on the caller's row lock; the lease renewal checks only token and expiry, under the caller's lock.Not moved:
update_and_fetch_post_wake_sandboxinresponses.rs. ItsUPDATE … RETURNING *CTE decodes into the api's joinedSandboxrow, built from api-ownedSANDBOX_COLUMNS/SANDBOX_JOIN_TAIL, which the store can't decode or own;responses.rsstays at 3 in the ratchet.sql!locators change: the moved statements now carrypplx_space_sandbox_store::wake, which is whatpg_stat_activityand query monitoring show.Baseline: removes the
sandbox_writesentries forlifecycle.rs,wake_completion.rs,activation_fence.rs,execution_rows.rs,pod_placement.rsandservice_route.rs; thelifecycle.rsfile_sizecap goes from 1793 to 1775.Validation
cargo nextest run --locked --all-features -p pplx-space-db-test-fixtures -p pplx-space-sandbox-store -p pplx-space-internal-api-server: 465 passed, 0 skipped.… -p pplx-space-db-test-fixtures -p pplx-space-api: 2160 passed, 1 skipped (an#[ignore]benchmark). Postgres tests ran (no opt-out).lifecycle = 'started'fromclear_command_ready_pendingfailsk8s_store_postgres_behaviors; dropping'suspending'fromcomplete_wakefailswake_completion_cas_outcome_for_every_prior_lifecycle.cargo clippy --locked --all-targets --all-features -p <the 3> -- -D warnings: clean.cargo arch --base-baseline <main> --base-architecture <main>: 0 required findings.infra/space/kind/scripts/up.sh, 730 s; later edits change only comments), thenscripts/tests/smoke-kind-typed.sh all(3076 s):ecw.cold_create_environmentandecw.warm_pool_environmentneededSPACE_SMOKE_KIND_COLD_RECEIPTS; with it set, both passed.local.restarted_btrfs_send_is_rejected_and_retriedneeds telemetry modeotel; not run.cargo arch0 required.Severity and risk
Severity: does not apply (refactor). Risk: low: the same statements, locks and transactions. Roll back by reverting the commit.
Rollout
No migration. Mixed-version pods issue the same statements apart from the locator comment and that whitespace. Monitoring keyed on the old locator paths needs the new one.
Open PRs that will need to rebase
UPDATEinpod_placement.rspersist_pod_node_placement→wake::record_pod_node_placement(re-apply its new WHERE term and bind there). It also rewrites the unmovedupdate_and_fetch_post_wake_sandbox, and itssandbox_writesedits are next to the removed lines.persist_pod_node_placementbody into a new function; theUPDATEis nowwake::record_pod_node_placement.ensure_active_execution_claim_for_lifecycle; the lease renewal there is nowwake::renew_restore_lease_for_execution_claim. Textual conflict only.lib.rs; Add idempotent ECW network policy replacement and live status #1297'ssandbox_writeshunk is next to the removed entries.AI assistance: Claude Code (an AI agent) wrote the code, ran the validation and drafted this description.
After the wave-2 restack
This PR is one layer of a 10-PR stack, restacked onto main
c5fdf0c7(which includes #826) and then rebased mechanically onto42a99002, which changed only baseline context lines, in order #1329 → #1336 → #1338 → #1339 → #1342 → #1347 → #1333 → #1335 → #1328 → #1332. The validation earlier in this description ran at pre-restack heads; this layer's head ise0b4d257.lifecycle.rs, so thefile_sizecap this layer lowers is now 1777. For every file [cluster-controller] re-place an evacuated stopped sandbox as stopped on another node, materialized by the shim without a VM #826 and this stack share, each SQL line [cluster-controller] re-place an evacuated stopped sandbox as stopped on another node, materialized by the shim without a VM #826 added was checked to be present verbatim at the top head, in place or in the store module it moved to.cargo fmt --all -- --check,cargo check --workspace --all-targets --all-featuresandcargo arch(0 required findings, with main's layers and table-owner rules), and the ratchet and caps this layer changes are recounted exactly.e90aa284before that rebase; nextest passed 4370 tests again at77fbae1e):cargo clippy --workspace --locked --all-targets --all-features -- -D warningsis clean, andSPACE_CI_REQUIRE_TEST_DEPS=1 cargo nextest run --all-featurespassed 4355 tests across the store, api, internal-api server, cluster-controller server, metrics, db-test-fixtures, common-core, common-svc and portability crates, [cluster-controller] re-place an evacuated stopped sandbox as stopped on another node, materialized by the shim without a VM #826's suites included.scripts/tests/smoke-kind-typed.sh allgave ECW 91/91 and native 42/42, including [cluster-controller] re-place an evacuated stopped sandbox as stopped on another node, materialized by the shim without a VM #826'snative.forced_drain_re_places_stopped_sandboxand its re-drain and restarted variants. The Direct substrate lane'sallgave ECW 51/51 and native 27/27. No flakes and no reruns.+/-lines and its SQL string literals match its reviewed head (range-diff plus a literal multiset compare).