refactor: migrate stores to features/, remove dead packages, add modals + workspace sync

## Store migration (packages → features)
- Delete `packages/store/` — stores moved into web app's feature modules
- Delete `packages/hooks/` — replaced by feature-level hooks
- `features/issues/store.ts` — useIssueStore (was packages/store/issue-store)
- `features/inbox/store.ts` — useInboxStore (was packages/store/inbox-store)
- `features/workspace/store.ts` — absorbs agent state (was packages/store/agent-store)
- All imports updated from `@multica/store` → `@/features/*/store`

## Global modal system
- `features/modals/store.ts` — useModalStore (zustand)
- `features/modals/registry.tsx` — ModalRegistry renders active modal
- Mounted in app/layout.tsx alongside Toaster
- Create Workspace dialog now works (was broken: DropdownMenu ate click)

## Workspace real-time sync
- useRealtimeSync subscribes to workspace:updated, member:removed
- Member removal → auto-switch to another workspace
- Workspace settings update → sidebar reflects name change
- Workspace switch → parallel fetch issues + inbox + agents

## Bug fixes
- theme-provider: guard event.key for IME composition (isComposing check)
- task.go: publish comment:created + inbox:new events on task complete/fail
- listeners.go: broadcast comment:created, workspace:updated, member events
- events.go: add EventCommentUpdated, EventCommentDeleted constants

## Cleanup
- Remove _features/ tracking files (dev-only, not for main)
- Remove server/server binary from worktree
- Update CLAUDE.md to reflect new architecture

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
Naiyuan Qing 2026-03-25 16:37:22 +08:00
parent 0c52b89e40
commit 66b1defab7
48 changed files with 607 additions and 861 deletions

View file

@ -37,14 +37,15 @@ apps/web/
|---|---|---|
| `features/auth/` | Authentication state | `useAuthStore`, `AuthInitializer` |
| `features/workspace/` | Workspace, members, agents | `useWorkspaceStore`, `useActorName` |
| `features/issues/` | Issue components and config | Icons, pickers, status/priority config |
| `features/realtime/` | WebSocket connection | `WSProvider`, `useWSEvent` |
| `features/issues/` | Issue state, components, config | `useIssueStore`, icons, pickers, status/priority config |
| `features/inbox/` | Inbox notification state | `useInboxStore` |
| `features/realtime/` | WebSocket connection + sync | `WSProvider`, `useWSEvent`, `useRealtimeSync` |
**`shared/`** — Code used across multiple features. Currently only `api.ts` (SDK singleton).
### State Management
- **Zustand** for global client state (`features/auth/store.ts`, `features/workspace/store.ts`).
- **Zustand** for global client state — one store per feature domain (`features/auth/store.ts`, `features/workspace/store.ts`, `features/issues/store.ts`, `features/inbox/store.ts`).
- **React Context** only for connection lifecycle (`WSProvider` in `features/realtime/`).
- **Local `useState`** for component-scoped UI state (forms, modals, filters).
- Do not use React Context for data that can be a zustand store.
@ -62,6 +63,8 @@ Use `@/` alias (maps to `apps/web/`):
import { api } from "@/shared/api";
import { useAuthStore } from "@/features/auth";
import { useWorkspaceStore } from "@/features/workspace";
import { useIssueStore } from "@/features/issues";
import { useInboxStore } from "@/features/inbox";
import { useWSEvent } from "@/features/realtime";
import { StatusIcon } from "@/features/issues/components";
```
@ -92,9 +95,7 @@ Browser ← WSClient (SDK) ← WebSocket ← Hub.Broadcast() ← Handlers/TaskSe
- **`@multica/sdk`**: `ApiClient` (REST) and `WSClient` (WebSocket) classes. All backend communication goes through here.
- **`@multica/types`**: Shared domain types + WebSocket event types (issue:created/updated/deleted, task:*, agent:status, comment:*, inbox:new, daemon:*).
- **`@multica/store`**: Zustand stores — simple arrays with add/update/remove. No persistence; memory only.
- **`@multica/ui`**: shadcn/ui component library with Radix primitives, Tailwind CSS 4, Shiki syntax highlighting for markdown.
- **`@multica/hooks`**: `useRealtime()` (WS → store sync), `useIssues()`, `useAgents()`, `useInbox()` (fetch + cache).
### Multi-tenancy