Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
249 commits
Select commit Hold shift + click to select a range
38329e8
feat(onboard): add managed startup profile schema
ericksoa Jul 30, 2026
7f3859a
docs(onboard): clarify startup profile transport encoding
ericksoa Jul 30, 2026
32561a9
fix(onboard): harden managed startup profile
ericksoa Jul 30, 2026
087a9a5
chore(stack): sync PR3.2 with current main
ericksoa Jul 30, 2026
e1845dd
fix(onboard): close startup profile contract gaps
ericksoa Jul 30, 2026
244e3e6
chore(stack): sync PR3.2 with current main
ericksoa Jul 30, 2026
2403316
chore(stack): sync PR3.2 with current main
ericksoa Jul 30, 2026
ea5bd8a
chore(stack): sync PR3.2 with current main
ericksoa Jul 31, 2026
357081a
feat(onboard): construct managed startup profiles
ericksoa Jul 31, 2026
25d32e0
feat(onboard): map and coordinate startup profiles
ericksoa Jul 31, 2026
094d177
feat(onboard): apply startup profiles in managed images
ericksoa Jul 31, 2026
06f67e5
feat(onboard): add managed shared-state transactions
ericksoa Jul 31, 2026
2a048ae
chore(stack): restack PR3.3 on merged PR3.2
ericksoa Jul 31, 2026
498e521
chore(stack): restack PR3.4a on PR3.3
ericksoa Jul 31, 2026
3206926
chore(stack): restack PR3.4b on PR3.4a
ericksoa Jul 31, 2026
f3081cc
chore(stack): restack PR3.5 on PR3.4b
ericksoa Jul 31, 2026
6da5eb2
test(onboard): keep managed startup tests branchless
ericksoa Jul 31, 2026
51126c4
chore(stack): carry PR3.4b guardrail fix into PR3.5
ericksoa Jul 31, 2026
bb7a260
chore(stack): restack PR3.4a after PR3.3 merge
ericksoa Jul 31, 2026
fafdbd1
chore(stack): restack PR3.4b after PR3.3 merge
ericksoa Jul 31, 2026
0edd158
chore(stack): restack PR3.5 after PR3.3 merge
ericksoa Jul 31, 2026
b14013f
test(onboard): cover managed startup fixture CLI
ericksoa Jul 31, 2026
46fbe19
feat(onboard): apply startup profiles in managed images
ericksoa Jul 31, 2026
b2027a9
feat(onboard): add managed shared-state transactions
ericksoa Jul 31, 2026
c95bdf7
fix(onboard): serialize managed startup transactions
ericksoa Jul 31, 2026
3f3bdbb
feat(onboard): apply startup profiles in managed images
ericksoa Jul 31, 2026
8ff8094
feat(onboard): add managed shared-state transactions
ericksoa Jul 31, 2026
7d1668b
test(onboard): keep transaction races branchless
ericksoa Jul 31, 2026
540494c
chore(stack): inherit PR3.4a guardrail fix
ericksoa Jul 31, 2026
1463687
chore(stack): inherit PR3.4b restack
ericksoa Jul 31, 2026
3a03eeb
merge: resolve conflicts with main
github-actions[bot] Jul 31, 2026
d97b259
chore(stack): restack PR3.5 after PR3.4a merge
ericksoa Jul 31, 2026
deb1581
chore(stack): refresh PR3.4b validation
ericksoa Jul 31, 2026
0ad91a5
chore(stack): inherit PR3.4b validation refresh
ericksoa Jul 31, 2026
a0f12f1
fix(onboard): harden managed startup inputs
ericksoa Jul 31, 2026
27c72f5
fix(runtime): close prior review debt
ericksoa Jul 31, 2026
1c824cc
test(runtime): keep env cleanup branchless
ericksoa Jul 31, 2026
5c6b3f7
fix(runtime): preserve direct image execution
ericksoa Jul 31, 2026
611fdb6
fix(messaging): reject ambiguous channel identities
ericksoa Jul 31, 2026
76c54d4
fix(messaging): require canonical persisted channel ids
ericksoa Jul 31, 2026
e41521b
chore(stack): refresh PR3.4b on current main
ericksoa Jul 31, 2026
bebfc6c
chore(stack): refresh PR3.5 on current PR3.4b
ericksoa Jul 31, 2026
864e249
chore(stack): refresh PR3.5a on current PR3.5
ericksoa Jul 31, 2026
7cf2a8d
chore(stack): refresh PR3.5b on current PR3.5a
ericksoa Jul 31, 2026
5f9d97d
test(e2e): add cross-runtime foundation
ericksoa Jul 31, 2026
abf45b3
test(e2e): keep runtime foundation branchless
ericksoa Jul 31, 2026
ed479ae
refactor(runtime): unify provider bundle registry
ericksoa Jul 31, 2026
005b3a7
fix(runtime): harden provider contract boundaries
ericksoa Jul 31, 2026
05cf2a5
fix(runtime): fail closed on managed image cleanup
ericksoa Jul 31, 2026
5c29046
fix(messaging): reject unresolved build hooks
ericksoa Jul 31, 2026
534773b
fix(runtime): close provider lifecycle authority gaps
ericksoa Jul 31, 2026
847e827
chore(stack): refresh PR3.5c on current PR3.5b
ericksoa Jul 31, 2026
77559f7
test(runtime): keep provider parity branchless
ericksoa Jul 31, 2026
a2afe77
fix(e2e): harden runtime foundation contracts
ericksoa Jul 31, 2026
13932b9
chore(stack): refresh PR3.4b on current main
ericksoa Jul 31, 2026
5111410
chore(stack): refresh PR3.5 on current PR3.4b
ericksoa Jul 31, 2026
7d51947
chore(stack): refresh PR3.5a on current PR3.5
ericksoa Jul 31, 2026
004b060
test(e2e): verify fixture profiles stay unregistered
ericksoa Jul 31, 2026
771f48c
chore(stack): refresh PR3.5b on current PR3.5a
ericksoa Jul 31, 2026
c67afd3
chore(stack): refresh PR3.5c on current PR3.5b
ericksoa Jul 31, 2026
4788d28
test(e2e): expose runtime profile registration state
ericksoa Jul 31, 2026
64f562f
fix(runtime): preserve unproven cleanup authority
ericksoa Jul 31, 2026
15eef1b
chore(stack): refresh PR3.6 on repaired base
ericksoa Jul 31, 2026
d73f13a
test(runtime): cover unknown provider doctor result
ericksoa Jul 31, 2026
8f8bcd5
test(runtime): prove provider recovery boundaries
ericksoa Jul 31, 2026
f77bff8
fix(runtime): fail closed on retained cleanup ownership
ericksoa Jul 31, 2026
bf2fd19
test(rebuild): type cleanup ownership receipt
ericksoa Jul 31, 2026
4316a18
fix(runtime): prove cleanup authority before deletion
ericksoa Jul 31, 2026
062d66b
test(snapshot): mock destructive cleanup authority
ericksoa Jul 31, 2026
75730cf
test(runtime): prove cleanup planning is inert
ericksoa Jul 31, 2026
0b21b79
feat(rebuild): add atomic managed workload replacement
ericksoa Jul 31, 2026
438f79f
fix(rebuild): fail closed across authority cutover
ericksoa Jul 31, 2026
412d69d
docs(rebuild): define deferred recovery ownership
ericksoa Jul 31, 2026
cfe84cd
fix(rebuild): bind retained workload authority
ericksoa Jul 31, 2026
827f545
test(rebuild): keep failure matrices linear
ericksoa Jul 31, 2026
add3965
test(rebuild): cover invalid provider artifacts
ericksoa Jul 31, 2026
9bbf75d
fix(rebuild): address review feedback
ericksoa Jul 31, 2026
8212bf9
merge: resolve conflicts with main
github-actions[bot] Aug 1, 2026
4960f4d
chore(stack): refresh managed rebuild on current main
ericksoa Aug 1, 2026
bf94633
feat(snapshot): preserve managed runtime authority
ericksoa Jul 31, 2026
3a4321d
fix(snapshot): enforce managed authority boundaries
ericksoa Jul 31, 2026
8b19581
feat(snapshot): prepare immutable managed clone handoff
ericksoa Aug 1, 2026
1a91ef2
test(snapshot): keep provider authority cases linear
ericksoa Aug 1, 2026
410d4c9
chore(stack): refresh clone contract on PR3.8
ericksoa Aug 1, 2026
fabad32
test(snapshot): keep clone authority cases linear
ericksoa Aug 1, 2026
25aa304
feat(snapshot): add managed clone provider transaction
ericksoa Aug 1, 2026
6d4d858
test(snapshot): satisfy provider transaction CLI typings
ericksoa Aug 1, 2026
94cb164
chore(stack): refresh provider transaction on PR3.9A
ericksoa Aug 1, 2026
cbecf7b
feat(snapshot): stage Hermes clone broker activation
ericksoa Jul 31, 2026
888e2f9
test(snapshot): satisfy Hermes broker CLI typings
ericksoa Jul 31, 2026
c176a4f
fix(snapshot): use shared immutable boundary
ericksoa Aug 1, 2026
8bc9ea1
feat(onboard): define dormant transactional managed bootstrap
ericksoa Aug 1, 2026
69bcdc4
feat(onboard): add transactional Docker bootstrap adapter
ericksoa Jul 31, 2026
22c198a
test(onboard): satisfy strict Docker bootstrap fixture typing
ericksoa Jul 31, 2026
ff836ad
test(snapshot): complete dependency adapter mocks
ericksoa Jul 31, 2026
88ff07b
fix(snapshot): keep clone transaction dormant
ericksoa Aug 1, 2026
5429f52
chore(stack): refresh Hermes clone broker on PR3.9B
ericksoa Aug 1, 2026
101e408
test(snapshot): satisfy Hermes broker growth guard
ericksoa Aug 1, 2026
0c4440c
chore(stack): refresh bootstrap protocol on PR3.9C
ericksoa Aug 1, 2026
f251a72
test(onboard): satisfy bootstrap protocol growth guard
ericksoa Aug 1, 2026
b7561d1
feat(onboard): persist managed bootstrap transactions
ericksoa Aug 1, 2026
17843c3
chore(stack): refresh Docker bootstrap adapter on protocol
ericksoa Aug 1, 2026
01a554d
test(onboard): linearize Docker bootstrap fixtures
ericksoa Aug 1, 2026
a5de860
feat(onboard): bind managed create to runtime providers
ericksoa Aug 1, 2026
844bfb6
fix(snapshot): pin files during authority hashing
ericksoa Aug 1, 2026
aeddd24
chore(stack): refresh clone handoff on snapshot security fix
ericksoa Aug 1, 2026
f7068d0
chore(stack): refresh provider transaction on clone handoff
ericksoa Aug 1, 2026
122f8c3
merge: refresh managed create on Docker bootstrap
ericksoa Aug 1, 2026
0711807
chore(stack): refresh Hermes broker on provider transaction
ericksoa Aug 1, 2026
a396904
chore(stack): refresh bootstrap protocol on Hermes broker
ericksoa Aug 1, 2026
8faa1b4
chore(stack): refresh Docker adapter on bootstrap protocol
ericksoa Aug 1, 2026
4e68970
merge: refresh managed create on Docker bootstrap security fix
ericksoa Aug 1, 2026
3c47ca5
feat(onboard): persist shared-state commit receipts
ericksoa Aug 1, 2026
3e0645f
chore(stack): append runtime lifecycle parent
ericksoa Aug 1, 2026
ed60882
fix(snapshot): address restore review findings
ericksoa Aug 1, 2026
ed34be3
refactor(onboard): extract managed GPU finalization
ericksoa Aug 1, 2026
7c823d4
fix(snapshot): address clone handoff review findings
ericksoa Aug 1, 2026
361b455
test(runtime): advance managed bootstrap boundary
ericksoa Aug 1, 2026
e962454
merge: update PR3.8 review fixes
ericksoa Aug 1, 2026
c2e6f06
fix(snapshot): address provider transaction review
ericksoa Aug 1, 2026
9e64898
docs(snapshot): clarify legacy restore retention
ericksoa Aug 1, 2026
738e680
merge: refresh PR3.8 documentation
ericksoa Aug 1, 2026
d7d4adc
merge: refresh clone handoff contract
ericksoa Aug 1, 2026
e2e556b
chore(stack): append provider lifecycle guardrails
ericksoa Aug 1, 2026
380925a
fix(hermes): address broker transaction review
ericksoa Aug 1, 2026
ffacfb3
merge: refresh Hermes broker on provider transaction
ericksoa Aug 1, 2026
c3f9fdc
fix(onboard): harden bootstrap dormancy contract
ericksoa Aug 1, 2026
d69a390
merge: refresh bootstrap protocol on Hermes broker
ericksoa Aug 1, 2026
e587010
test(onboard): update managed cutover fixtures
ericksoa Aug 1, 2026
d416d08
chore(stack): append provider lifecycle CI fixes
ericksoa Aug 1, 2026
1fb671d
fix(bootstrap): harden Docker transaction review contracts
ericksoa Aug 1, 2026
93fe6d8
merge: refresh Docker bootstrap adapter on protocol hardening
ericksoa Aug 1, 2026
333b673
fix(onboard): reconcile managed bootstrap after restart
ericksoa Aug 1, 2026
0cf5aac
test(onboard): inventory Docker bootstrap sources
ericksoa Aug 1, 2026
b79f034
test(cli): exclude source fixtures from distribution
ericksoa Aug 1, 2026
2984099
fix(onboard): make terminal recovery restart-safe
ericksoa Aug 1, 2026
0aabe5e
merge: refresh managed create on Docker adapter
ericksoa Aug 1, 2026
310ebeb
test(onboard): fence create on restart recovery
ericksoa Aug 1, 2026
b3b96bc
merge: refresh durable transactions on managed create
ericksoa Aug 1, 2026
0013772
test(messaging): keep staged channel fixture canonical
ericksoa Aug 1, 2026
4e9c72f
chore(stack): append durable transaction restack
ericksoa Aug 1, 2026
61aa6d6
merge(stack): refresh clone handoff fixture
ericksoa Aug 1, 2026
4bb2b58
merge(stack): refresh managed clone provider
ericksoa Aug 1, 2026
b596445
merge(stack): refresh Hermes clone broker
ericksoa Aug 1, 2026
e11da6b
merge(stack): refresh bootstrap protocol
ericksoa Aug 1, 2026
889579b
merge(stack): refresh Docker bootstrap adapter
ericksoa Aug 1, 2026
1c32a4d
merge(stack): refresh managed bootstrap create
ericksoa Aug 1, 2026
16f78b4
merge(stack): refresh durable bootstrap transactions
ericksoa Aug 1, 2026
e97ecce
merge(stack): refresh managed workload rebuild parity
ericksoa Aug 1, 2026
6b2c464
merge(stack): refresh managed snapshot parity
ericksoa Aug 1, 2026
91c807c
merge(stack): refresh managed clone handoff contract
ericksoa Aug 1, 2026
8ca5867
merge(stack): refresh managed clone provider transaction
ericksoa Aug 1, 2026
2faa95d
merge(stack): refresh Hermes managed clone broker
ericksoa Aug 1, 2026
fc9ff91
merge(stack): refresh managed bootstrap protocol
ericksoa Aug 1, 2026
0d3442e
merge(stack): refresh Docker managed bootstrap adapter
ericksoa Aug 1, 2026
cd65972
merge(stack): refresh managed bootstrap provider create
ericksoa Aug 1, 2026
f72b165
merge(stack): refresh durable bootstrap transactions
ericksoa Aug 1, 2026
0be111d
merge(stack): refresh managed bootstrap recovery
ericksoa Aug 1, 2026
362a70c
chore(stack): refresh managed workload rebuild parity on current main
ericksoa Aug 1, 2026
b2374ee
chore(stack): refresh managed snapshot parity parent
ericksoa Aug 1, 2026
e09ce8a
chore(stack): refresh managed clone handoff parent
ericksoa Aug 1, 2026
aeeb6dd
chore(stack): refresh managed clone provider parent
ericksoa Aug 1, 2026
968c795
chore(stack): refresh Hermes clone broker parent
ericksoa Aug 1, 2026
fb0d7aa
chore(stack): refresh managed bootstrap protocol parent
ericksoa Aug 1, 2026
976771e
chore(stack): refresh Docker bootstrap adapter parent
ericksoa Aug 1, 2026
ff5b16b
chore(stack): refresh managed bootstrap create parent
ericksoa Aug 1, 2026
998296e
chore(stack): refresh durable bootstrap transaction parent
ericksoa Aug 1, 2026
3be9d84
chore(stack): refresh managed bootstrap recovery parent
ericksoa Aug 1, 2026
ca85ca7
fix(hermes): preserve broker write ownership
ericksoa Aug 1, 2026
8db756d
chore(stack): incorporate Hermes broker review repairs
ericksoa Aug 1, 2026
3e25313
chore(stack): incorporate Hermes broker review repairs
ericksoa Aug 1, 2026
08060dd
chore(stack): incorporate Hermes broker review repairs
ericksoa Aug 1, 2026
bcf2ae9
chore(stack): incorporate Hermes broker review repairs
ericksoa Aug 1, 2026
f2a5806
test(onboard): linearize transaction recovery cases
ericksoa Aug 1, 2026
743a2f3
chore(stack): incorporate transaction test repairs
ericksoa Aug 1, 2026
5aaf988
chore(stack): refresh E2E qualification
ericksoa Aug 1, 2026
5472c30
chore(stack): incorporate prior-slice qualification refresh
ericksoa Aug 1, 2026
b349b98
merge: resolve conflicts with main
github-actions[bot] Aug 1, 2026
33d1756
merge(stack): restack #8031 onto current main
ericksoa Aug 2, 2026
65f4d68
merge(stack): restack #8032 onto #8031
ericksoa Aug 2, 2026
380d885
merge(stack): restack #8034 onto #8032
ericksoa Aug 2, 2026
6c7f81d
merge(stack): restack #8035 onto #8034
ericksoa Aug 2, 2026
7097017
test(hermes): assert clone cleanup writes no state
ericksoa Aug 2, 2026
c1fd385
chore(stack): refresh Hermes review fix on current parent
ericksoa Aug 2, 2026
c5db5df
merge(stack): restack #8036 onto repaired #8035
ericksoa Aug 2, 2026
9a7fc82
merge(stack): restack #8037 onto #8036
ericksoa Aug 2, 2026
982be3a
merge(stack): restack #8040 onto #8037
ericksoa Aug 2, 2026
b3e6ca6
merge(stack): restack #8041 onto #8040
ericksoa Aug 2, 2026
d91ee2c
merge(stack): restack #8043 onto #8041
ericksoa Aug 2, 2026
8628b8a
fix(hermes): harden broker control recovery
ericksoa Aug 2, 2026
bd43818
merge(stack): restack #8036 onto repaired #8035
ericksoa Aug 2, 2026
f4a28b9
merge(stack): restack #8037 onto #8036
ericksoa Aug 2, 2026
76e3a0f
merge(stack): restack #8040 onto #8037
ericksoa Aug 2, 2026
333d1c2
merge(stack): restack #8041 onto #8040
ericksoa Aug 2, 2026
502a52e
merge(stack): restack #8043 onto #8041
ericksoa Aug 2, 2026
d7cb7f7
test(hermes): rely on owned child cleanup
ericksoa Aug 2, 2026
53b3404
merge(stack): restack #8036 onto #8035
ericksoa Aug 2, 2026
db8e1cd
merge(stack): restack #8037 onto #8036
ericksoa Aug 2, 2026
1edfdc2
merge(stack): restack #8040 onto #8037
ericksoa Aug 2, 2026
00310bf
merge(stack): restack #8041 onto #8040
ericksoa Aug 2, 2026
bd57ed7
merge(stack): restack #8043 onto #8041
ericksoa Aug 2, 2026
a41d7e3
merge: resolve conflicts with main
github-actions[bot] Aug 2, 2026
4699ab7
merge(stack): append final #8032 ancestry
ericksoa Aug 2, 2026
4824fce
merge(stack): append final #8034 ancestry
ericksoa Aug 2, 2026
82a4877
merge(stack): append final #8035 ancestry
ericksoa Aug 2, 2026
ad5397a
merge(stack): append final #8036 ancestry
ericksoa Aug 2, 2026
8c12001
merge(stack): append final #8037 ancestry
ericksoa Aug 2, 2026
ad6680e
merge(stack): append final #8040 ancestry
ericksoa Aug 2, 2026
4acf574
merge(stack): append final #8041 ancestry
ericksoa Aug 2, 2026
c05a422
feat(onboard): add Docker bootstrap transaction primitives
ericksoa Aug 3, 2026
345efce
refactor(stack): extract Docker bootstrap primitives
ericksoa Aug 3, 2026
a252bae
feat(onboard): add transactional Docker bootstrap adapter
ericksoa Aug 3, 2026
4be7221
fix(onboard): validate managed bootstrap clone inputs
ericksoa Aug 3, 2026
e42b09e
fix(onboard): freeze canonical Docker launch specs
ericksoa Aug 3, 2026
1275cf3
feat(onboard): add Docker bootstrap transaction primitives
ericksoa Aug 3, 2026
149b3a2
fix(onboard): freeze canonical Docker launch specs
ericksoa Aug 3, 2026
a352b71
refactor(stack): restack Docker bootstrap primitives
ericksoa Aug 3, 2026
500656e
feat(onboard): add transactional Docker bootstrap adapter
ericksoa Aug 3, 2026
88adfe1
fix(onboard): validate managed bootstrap clone inputs
ericksoa Aug 3, 2026
28dcd55
refactor(stack): restack transactional Docker bootstrap
ericksoa Aug 3, 2026
2c64343
refactor(stack): restack transactional Docker bootstrap
ericksoa Aug 3, 2026
51b75ae
feat(onboard): bind managed create to runtime providers
ericksoa Aug 3, 2026
df41b1c
refactor(stack): restack managed create provider integration
ericksoa Aug 3, 2026
7bcc852
fix(onboard): address Docker bootstrap review feedback
ericksoa Aug 3, 2026
c874abc
test(onboard): harden Docker bootstrap assertions
ericksoa Aug 3, 2026
d3f532e
test(onboard): scope bootstrap fixture switch state
ericksoa Aug 3, 2026
633e0dc
test(onboard): guard Docker agent argument lookup
ericksoa Aug 3, 2026
908c2dc
feat(onboard): add Docker managed bootstrap lifecycle
ericksoa Aug 3, 2026
503fdd8
refactor(stack): restack Docker bootstrap on current main
ericksoa Aug 3, 2026
2062283
test(onboard): linearize helper environment assertions
ericksoa Aug 3, 2026
52e7144
feat(onboard): bind managed create to runtime providers
ericksoa Aug 3, 2026
c14be06
refactor(stack): restack provider create on corrected bootstrap
ericksoa Aug 3, 2026
7ed953c
feat(onboard): bind managed create to runtime providers
ericksoa Aug 3, 2026
4852666
refactor(stack): restack provider create on merged bootstrap
ericksoa Aug 3, 2026
34b4376
test(docs): cover local NIM post-ready wording
ericksoa Aug 3, 2026
1c4933c
feat(onboard): persist managed bootstrap finalization
ericksoa Aug 3, 2026
ec88369
merge(stack): restack durable bootstrap finalization
ericksoa Aug 3, 2026
bab428d
refactor(onboard): defer bootstrap recovery enumeration
ericksoa Aug 3, 2026
a3571b2
docs(onboard): bind recovery enumeration to its consumer
ericksoa Aug 3, 2026
79fd307
feat(onboard): persist managed bootstrap finalization
ericksoa Aug 3, 2026
3aa4ba6
merge(stack): restack durable bootstrap on merged create
ericksoa Aug 3, 2026
942ce85
feat(onboard): recover durable bootstrap transactions
ericksoa Aug 3, 2026
a943d26
merge(stack): restack recovery on durable transactions
ericksoa Aug 3, 2026
f1b50a4
feat(onboard): recover durable bootstrap transactions
ericksoa Aug 3, 2026
f3d3989
merge(stack): restack recovery on merged durable transactions
ericksoa Aug 3, 2026
2d1c542
fix(onboard): close durable recovery feedback
ericksoa Aug 3, 2026
fd260f2
fix(onboard): close remaining recovery review notes
ericksoa Aug 3, 2026
456fd86
fix(onboard): scope legacy bootstrap recovery
ericksoa Aug 3, 2026
aca6e3d
test(onboard): harden recovery evidence
ericksoa Aug 3, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
79 changes: 66 additions & 13 deletions src/lib/onboard/managed-bootstrap/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -91,20 +91,73 @@ sandbox identities, plan and profile
fingerprints, exact original and replacement IDs, rollback target, and phase.
Exact commit and cleanup receipts are durable terminal records, so adapter
recreation does not depend on process-local transaction sets or tombstone maps.
Rollback retains an `owner-cleanup-required` phase only after image-owned shared
state is restored and the exact replacement is absent. That phase keeps the
restored original quiescent and preserves the journal without a terminal
receipt until the owning sandbox service removes the exact runtime and the
provider proves its absence. Unknown runtime presence is a retryable durable
cleanup failure, never evidence of absence.
The image-owned shared-state transaction uses the same identity-bound model: a
commit atomically moves its pending manifest and backups into a durable receipt
namespace, compacts that state to an exact commit receipt, and rejects rollback
when a later image-runtime invocation reads that receipt. The provider may
retire that receipt only after it proves the external rollback backup is gone,
so that this receipt does not block the next bootstrap attempt.
Direct identity lookup reconstructs one known transaction record. The bounded
[3.12b recovery slice](https://github.com/NVIDIA/NemoClaw/issues/7744) introduces
unfinished-record enumeration together with phase reconciliation and
cross-surface resume or rollback. The adapter reads mutable OpenShell names only
to detect ownership reuse. Unsafe name-only deletion returns a typed retention
error. The dormant adapter assumes the protocol's single coordinator;
multi-process lease/arbitration remains an explicit production-activation gate.
Activation must also inject the selected gateway's canonical state root.
after a restart. The provider may retire that receipt only after it proves the
external rollback backup is gone, leaving the next bootstrap attempt unblocked.
Direct identity lookup reconstructs one known transaction record, while managed
create-lifecycle startup uses unfinished-record enumeration to ask the selected
provider to reconcile every identity-addressed record before a new sandbox
create begins. The Docker provider then resumes the durable phase monotonically:
staged work rolls back without entering cutover; cutover work follows a proven
image-owned commit forward or durably authorizes rollback; rollback-authorized
work completes exact restore and cleanup; and shared-state-committed work
completes exact backup cleanup and commit. Recovery persists an identity-bound
finalization receipt before removing the active journal, is idempotent across
another interruption, and enumerates durable identities before loading each
record so one unreadable transaction does not hide other results. The provider
returns bounded `{ receipts, failures }` evidence; the coordinator validates,
copies, freezes, and orders both arrays without routing on provider phases or
failure codes. A failure for the requested sandbox name, or one whose sandbox
identity cannot be proven, blocks create. An exact failure for another sandbox
is warned and retained without blocking the requested create. The code reads
mutable OpenShell names only to detect ownership reuse, and unsafe name-only
deletion returns a typed retention error. Docker mutations use the previously
journaled full container ID, whose identity cannot be rebound, then re-inspect
that same ID after quiescence. Multi-process lease/arbitration remains an
explicit production-activation gate. Activation must also inject the selected
gateway's canonical state root.

## Legacy journal drain (schema 1 and 2)

Schema 1 and schema 2 journal bodies predate durable agent identity. They cannot
be upgraded by guessing from a mutable sandbox name, image repository, or the
agent selected by a later command. Recovery therefore preserves the canonical
record and any decision sidecar, reports its exact bootstrap, provider, sandbox,
original-runtime, and replacement-runtime identities, and fences only that
sandbox name. A create for another sandbox may continue after warning about the
retained record.

When recovery reports one of these records:

1. Stop onboarding the named sandbox. Save the complete diagnostic and back up
the canonical state root's
`managed-bootstrap/<bootstrap-identity>.json` file and any adjacent decision
sidecar without editing either record.
2. Inspect the reported full runtime IDs through the owning provider. Treat
sandbox and container names as diagnostic text only. Never delete, rename,
or adopt a runtime by name, and never copy agent identity from the current
invocation into the old record.
3. If either exact runtime is present, or its presence cannot be proven, leave
the journal in place and recover the provider-owned transaction using those
immutable IDs. A legacy cutover decision may be newer than the journal-body
phase, so the body alone never authorizes commit or rollback.
4. If both exact runtimes are proven absent, still preserve the journal and its
image-owned shared-state evidence. Record the exact absence proof on
[epic #7744](https://github.com/NVIDIA/NemoClaw/issues/7744) for the
identity-checked retirement path. Until that path ships, use a different
sandbox name rather than deleting durable authority.

Production activation must include the identity-checked retirement path and
protected recovery qualification. This candidate remains inert, so it does not
expose a runtime that could create these legacy records without that support.

## Architectural disposition

Expand All @@ -113,8 +166,8 @@ candidate Docker surface owns create routing, replacement construction,
native-to-compatibility fallback evidence, and deferred commit or rollback.
Central onboarding accepts that provider-neutral surface without a Docker or
Podman selection branch. Tests register an MXC-style surface through the same
bundle and render held launches for OpenClaw, Hermes, and LangChain Deep Agents
Code.
bundle, render held launches for OpenClaw, Hermes, and LangChain Deep Agents
Code, and exercise recovery phases across all three agents.

The coordinator remains the driver-neutral transaction authority: its receipt
shapes, normalization, state transitions, and rollback proofs form one cohesive
Expand Down
182 changes: 182 additions & 0 deletions src/lib/onboard/managed-bootstrap/adapter.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import {
import { createManagedStartupRootApplyRequest } from "../managed-startup/root-apply";
import {
activateManagedBootstrapSequence,
enforceManagedBootstrapRecoveryForSandbox,
finalizeManagedBootstrapSequence,
MANAGED_BOOTSTRAP_SCHEMA_VERSION,
type ManagedBootstrapAdapter,
Expand All @@ -23,8 +24,10 @@ import {
type ManagedBootstrapHeldWorkloadHandle,
type ManagedBootstrapObservedSnapshot,
type ManagedBootstrapPreparedReplacementHandle,
ManagedBootstrapRecoveryBlockedError,
type ManagedBootstrapReplacementHandle,
prepareManagedBootstrapSequence,
recoverManagedBootstrapTransactions,
renderManagedBootstrapHeldCommand,
} from "./adapter";

Expand Down Expand Up @@ -227,6 +230,7 @@ function adapterFor(agent: ManagedStartupAgent): Fixture {
const order: string[] = [];
const raw: Fixture["raw"] = { handle: null, snapshot: null, prepared: null };
const adapter: ManagedBootstrapAdapter = {
recoverUnfinishedTransactions: vi.fn(async () => ({ receipts: [], failures: [] })),
createHeldWorkload: vi.fn(async (input) => {
order.push("create");
const receipt = await input.launch({
Expand Down Expand Up @@ -908,6 +912,184 @@ describe("managed bootstrap adapter contract", () => {
expect(fixture.adapter.finalizeBootstrap).not.toHaveBeenCalled();
});

it("normalizes, freezes, and orders provider-owned restart recovery receipts", async () => {
const fixture = adapterFor("openclaw");
const receipt = cleanupReceipt();
const candidate = (bootstrapIdentity: string) => ({
schemaVersion: MANAGED_BOOTSTRAP_SCHEMA_VERSION,
providerId: receipt.sandbox.driverId,
sourcePhase: "cutover",
sandbox: receipt.sandbox,
bootstrapIdentity,
outcome: "rolled-back" as const,
finalization: { ...receipt, bootstrapIdentity },
});
vi.mocked(fixture.adapter.recoverUnfinishedTransactions).mockResolvedValueOnce({
receipts: [candidate("b".repeat(64)), candidate("a".repeat(64))],
failures: [],
});

const recovered = await recoverManagedBootstrapTransactions(fixture.adapter);

expect(recovered.receipts.map(({ bootstrapIdentity }) => bootstrapIdentity)).toEqual([
"a".repeat(64),
"b".repeat(64),
]);
expect(Object.isFrozen(recovered)).toBe(true);
expect(Object.isFrozen(recovered.receipts)).toBe(true);
expect(recovered.receipts.every((entry) => Object.isFrozen(entry.finalization))).toBe(true);
});

it("rejects recovery evidence whose provider does not own the durable sandbox", async () => {
const fixture = adapterFor("openclaw");
const receipt = cleanupReceipt();
vi.mocked(fixture.adapter.recoverUnfinishedTransactions).mockResolvedValueOnce({
receipts: [
{
schemaVersion: MANAGED_BOOTSTRAP_SCHEMA_VERSION,
providerId: "mxc",
sourcePhase: "cutover",
sandbox: receipt.sandbox,
bootstrapIdentity: IDENTITY,
outcome: "rolled-back",
finalization: receipt,
},
],
failures: [],
});

await expect(recoverManagedBootstrapTransactions(fixture.adapter)).rejects.toThrow(
"recovery provider does not own",
);
});

it("normalizes provider-neutral failures and preserves bounded MXC-style diagnostics", async () => {
const fixture = adapterFor("hermes");
const failure = (bootstrapIdentity: string, sandboxName: string | null) => ({
schemaVersion: MANAGED_BOOTSTRAP_SCHEMA_VERSION,
providerId: "mxc",
sourcePhase: "provider-owned-cleanup",
sandbox:
sandboxName === null
? null
: { sandboxName, sandboxId: `mxc-${sandboxName}`, driverId: "mxc" },
bootstrapIdentity,
code: "provider-owned-retry",
retryable: true,
detail: "opaque MXC recovery evidence",
});
vi.mocked(fixture.adapter.recoverUnfinishedTransactions).mockResolvedValueOnce({
receipts: [],
failures: [failure("b".repeat(64), "bravo"), failure("a".repeat(64), null)],
});

const recovered = await recoverManagedBootstrapTransactions(fixture.adapter);

expect(recovered.failures.map(({ bootstrapIdentity }) => bootstrapIdentity)).toEqual([
"a".repeat(64),
"b".repeat(64),
]);
expect(recovered.failures[0]).toMatchObject({ sandbox: null, providerId: "mxc" });
expect(Object.isFrozen(recovered.failures)).toBe(true);
expect(recovered.failures.every(Object.isFrozen)).toBe(true);
});

it("rejects duplicate identities across recovered receipts and failures", async () => {
const fixture = adapterFor("openclaw");
const receipt = cleanupReceipt();
vi.mocked(fixture.adapter.recoverUnfinishedTransactions).mockResolvedValueOnce({
receipts: [
{
schemaVersion: MANAGED_BOOTSTRAP_SCHEMA_VERSION,
providerId: receipt.sandbox.driverId,
sourcePhase: "cutover",
sandbox: receipt.sandbox,
bootstrapIdentity: IDENTITY,
outcome: "rolled-back",
finalization: receipt,
},
],
failures: [
{
schemaVersion: MANAGED_BOOTSTRAP_SCHEMA_VERSION,
providerId: receipt.sandbox.driverId,
sourcePhase: "cleanup",
sandbox: receipt.sandbox,
bootstrapIdentity: IDENTITY,
code: "retry",
retryable: true,
detail: "retained",
},
],
});

await expect(recoverManagedBootstrapTransactions(fixture.adapter)).rejects.toThrow(
"duplicate bootstrap identities",
);
});

it("rejects an unbounded provider recovery result before normalizing records", async () => {
const fixture = adapterFor("hermes");
const candidate = {
schemaVersion: MANAGED_BOOTSTRAP_SCHEMA_VERSION,
providerId: "mxc",
sourcePhase: "provider-owned-cleanup",
sandbox: null,
bootstrapIdentity: IDENTITY,
code: "provider-owned-retry",
retryable: true,
detail: "opaque MXC recovery evidence",
} as const;
vi.mocked(fixture.adapter.recoverUnfinishedTransactions).mockResolvedValueOnce({
receipts: [],
failures: Array.from({ length: 4097 }, () => candidate),
});

await expect(recoverManagedBootstrapTransactions(fixture.adapter)).rejects.toThrow(
"provider recovery returned too many records",
);
});

it("blocks same-name and identity-unknown failures while warning for unrelated sandboxes", () => {
const failure = (bootstrapIdentity: string, sandboxName: string | null) =>
Object.freeze({
schemaVersion: MANAGED_BOOTSTRAP_SCHEMA_VERSION,
providerId: "mxc",
sourcePhase: "cleanup",
sandbox:
sandboxName === null
? null
: Object.freeze({ sandboxName, sandboxId: `mxc-${sandboxName}`, driverId: "mxc" }),
bootstrapIdentity,
code: "provider-owned-retry",
retryable: true,
detail: "opaque provider detail",
});
const warn = vi.fn();
const unrelated = failure("a".repeat(64), "bravo");
const sameName = failure("b".repeat(64), "alpha");
const identityUnknown = failure("c".repeat(64), null);

expect(
enforceManagedBootstrapRecoveryForSandbox(
Object.freeze({ receipts: Object.freeze([]), failures: Object.freeze([unrelated]) }),
"alpha",
warn,
),
).toMatchObject({ failures: [unrelated] });
expect(warn).toHaveBeenCalledWith(expect.stringContaining("unrelated sandbox 'bravo'"));

for (const blocking of [sameName, identityUnknown]) {
expect(() =>
enforceManagedBootstrapRecoveryForSandbox(
Object.freeze({ receipts: Object.freeze([]), failures: Object.freeze([blocking]) }),
"alpha",
warn,
),
).toThrow(ManagedBootstrapRecoveryBlockedError);
}
});

it.each([
"BASHOPTS=extdebug",
"BASH_ENV=/sandbox/attacker",
Expand Down
Loading
Loading