Skip to content

feat: New Fleet wizard writes config.toml locally before S3 (studio#135) - #136

Merged
brettchien merged 1 commit into
mainfrom
feat/wizard-writes-local-config-first-135
Aug 29, 2026
Merged

feat: New Fleet wizard writes config.toml locally before S3 (studio#135)#136
brettchien merged 1 commit into
mainfrom
feat/wizard-writes-local-config-first-135

Conversation

@brettchien

Copy link
Copy Markdown
Contributor

Summary

Closes the gap #134 flagged: the wizard generated config.toml server-side but never wrote it into the operator's local Config folder (#130), so the "Agent configs" view (#134) had nothing to show until something else populated the folder by hand.

Brett's explicit ordering, confirmed directly rather than guessed: "Wizard should write to local first, write to s3 if needed." That ordering can only actually be guaranteed inside the sidecar (oab-mcp) — provision_agent/provision_agent_k8s are what do the S3 upload, so writing the local copy there, before the upload, is a real sequencing guarantee. Having the console write a local copy after receiving the tool's response back (my own earlier #135 write-up's default assumption) would mean S3 had already happened first no matter what — the opposite of what was asked.

Change

  • studio-cp: new write_local_agent_config()<folder>/<name>/config.toml, written from generate_agent_config()'s raw output before inject_pre_seed_hook mutates a copy for the S3/bundle path (that hook wires in an S3 zip URI meaningless for a local reference copy — the local file is the clean, human-authored text, not an ECS/k8s-specific artifact). Both provision_agent and provision_agent_k8s gained a local_config_folder: Option<&str> parameter — write happens unconditionally whenever the caller passes one, and hard-fails the whole deploy on a write error rather than silently proceeding without the copy it promised (folder set = a real requirement per Brett's phrasing, not best-effort).
  • oab-mcp: deploy_provision_agent's schema gained local_config_folder (optional).
  • src-tauri: bridge command threads the new param through.
  • console: deploy.ts reads the same oab-studio.configFolder localStorage key the Config-folder setting (feat(console,src-tauri): local "Config folder" setting (studio#128) #130) already uses and sends it along.

This also resolves the mechanism question #135's own write-up had left open (send config_toml text back to console vs. have the sidecar write directly) — the ordering requirement settles it on its own: only the sidecar-writes approach can guarantee local-before-S3, so no config.toml text (which could carry secret references, aws-sm://..., even if never raw values) needs to cross the Tauri IPC bridge back to the console at all.

Verification

  • npm run typecheck clean, npm test 100/100 passing, npm run build succeeds.
  • Rust side not locally compiled — same pre-existing aws-sdk-ec2 OOM limitation as every other Rust change this week.
  • Worth Brett re-testing a New Fleet deploy with a Config folder set, confirming the local file lands before/regardless of the S3 step completing.

Ref #135.

🤖 Generated with Claude Code

Closes the gap #134 flagged: the wizard generated config.toml server-side
but never wrote it into the operator's local Config folder (#130), so the
"Agent configs" view (#134) had nothing to show until something else
populated the folder by hand.

Brett's explicit ordering: "Wizard should write to local first, write to
s3 if needed." That ordering can only actually be guaranteed inside the
sidecar (oab-mcp) — provision_agent/provision_agent_k8s are what do the S3
upload, so writing the local copy there, before the upload, is a real
sequencing guarantee. Having the console write a local copy *after*
receiving the tool's response back would mean S3 had already happened
first no matter what, the opposite of what was asked — and was the
implementation this session's own earlier #135 write-up had assumed by
default, corrected here after asking Brett directly rather than guessing.

- studio-cp: new write_local_agent_config() — <folder>/<name>/config.toml,
  written from generate_agent_config()'s raw output *before*
  inject_pre_seed_hook mutates a copy for the S3/bundle path (the S3 zip
  URI hook injects is meaningless for a local reference copy). Both
  provision_agent and provision_agent_k8s gained a
  local_config_folder: Option<&str> parameter; write happens unconditionally
  whenever the caller passes one, hard-fails the whole deploy on a write
  error (folder set = a real requirement, not best-effort) rather than
  silently proceeding without the copy it promised.
- oab-mcp: deploy_provision_agent's schema gained local_config_folder
  (optional).
- src-tauri: bridge command threads the new param through.
- console: deploy.ts reads the same oab-studio.configFolder localStorage
  key the Config-folder setting (#130) already uses and sends it along.

This also resolves the mechanism question #135's own write-up had left
open (send config_toml back to console vs. have the sidecar write
directly) — the ordering requirement settles it: only the sidecar-writes
approach can guarantee local-before-S3, so no config.toml text (which
could contain secret *references*, if not raw values) needs to cross the
Tauri IPC bridge back to the console at all.

Ref #135.
@brettchien
brettchien merged commit f96b687 into main Aug 29, 2026
2 checks passed
@brettchien
brettchien deleted the feat/wizard-writes-local-config-first-135 branch August 29, 2026 14:02
brettchien added a commit that referenced this pull request Aug 29, 2026
…(studio#132/#136) (#137)

Two things Brett caught live-testing the wizard (screenshot: Bot token +
Channel secret both showing with Chat platform = "— none —").

## Bug: hidden chat token/secret fields stayed visible

`.compose-form label { display: flex; ... }` has higher specificity
((0,1,1)) than the UA stylesheet's `[hidden] { display: none }` ((0,1,0)),
so toggling `.hidden` on `#deploy-chat-token-wrap`/`#deploy-chat-secret-wrap`
(both <label> elements inside .compose-form) did nothing — same CSS
gotcha already hit once in studio#83's implementation (see that memory),
missed again here since this sandbox can't render the app to catch it.
Added `.compose-form label[hidden] { display: none }` to force the
override, plus the same fix for `.deploy-identity label[hidden]` (the k8s
"new namespace" field has the identical latent bug, unconfirmed live but
same root cause — fixed proactively).

## Feature: ACP token field + Generate button

Brett: "when ACP is enabled, need a field for acp token, and we should
provide a token generator button." Previously the ACP auth key was always
silently auto-generated server-side (uuid v4) with no way for the operator
to see or choose it ahead of deploy.

- console: new "ACP token" field + Generate button (client-side
  crypto.randomUUID(), same shape the server generates), visible only
  while Enable ACP is checked+enabled (reuses the same show/hide-on-toggle
  pattern as the chat platform fields, via a new applyAcpMode() helper).
- studio-cp: AgentWizardInput gained acp_token: Option<String>.
  provision_acp_auth_secret/provision_acp_auth_k8s_secret now take a
  token: Option<&str> — use it if the caller supplied one, else generate
  as before (backward compatible: the compose-library path still always
  passes None). build_default_manifest/build_default_k8s_manifest thread
  it through; all 4 call sites updated.
- oab-mcp: deploy_provision_agent's schema gained acp_token (optional).
- src-tauri: bridge command threads the new param through.

Verification: npm run typecheck clean, npm test 100/100 passing, npm run
build succeeds. Rust side not locally compiled — same pre-existing
limitation as every other Rust change this week.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant