Print parity across backends #96
Reference in New Issue
Block a user
Delete Branch "%!s()"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Problem
The y/N preflight
print()method is declared@abstractmethodonBottlePlanbut implemented independently on each backend. The two implementations produce different output for equivalent configurations.After PRD 0038 (smolmachines env contract), the env_names divergence is resolved —
resolved.forwardedis now merged intoagent_provision.guest_envat prepare time on both backends, so the displayed env names are equivalent.The remaining gaps are two rendering differences, both using the same underlying plan fields:
upstream_host:upstream_portfrom resolvedgit_gate_plan.upstreamsName → Upstreamfrom manifestbottle.githost [auth:scheme]hostonly (auth dropped)The smolmachines docstring says "same shape as the Docker backend's" — that intent is real but not enforced by anything structural.
Proposed data-layer solution
Both backends already carry
git_gate_plan: GitGatePlanandegress_plan: EgressPlanas fields. The fix is to hoist these (along withagent_provisionandsupervise_plan) toBottlePlanand implementprintconcretely there, eliminating the per-backend implementations.Hoist shared fields — move
git_gate_plan,egress_plan,agent_provision, andsupervise_planfrom the concrete subclasses up toBottlePlan. Both backends already populate them at prepare time with the same types.Unify git display — use
git_gate_plan.upstreams(the resolved plan) everywhere, dropping smolmachines's use of manifest-levelbottle.git. Format:upstream_host:upstream_port, consistent with Docker today.Unify egress display — use the full
[auth:scheme]annotation in both backends, sinceegress_plan.routescarriesauth_schemeon both.Make
printconcrete — once the above is in place, remove@abstractmethodfromBottlePlan.printand implement it there. The backends drop their ownprintmethods entirely.Consolidate print command for plansto Print parity across backendsIs there a reason for the
forwarded_envdivergence? Gut tells me we should just be addingforwarded_envfor smolmachines as well, but I don't remember the exact purpose of it.forwarded_envexists specifically to keep secret values off argv, off the env-file, and out of the compose YAML. Incompose.pythe service gets bare names only (env.append(name)with no=value), so Docker inherits the value from the compose-up process env — which holdsforwarded_envvia**plan.forwarded_envincompose_env. The OAuth token and any host-env-interpolated manifest values flow through that path.smolmachines has no equivalent today:
smolvm machine create -e K=Valways puts the value on argv. That's the rank-1 gap from audit #134, filed as #135 and tracked as PRD 0038 (branch exists, not merged yet). So the asymmetry inprintisn't a display bug we accidentally introduced — it reflects a real structural difference.For the print fix, the
_extra_env_keys()hook sidesteps the question cleanly: Docker overrides it to returnforwarded_env.keys(), and smolmachines can override it once PRD 0038 lands and gives it an equivalent field (whatever that ends up being named). The baseprintstays ignorant of the mechanism either way. That said, it's worth confirming what 0038 actually settles on before wiring the hook — if smolmachines ends up with aforwarded_envfield of its own, hoisting that toBottlePlandirectly would be simpler than the hook.Correction to my previous comment: PRD 0038 was already merged via #141 (and is Active) — I was looking at a stale local clone. Apologies for the noise.
After that change, smolmachines
prepare.pymergesresolved.forwardedintoguest_envbefore buildingagent_provision, soagent_provision.guest_envnow includes the forwarded keys. The env_names divergence I flagged is largely already resolved by that work — the_extra_env_keys()hook I proposed is unnecessary.The real remaining gaps are just the two formatting differences: git gate lines (Docker renders the resolved
upstream_host:upstream_portfromgit_gate_plan.upstreams; smolmachines renders the manifest-levelName → Upstreamfrombottle.git) and egress lines (Docker includes[auth:scheme]; smolmachines drops it). Both use the same underlying plan fields (git_gate_planandegress_plan), so unifying the rendering is straightforward once the fields are hoisted toBottlePlan.