Part II — The workbench
This part covers Chapters 4–8 and introduces the core vehicles of daily use: how workspaces and sessions are organised, the five work modes, assistant personas, and model and parameter configuration.
4. Workspaces
A workspace is the smallest unit of execution in AVL Code. Each workspace binds one local directory plus a set of configuration.
The UI consistently calls it a "project workspace" (e.g. "New project workspace", "Open remote project workspace", "Close project workspace"); this manual says "workspace" for short — the two mean the same thing.
4.1 Create a workspace
- Click "+ New project workspace" in the left sidebar.
- Pick a local path (e.g.
~/projects/my-appor~/samples/2026-04-malware). - Give it a short name (used in the sidebar and in messaging-side shortcuts).
One local directory can be shared by multiple workspaces — e.g. the same repo can be opened twice as "Dev" and "Security audit" with different persona and tool policies.
4.2 Per-workspace directory contents
Each workspace tracks (the user doesn't need to touch this directly):
- All session history under this workspace
- Tool switches and permission policy
- Persona-to-mode bindings
- Connected external tool services
- Companion-messaging bindings
- Skills visible to this workspace
These all live per-workspace and don't interfere with each other.
4.3 Switch, archive and delete
- Switch: click in the sidebar, or
⌘1 ~ ⌘9(macOS) /Ctrl+1 ~ Ctrl+9. - Rename: right-click → Rename.
- Reveal in file manager: right-click → Reveal in Finder / Reveal in File Manager (label adapts to your platform). The header dropdown also has the same entry.
- Close other project workspaces: right-click → Close other project workspaces. Keeps the currently-focused workspace open and closes everything else.
- Archive: right-click → Archive. Archived workspaces leave the main list; restore them in Settings → Recent.
- Delete: right-click → Delete. This wipes session and config for this workspace, but does not delete your source code or samples. A confirmation appears first.
On macOS the "Open workspace" dialog supports creating a new folder directly — no need to make the directory in Finder first.
4.4 Project instructions (AGENTS.md)
Put an AGENT.md / AGENTS.md / CLAUDE.md (in that priority) at the workspace root and its content becomes a # Project Instructions block automatically injected into the system prompt every turn — so the AI keeps to your project rules (coding style, directory conventions, things to avoid, etc.).
- Re-read every turn: edits take effect immediately, no restart needed.
- Subdirectory instructions injected on demand: when the AI reads or writes a file in a subdirectory, the
AGENT.mdfiles along that path's directory chain are also injected as supplementary context (once per session per subdirectory — no spam). Particularly useful in large repos where different modules have different rules. - Safety: reads go through in-workspace path validation + symlink-escape defence (real-path is resolved and confirmed inside the workspace), so a symlink can't take you out of the workspace. Long files are safely truncated on UTF-8 character boundaries and tagged as truncated — no garbled glyphs.
4.4.1 Built-in AGENTS.md editor
No need to switch to an external editor: the session menu and the workspace menu (sidebar + header current-workspace) both have an "Edit AGENTS.md" entry that opens a built-in editor:
- Edit / preview (Markdown render) toggle.
- Shortcuts:
Cmd/Ctrl+Sto save,Tab/Shift+Tabto indent. - Real-time word count in the subtitle area.
- Unsaved-changes protection: closing with unsaved edits confirms first.
- Empty-state template: starting from zero fills in an editable
AGENTS.mdtemplate (which the user can override at~/.config/avlcode/agents-md-template.md). - The save path is also symlink-escape-checked: only writes the workspace-root
AGENTS.md.
4.4.2 SSH remote workspaces (zero install on the remote)
As long as the remote can be reached by SSH, you can use its directory as a workspace — nothing has to be installed on the remote. File I/O, command execution, git operations all go over SSH / SFTP.
Add entry: "Open remote project workspace" in the left sidebar opens the "Connect remote project workspace" dialog, with separate sections by protocol (zWorkspace / SSH). You can connect to a remote before any workspace is open — the empty state page, empty sidebar and empty tab strip all carry a remote entry point, and the menu bar's File → Connect Remote Workspace… ({{kbd:Cmd+Shift+O}} / {{kbd:Ctrl+Shift+O}}) opens the same dialog at any time. The SSH form supports:
- Password / private key / private key + passphrase authentication; the private key picker can browse for a file
- Remote root supports
~(auto-expands to the remote home directory); it may not point at/, and it can't escape the home directory via..or~/.. - "Remember password / passphrase" checkbox: checked ⇒ the credential is encrypted at rest and kept indefinitely; unchecked ⇒ it only lives for this run — kept for the lifetime of the connection so reconnects work, and cleared automatically on app start and on exit
- Existing connections can be right-clicked → "Edit SSH connection" (the checkbox is pre-filled from the stored state, so a remembered credential isn't accidentally downgraded)
Credential security: SSH passwords and private-key passphrases are encrypted at rest with GM SM4-GCM, bound to the local machine, and a random salt is used on every save.
The first connection asks you to verify the host fingerprint: when you connect to a new host, a confirmation block expands in the dialog listing the host's host:port and its SHA256 key fingerprint — check it against the fingerprint supplied by whoever runs the server, then click "Confirm and continue". No password is sent before you confirm; only after confirmation is the fingerprint pinned and verified automatically on later connections. If a known host's key changes, the connection fails outright rather than silently accepting it — that can mean a man-in-the-middle attack, so track down the reason for the change first.
Deep remote integration:
- The file-changes panel uses remote git (if git isn't installed on the remote, the panel is cleanly hidden rather than throwing red errors).
- Skills / Plugins / Hooks are fully available in SSH workspaces: skills are read from the remote, plugin personas are written to remote
.avlcode/, hook commands run on the remote. - File threat scanning (VirusTotal AI) works on remote files (bytes fetched over SFTP).
fs.grepunder SSH uses the remote system grep for speed.- Plans, result drafts and other files all land on the remote — no local/remote brain-split.
- Long-running background commands work here too: start a long-running command on the remote (a service, a build, a test run), then pull its output, list what's still running, and kill it when you're done. Session state lives on the remote, so you can still list and follow those commands after a dropped connection reconnects — or even after the app restarts (background sessions in a local workspace, by contrast, end when the app exits); killing one takes its child processes with it. Note that remote background commands don't auto-detect Python virtual environments (venv detection relies on the local machine's directory layout), so name the interpreter explicitly in the command when you need one.
Safety hardening:
- The
samples/sub-sandbox runs end-to-end on the remote. sys.infofaithfully reports the remote identity.- The right-click menu does not offer "Close and clear data" — this cleanup is fine on local workspaces but would delete real directories on the remote server; irreversible. Plain "Close workspace" remains; the backend hard-rejects the operation too (even if you bypass the UI). The error message points you to "Remove workspace" (which only clears local records and stored credentials, never touching remote files).
Connection failures are reported inline in the dialog with distinct reasons (wrong password / unreachable / etc.), instead of just a vague toast.
When it drops, you can see it and fix it in one click:
- When the remote connection drops, a disconnect icon lights up both on the workspace title and on the sidebar badge, with the tooltip "Remote connection lost — click to reconnect". The icon itself is clickable — no more closing and reopening the workspace.
- Clicking turns the badge into a "Reconnecting…" spinner; on success the connection is restored, on failure it says "Reconnect failed" and you can try again.
- Whether the icon lights up comes from the real link state (not a local cached flag), so you won't get "it's clearly dead but the icon is dark" or "I clicked and nothing happened".
- Half-open connections (the peer is gone but the TCP socket still looks alive) used to hang operations like
fs.grepforever; there is now a connection keep-alive heartbeat plus a timeout on opening a session, so you get an honest error instead of an endless spinner.
Remote operations are considerably faster: directory walks prefetch concurrently, fs.grep prefers a remote ripgrep (falling back to grep, and remembering "this machine has neither" instead of probing every time), and fs.glob lists the whole tree with a single remote find. File I/O moved from "sequential small chunks" to "concurrent large chunks", several times the single-file throughput. The old behaviour where a whole-repo search on an SSH workspace could sit there for ten minutes is gone, and searches now carry an overall budget as a backstop.
Attaching remote directories / files: picking a "session attachment" inside an SSH workspace opens a remote file picker (browsing the remote tree over SFTP) rather than only local paths, and the selection is pushed to the remote sandbox immediately (see §5.6.1).
Cross-OS clients (Windows client to a Linux remote, and vice versa) is fully ironed out: remote commands no longer inject the local environment (they use the remote login shell's own env), and remote paths are always constructed in POSIX style. Earlier releases had pretty much every command on Windows-to-Linux fail with
bash: syntax erroror path-not-found — this release roots it out.
Custom names survive restarts: once you rename an SSH / remote workspace, the restore on restart reads back the name you saved instead of overwriting it with the auto-derived
SSH-<hostname>.
4.5 Active-workspaces cap is 7
To stop a single open session from saturating memory and file handles, AVL Code limits simultaneously active workspaces to 7. When you hit the cap:
- The sidebar "+" and "Open remote project workspace" buttons auto-hide.
- Clicking a history entry in Settings → Recent is rejected with an inline reason; Settings is not auto-closed so you can read the reason and decide.
To add another workspace, close one or two unused ones from the sidebar first.
4.6 Recent workspaces panel
Settings → Recent (page title "Recent project workspaces") is a dedicated tab for every workspace you've ever opened:
- Search box always visible; the list scrolls adaptively; hit terms are highlighted.
- Pinned section and Other section scroll independently — pinned items don't disappear as you scroll the rest.
- Multi-select + top batch operations bar (batch delete / open selected).
- Batch open is now "open selected" (no longer "open all"), to avoid accidentally opening too many at once; beyond the concurrent-active cap it opens the first N, truncated, and tells you so.
- Deletion uses inline countdown (arm-then-confirm, no native confirm dialog).
4.7 Per-workspace settings
The following are per workspace:
- Default work mode
- Persona binding for each mode
- Tool switches and permission policy
- Model choice and parameters
- Connected external tool services
- Companion-messaging bindings
To copy config from an existing workspace to a new one, use Settings → Data.
4.8 Workspace and session layout (sidebar / top tabs)
Workspace-and-session navigation has two layout tiers, switchable in Settings → General → Project workspace & session layout (the "Layout" slider in the header quick menu switches it in one click, without opening Settings):
| Tier | Presentation |
|---|---|
| Sidebar (default) | Vertical workspace icons on the left + tool buttons at the bottom — the classic layout |
| Top tabs | Workspaces and sessions render as a horizontal tab strip at the top; the content area extends edge-to-edge beneath it, freeing up vertical space |
Details of top-tabs mode:
- Each workspace is a coloured chip; the current workspace shows its name. Clicking the chip text or the ▾ both open/close the dropdown (recent sessions / new session / new routine).
- Sessions render as tabs: click to switch; the active tab carries an × close button, and middle-click or the right-click menu's "Close tab" do the same. Closing a tab merely removes it from the strip — the session itself remains, reachable from the chip dropdown or the command palette.
- Open tabs are remembered and restored automatically after a restart.
- Pin a tab: the right-click menu's "Pin tab" keeps a frequently-used session at the front of the strip; pinned tabs are never pushed out by the tab-count limit and are grouped under "Pinned". Right-click again to unpin.
- Drag to reorder: tabs can be dragged into any order. The default order is by most-recently-updated; the first drag switches to a manual order, and the right-click menu's "Sort by most recent" restores the default.
- The right end of the strip keeps the sign-in / settings / help entries and the version badge; after sign-in it shows the current username (fixed width; over-long names are ellipsis-truncated, hover to see the full name).
4.8.1 Sorting and grouping the session list (sidebar layout)
The sidebar's session list can be organised to suit you. Click the slider icon in the list toolbar to open the "Sort and group" menu:
| Dimension | Options |
|---|---|
| Sort | Most recently updated (default) / Created time / Name / Manual drag |
| Group | By time (default) / By status (active, archived) / No grouping |
- Choosing Manual drag flattens the list (no grouping) so you can drag sessions into any order.
- The sort and grouping choice is a global preference; a manually-arranged order is saved per workspace.
- The default combination (most recently updated + grouped by time) matches the previous behaviour — leave the settings alone and nothing changes.
