# Workspace = Claude-Desktop-style project (v2 of the workspace redesign) _Replaces the Orca-shaped project → workspace → worktree tree from phase 1. Three phases, each one commit on `main`, in order._ ## What the user asked for 1. Merge the **Workflows** page into the Dashboard → **Analytics** tab. 2. The sidebar lists **workspaces**, each expanding to **its sessions only** — like Claude Desktop's project list (name ›, `+` on the row, sessions under it). 3. A workspace opens on a **project home** like Claude Desktop's: title, prompt box, Recents; on the right, **Instructions**, **Memory**, **Context** (files/documents) and **Folder** (folders) — no Scheduled. 4. Clicking a session **opens its tmux pane** and never resumes it (a resume re-reads the whole transcript and burns tokens). 5. The Orca parts are regrouped by workspace and kept where they still make sense. ## Phase A — Workflows inside Analytics - `Dashboard.tsx` Analytics → the existing `workflow` sub-tab renders the whole `Workflows` page body (pipelines, skill usage, Workflow-tool runs, DAG, error map, complexity, compaction, drill-in) under its current small cards. - `/workflows` → ``; the sidebar loses its **Workflows** item; `DocumentTitle`, i18n `nav.workflows` removed. - No server change. ## Phase B — Sidebar: workspaces → sessions ``` WORKSPACES + 🔍 ⚙ agenthub › + SG_MiniApp ⌄ + ● Tách thông tin official account (● = a live tmux pane) ○ Kiến trúc tenant đơn mở rộng scratch › + ``` - A flat list in the stored drag order (`agenthub.workspace.laneOrder`, kept); the repo grouping, the "Folders" pseudo-project, untracked worktrees and Adopt leave the sidebar. - A row's chevron expands its sessions (`GET /api/sessions?cwd=&tool=`, the newest 20, the session's name or first prompt). A dot shows a live pane. - Click the **name** → the workspace home (Phase C). Click `+` → the home with the prompt focused. Click a **session**: - its pane is alive (a `dashboard_runs` row with that `session_id`, the tmux session `agenthub-lane-[-slot]` still there) → the session view attached to that pane — no new process, no resume; - no live pane → the read-only transcript (`/sessions/:id`, Conversation tab), with **Resume** as a separate, explicit button that warns about context cost. - Kept: rename (double-click), drag / Alt+↑↓ reorder, right-click menu (Start/Stop, Rename, router, readme, Copy path, Reset, Remove). - Header: `+` new workspace (the Add modal), search (filters workspaces and loaded session titles), a tool filter. ## Phase C — Workspace home + sources Route: `/workspace?lane=` = home; `/workspace?lane=&run=` = the session view (today's terminal, split panes and the Files/Changes panel, unchanged — the one-render-site console rule still holds). ``` Workspaces / SG_MiniApp 📌 ⋯ ┌────────────────────────────────────────────┐ ┌ Instructions ✎ ┐ │ How can I help you today? │ │ text… │ │ + [Claude ▾] [model ▾] [effort ▾] [Run]│ ├ Memory View ────┤ └────────────────────────────────────────────┘ │ CLAUDE.md, auto │ Recents ├ Context + ─┤ Tách thông tin official account 2h ago ● │ spec.pdf notes… │ Kiến trúc tenant đơn mở rộng Sep 29 ├ Folder + ─┤ │ 📁 SG_MiniApp │ │ 📁 sg-shared │ └──────────────────┘ ``` - **Prompt box** = today's run form (tool's model picker, permission, effort, bypass), compact. Run → a new pane, then the session view. - **Recents** = the same session list as the sidebar, with time ago, cost and the live dot. - **Instructions** — one text per workspace, `lanes.instructions`. Reaches the agent at spawn: Claude `--append-system-prompt `; Codex `-c developer_instructions=` if 0.155 accepts it (verified while building — otherwise Claude-only, shown as "not supported by "). Never written into the user's repo. - **Memory** — read-only: the folder's `CLAUDE.md` / `AGENTS.md` and Claude's auto-memory dir for that cwd (`/projects//memory/`). **View memory** opens them in the existing markdown viewer. - **Context** — files the user uploads (pdf, md, txt, images…, ≤ 10 MB each), stored by AgentHub under `/workspace-context//` with a server-chosen name. The directory goes to the agent as `--add-dir`, and the appended instructions list the files, so the agent knows to read them. - **Folder** — the workspace's own cwd (fixed) plus extra folders, each `--add-dir` for Claude and Codex (both verified in `--help`); other tools show them as unsupported. **+** opens a folder picker that also suggests the repo's untracked worktrees (what is left of Adopt). A folder must exist, be a directory and not be or contain the OS home (`validateHomeDir`). - **⋯ menu** = the row menu plus what Settings → Projects held (facts, worktree count, Forget). ### Schema (migration-safe) - `lanes.instructions TEXT` (ADD COLUMN, null). - `CREATE TABLE IF NOT EXISTS lane_sources (id INTEGER PRIMARY KEY, lane_id INTEGER NOT NULL REFERENCES lanes(id) ON DELETE CASCADE, kind TEXT NOT NULL CHECK (kind IN ('folder','file')), path TEXT NOT NULL, name TEXT NOT NULL, size INTEGER, added_at TEXT NOT NULL)`. - Removing a workspace deletes its rows and AgentHub's own context copies — never a user folder. ### API - `GET/PUT /api/lanes/:id/instructions` - `GET /api/lanes/:id/sources`, `POST …/sources/folder {path}`, `POST …/sources/file` (raw body, name header, size cap), `DELETE …/sources/:sourceId` — all `sameOriginGuard`. - `GET /api/lanes/:id/memory` → the memory files above, read-only. - Spawn (`spawnRun`) reads instructions + sources from the lane row, never from the request — the same rule as `tool`. ### Settings - **Projects** group leaves Settings (now the workspace's ⋯ menu). - **Worktrees** stays, renamed "Worktree suggestions": whether Add folder suggests untracked worktrees and from which sources. ## Verification Each phase: tests first for new logic, `npm run test:server`, `npm run test:client`, headers, build, screenshots; docs + CLAUDE.md marker.