03 — Workspaces and Scopes¶
Replaces the earlier multi-tenant doc.
alexandriais single-user. The only boundary that matters is the workspace — a self-contained body of knowledge.
Two kinds of workspace¶
Global workspace¶
~/.alexandria/workspaces/global/
- Exactly one. Created at
alexandria init. - Holds the user's general knowledge — personal learning, long-standing interests, cross-cutting notes.
- Default target when no workspace is specified.
Project workspaces¶
~/.alexandria/workspaces/<slug>/
- Many. Created with
alexandria project create <name>. - One per customer, client, research topic, product, or coherent body of work.
- Each has its own sources, subscriptions, log, and wiki pages.
- Self-contained: deleting the directory removes the workspace (and the SQLite index rows reference by path, so they clean up on next
alexandria reindex).
Example layouts:
~/.alexandria/workspaces/
├── global/ # my general knowledge
├── customer-acme/ # work I'm doing for Acme Corp
├── paper-transformers/ # a literature review
├── side-project-xyz/ # personal build project
└── learning-rust/ # a topic I'm studying
What a workspace contains¶
workspaces/<slug>/
├── SKILL.md # the agent contract for this workspace (extends the global template)
├── config.toml # name, description, contract version, per-workspace settings
├── raw/ # immutable source material organized by adapter
│ ├── notion/
│ ├── github/
│ ├── papers/
│ ├── local/
│ └── subscriptions/
│ ├── newsletter/
│ └── twitter/
└── wiki/ # compiled markdown pages, agent-owned
├── overview.md # mandatory hub page
├── index.md # mandatory table of contents
├── log.md # mandatory append-only operation log
├── concepts/
│ └── ...md
├── entities/
│ └── ...md
└── archives/ # immutable query snapshots
Nothing else. If a user wants something else, they put it in raw/ and let the agent compile it.
One workspace at a time¶
The guardian agent is always scoped to one workspace for the duration of a session. It is passed as an argument (--workspace customer-acme) or selected via alexandria workspace use customer-acme which sets the current default.
The agent's MCP tools all operate inside that workspace's directory. A tool cannot reach outside it. There is no search --workspace=other, no read("../other/..."), no cross-workspace writes. This is enforced in the tool layer by resolving every path against the workspace root and rejecting paths that escape it.
Rationale: workspaces represent distinct knowledge scopes. Mixing them in the agent's context is exactly what corrupts the wiki. Steph Ango's vault-separation rule applies between workspaces as much as between us and Obsidian.
Switching workspaces¶
Three ways:
- Explicit argument on every command:
alexandria query --workspace customer-acme "...". - Current workspace set in
~/.alexandria/config.tomlunder[state] current_workspace = "customer-acme". Commands without--workspaceuse this. The CLI exposesalexandria workspace use <slug>andalexandria workspace current. - Environment variable
ALEXANDRIA_WORKSPACEfor scripts and agent sessions.
The daemon serves a separate MCP endpoint per workspace (e.g. http://localhost:<port>/mcp/customer-acme) so Claude/Cursor connectors can be pinned per project. Switching is a connector change, not a runtime state flip — avoids silent context bleed.
Cross-workspace queries — deferred¶
The user will eventually want "what do I know about OAuth across all my projects?" That's a cross-workspace query. It is explicitly not supported at MVP because:
- The agent's system prompt becomes ambiguous (which schema? which log?).
- Citations need to carry workspace identifiers, changing the file-reference format.
- Write-back (archive the answer) has no obvious target.
Future: a dedicated alexandria query --global or a meta workspace that indexes summaries from every other workspace. See 07_open_questions.md.
Config surface¶
~/.alexandria/config.toml:
[general]
data_dir = "~/.alexandria"
default_llm = "claude-opus-4-6"
editor = "nvim"
[state]
current_workspace = "global"
[daemon]
enabled = false
port = 7219
web_ui = true
mcp = true
[limits]
max_pages_per_workspace = 2000
max_tokens_per_ingest = 200000
[secrets]
keyring_service = "alexandria"
~/.alexandria/workspaces/<slug>/config.toml:
[workspace]
name = "Acme Corp"
description = "Everything I'm doing for Acme"
contract_version = "v1"
created_at = "2026-04-15"
[agent]
topics = ["integration", "contracts", "infra", "meetings"]
# optional: constrains the agent's topic subdirectories
Creating and destroying workspaces¶
alexandria project create customer-acme --description "Acme Corp work"
alexandria project list
alexandria project delete customer-acme # prompts for confirmation, archives to trash
alexandria project rename customer-acme acme
alexandria project info customer-acme # sources, pages, last activity
Delete is soft: the directory moves to ~/.alexandria/.trash/<timestamp>/. alexandria gc empties trash older than N days. SQLite rows are purged on next reindex.
Workspace templates¶
When creating a project, the user can pick a template that seeds topic directories and a tailored SKILL.md:
--template customer— topics:overview,contracts,meetings,integrations,decisions.--template research— topics:papers,concepts,methods,open-questions.--template product— topics:features,bugs,decisions,user-feedback.--template learning— topics:notes,examples,exercises,references.--template minimal— justoverview.md,index.md,log.md, no topics.
Templates live in the package at alexandria/templates/workspaces/. Users can override with ~/.alexandria/templates/.