Repository navigation
feat(pod): select the engine through the sdk resolvers and stage images on W3.7 (#41) - #42
Conversation
…es on W3.7 Every site in the plugin that read the run engine directly now consumes the ONE sdk selection model, and image staging moves onto the W3.7 image store: - ONE resolvePodSelection (selection.go) over deploykit.ResolvePodEngine + ResolveContainerdTarget; the hand-rolled deploy-entry-else-runtime lookup, the unset-engine fallback and the rt-only rootful predicate are deleted. - The resolved target carries the namespace and rootful mode, so a per-deploy namespace: / rootful: now reaches the engine argv, the unit and the store (the capability default was the only namespace source before). - A retired/unknown engine word is rejected instead of silently resolving to the default engine (the old lookup fed the capability table's fallback). - ensureImagePresent probes deploykit.NewImageStore built from the resolved target, then runs build:ensure (W3.6) and re-probes the same store. The engine-specific container.LocalImageExists probe is gone; a daemon failure is no longer read as absent. - Pins: spec v0.2026296.1036 + sdk v0.2026296.1207 (build, vet, test and charly box validate pass on the bump; go mod tidy is a no-op). Not in scope: the overlay build engine (#36, W3.6) and the systemd-container init work (W3.8). Refs #41 Assisted-by: Claude Code deepseek-v4.1-flash:cloud (analysed on a live system)
|
STATUS — the
Done: every engine read in the plugin is on Gate on the committed tree: Live: the changed config path ran live through the baked plugin (isolated XDG) and reached the new store probe; the full pod bed is a visible skip — the dev binary's Next: read the fresh Agent: |
Review — PASSI re-derived the PR against the complete current state (21 files, head Correctness vs. body claims. The per-site migration table matches the diff:
Tests. Security. No secrets introduced. The Honesty / scope. File count (21) and head SHA match. The Non-blocking observations. Comments. The comment thread is empty; nothing to disposition. Verdict: PASS ollama-cloud/deepseek-v4.1-flash — action-review. |
|
RESOLVED — the
Settled: every engine read in the plugin is on Validator observations, dispositioned: Gate on the committed tree: Not in scope, unchanged: W3.6 overlay build engine ( Agent: |
Summary
Migrates
plugin-deploy-pod— the largest consumer left — onto the sdk's ONE selection model and the W3.7 image store. Every site that readrt.RunEngine, re-derived "deploy entry else runtime" by hand, or carried an engine fallback now callsdeploykit.ResolvePodEngine+deploykit.ResolveContainerdTarget; image staging probesdeploykit.NewImageStoreinstead ofcontainer.LocalImageExists.Pins:
github.com/opencharly/spec v0.2026296.1036,github.com/opencharly/sdk v0.2026296.1207(W3.1 resolvers + W3.7ImageStore/ResolveImage).Behaviour this changes (each pinned by a test that fails on the pre-change tree):
kit.EngineBinaryfed it tocontainer.EngineCapabilityFor, which resolves ANY unknown word to the default engine — anerdctldeploy ran podman silently.namespace:now reaches the engine argv/unit/store. Before,engineGlobalArgsemitted the capability's default namespace only.rootful:now reaches the target (and the refusal predicate reads it). Before, the predicate readrt.Rootfulonly.absentis concluded only when the daemon answered.Not in scope (unchanged): the W3.6 overlay build engine (
overlay.go:51,#36) and the W3.8 systemd-container init work.Per-site migration (old → new)
origin/maina2d8546)resolve.go:47,212rootfulRefusal(rt.RunEngine, rt.RunMode),rootfulUnsupported(rt)rootfulRefusal(sel.Engine, …),rootfulUnsupported(sel.Target, rt.RunMode)resolve.go:60,95,313boxEngineForDeploy(…, rt.RunEngine)resolvePodSelectionFromConfig(dc, box, instance, rt)resolve.go:158-161detectDevices(…, rt.RunEngine);engine := rt.RunEngine;meta.EngineoverridedetectDevices(…, string(sel.Engine));sel.Engine(override deleted)resolve.go:178,181ensureImagePresent(…, rt.RunEngine),ExtractMetadata(rt.RunEngine, …)ensureImagePresent(…, sel.Target),ExtractMetadata(string(sel.Engine), …)resolve.go:293podRootful(rt)sel.Target.Rootfulconfig_setup.go:98,191,197,258,340,345,350,382,553rt.RunEngineat eachsel.Engine/sel.Target(resolved once per config run)config_setup_helpers.go:524,526runConfigDirectrootful/engine fromrtselconfig_setup_helpers.go:586,600dataEnginefrom the entry by hand;ensureImagePresent(rt.RunEngine)resolvePodSelectionFromConfig;sel.Targetconfig_setup_helpers.go:704,708,724,762,789updateAllDeployedQuadletsused the globalrt.RunEngineresolvePodSelectionFromConfigconfig_remove.go:40,42,44engineStopArgv(rt.RunEngine, …),engineRemoveArgv(rt.RunEngine, …)sel.Targetenc_tunnel_resolve.go:96engine := rt.RunEnginesel.Engineengine_ops.go:52engineRunArgv(engine, rootful, …)engineRunArgv(target, …)(Rootful+ globals from the target)engine_ops.go:142-151target.Address/target.Namespaceengine_ops.go:168-176engine_ops.go:216,231podRootful(rt),rootfulUnsupported(rt)image_ensure.go:36-64container.LocalImageExists(engine, ref)+resolveRunEnginefallbackNewImageStore(ex, target)+ResolveImagestep 1 +build:ensure+ re-probelifecycle.go:334ExtractMetadata(rt.RunEngine, …)resolve_f12.go:154,285,304boxEngineForDeploy(…, rt.RunEngine)resolve_ref.go:44currentRunEngine()volume_root.go:94sel.EngineDeleted in the same cut:
boxEngineForDeploy,currentRunEngine,resolveRunEngine,podRootful, themeta.Engineoverride, andimage_ensure_test.go(the test of the retired probe).How tested
Gate derived from
.github/workflows/(this repo ships onlytag-on-merge; the merge gate is the org-widecharly/pr-validator, and the repo's AGENTS build/validate/test surface is the local gate). Every command's OWN exit code, on the committed tree:Pin bump verified against the producers:
sdk v0.2026296.1207requiresspec v0.2026296.1036(its owngo.mod), and the downstream module builds, vets and tests at both tags — no assumption that a bumped producer compiles.Failing-without controls
The new tests were copied onto a throwaway worktree of the PRE-CHANGE
origin/main(a2d8546) and run there:The retired behaviour itself was measured on that same pre-change tree (one-off control, not shipped):
Each migrated site's arm:
TestResolvePodSelection_RejectsRetiredEngineWord(site 1),TestDeployNamespaceReachesEngineArgv+TestEngineRunArgv_UsesResolvedTarget(site 2 and the argv builders),TestDeployRootfulReachesTarget(site 3),TestEnsureImagePresent_ProbesResolvedStore(the store boundary, including the post-build:ensurere-probe).Live result — visible skip (mechanism named)
The migrated plugin was built from this head (
cmd/serve) and served as a baked provider (CHARLY_PLUGIN_DIR+plugin-deploy-pod.providers=deploy:pod) into an isolatedHOME/XDG_*, so the changed runtime path really ran:That failure is the NEW store probe correctly reporting absence (the local image is
localhost/check-crabbox-cli:…, and the short ref is a different storage key); the resolver +NewImageStore.Has+build:ensurepath executed live.A full pod deploy on a disposable bed was NOT achieved, for two mechanisms measured on this host, not faked:
charlybinary (source and binary both2026.293.1809) resolvesdeploy add's substrate from the compiled-in/project-scan path only:target "pod" is a known substrate but its deploy provider is not connected (… not compiled-in or failed to load)— even with the same bakeddeploy:podbinary theconfigpath connects. This is the deploy-add provider-resolution path, not this plugin's code.xt_multiportis absent from this kernel (modinfo xt_multiport→ERROR: Module xt_multiport not found; no/sys/module/xt_multiport), so a containerd lease cannot acquire here.The R10 pod beds (
check-pod-overlay,check-sidecar-pod) were therefore not run; the live evidence above is the changed config path. The tier says so.Rulebook compliance
#36.selection.go); the per-call-site lookups, the unset-engine fallback and the rt-only rootful predicate are deleted, not kept as siblings.#36.origin/main; no submodule tracked checkout was modified; no force-push.build:ensure, not just at call time.charly box validateran on the committed tree with the dev binary named above.specfields (Deploy.Engine/Namespace/Rootful,containerd.namespace); no CUE edit, so nocue-genrun was owed.Change classification
Runtime consumer migration in the out-of-tree
deploy:podplugin: Go source + tests +go.mod/go.sumpins. No schema, no CLI surface, no image definition.Filed issues
None filed by this PR. The one out-of-scope residue (W3.6 overlay build engine) is the pre-existing
opencharly/plugin-deploy-pod#36.Closes #41
Agent:
containerd-crabbox-program/w31d· session8b1c01cf-7f79-4a75-bff8-240415a06208Assisted-by: Claude Code deepseek-v4.1-flash:cloud (analysed on a live system)