Skip to content

Refactor app shell into MVVM layers and enforce architecture boundaries - #213

Merged
SWangHash merged 37 commits into
release/1.0.4from
main
Aug 11, 2026
Merged

SWangHash merged 37 commits into
release/1.0.4from
main

Conversation

@SWangHash

Copy link
Copy Markdown
Owner

Summary

Fixes #

Type and Areas

Type:

Areas:

Motivation / Impact

Verification

Reviewer Notes

Checklist

  • This PR is focused and does not include secrets, temporary prompts, generated scratch files, or unrelated artifacts.
  • Relevant verification is recorded above, or skipped checks are explained.
  • User-facing strings, docs, and locales are updated where applicable.

wgqqqqq and others added 30 commits August 7, 2026 17:22
AppRoot had grown into a single runtime object that owned routing, remote
transport, conversation state and presentation at once, so every feature
change reached across all of them. Split it along explicit boundaries:

- pages/runtime for the composition root and lifecycle
- pages/viewmodel for controllers and view models
- pages/policy for pure decision helpers
- pages/actions for the typed intent/action surface handed to components
- pages/navigation and pages/layout for route and geometry contracts

Components now receive typed action objects instead of reaching into view
models, which lets Local and Remote share one conversation shell
(ConversationRouteSurface on compact, WideConversationHost on wide).

Behaviour changes that came out of the split:

- Creating a chat from the "chat" option binds the desktop's assistant
  workspace first. The desktop ignores workspace_path for Claw sessions and
  always uses its assistant workspace, so the app used to keep showing the
  code workspace it was on while the session was actually created
  elsewhere - the new chat never appeared in the list.
- Picking a workspace in the create sheet now pairs it with the code agent,
  so the picker is honoured instead of being silently dropped.
- Compact remote conversations open the sidebar over the chat from a menu
  button, matching local chats, instead of popping back out of the
  conversation. The system back gesture still leaves the chat and reveals
  the drawer.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
The MVVM split only holds if the import direction is enforced. Add
`pnpm run harmony:architecture`, which fails when services import pages,
when components import view models, when the page graph gains a cycle, or
when action and hook interfaces are passed as anything but typed object
literals.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Remove the parallel application connection and batch review surface, keeping the existing source policy and owner-specific permission controls as the single path.

Reduce Web and TUI output, preserve remote and owner guards, and consume retired automatic defaults once without overwriting later user choices.
fix(agent): include goal lifecycle tools in Cowork
…-mode

fix(remote-ssh): restore target selection and container stdin
…l-tools

fix(agent): make goal lifecycle available to every primary agent
refactor(harmonyos): split the app shell into MVVM layers
Subscription OAuth login, token refresh, and credential resolution now honor the global AI proxy (ai.proxy), including bare host:port URLs normalized to http://. Applies to Codex, Antigravity, and OpenCode subscription providers, and aligns TLS verification with the model configuration.

Also reuse the credential committed by a concurrent refresh when the local conditional commit loses the race, instead of always failing on a revision conflict.
…ttings

feat(web-ui): add pet switch settings action
fix(acp-agents): hide remote servers without deleting
- move the auto-title toggle into the section header
- replace model radio options with a searchable model selector
- align session-title labels and remove obsolete layout styles
- update the Qwen help link to the Bailian console
fix(ai): route subscription auth through the configured proxy
… target

The setup dialog asked for an approval policy and reported target model
readiness, but protocol v4 carries both per turn and the composer already
edits both. Choosing them once while picking a target contradicted that,
and the model row pushed a manual, credential-bearing sync onto the user.

The model picker was also broken for a restored projection. Its options
came from the probe snapshot captured when the session was created, which
lives only in renderer cache — never in the durable outbound record. A
projection rebuilt from the controller index (invariant 28) therefore had
an empty list, and the selector rendered nothing at all, so that session
could never change model again. Models enabled locally after creation
were likewise invisible.

Setup now decides only what the target cannot change later: which target,
which base revision, and whether uncommitted changes travel.

- The new session's approval policy comes from this device's own
  permission default; the composer strip stays the only editor. Both
  mapping directions move into one module so they cannot drift.
- Because the policy is switchable per turn, a target must advertise all
  three approval capabilities to be usable, not just the current one.
- The dispatch model picker offers this device's catalog, unioning in the
  target's probed list rather than being replaced by it, and falls back to
  the local reasoning catalog and default model.
- Submission pushes this controller's model configuration to a target that
  cannot serve the model, before any baseline is created, then re-probes.
  It stays visible as `model-sync` setup-audit rows in the preparation
  journal and the projected transcript, exactly like `cli-install`. A
  failed push is not fatal: the submission reports the target's own model
  diagnostic instead.
- Older targets reject unknown audit actions, so those rows are forwarded
  only to a CLI advertising `setup_audit_model_sync`. The controller
  journal keeps them either way.

Device targets have no such repair path and still fail closed.

AI-assisted. Testing level: fully tested (automated) — dispatch suites in
bitfun-core, bitfun-services-core and the CLI, plus the web-ui dispatch,
ModelSelector and flow_chat suites. Not exercised against a live SSH host.
…-signing-pubkey

fix(ci): pass public key when signing Windows installer
Prevent MiniApp local node_modules and build outputs from triggering false ThemeService contract failures during desktop builds.
…e-web-api-bindings

# Conflicts:
#	scripts/check-github-config.test.mjs
@SWangHash
SWangHash merged commit 4632e79 into release/1.0.4 Aug 11, 2026
3 of 16 checks passed
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.

7 participants