A change that spans more than one repository, an API and the app that calls it, a service and its SDK, is awkward as separate branches in separate windows. A Topic is one branch name across any set of repositories, opened as a single workspace: one file tree, one search, one commit message, and one chat that sees all of them.
Each repository joins a Topic in one of two ways:
- Worktree: it gets its own worktree on the Topic’s branch, so the work can change it.
- Reference: no branch and no worktree. A read only view of the repository’s own checkout, for code the change needs to read but not touch.
Where Topics are listed
A Topic that belongs to no space is listed in Home, the first tile in the space strip, under its Topics heading. A Topic that belongs to a space is listed in that space’s tree, see Topics in a space.
Create a Topic
- In Home, click + by the heading and pick New topic, or click the + on the Topics heading.
- Type a name. Branch fills in from the name as you type, with no prefix added, until you change it yourself. It is the exact branch every worktree member will use. A name git would not accept says not a valid branch name.
- On the left, pick the repositories, grouped by space. Filter them with Filter repositories.
- Each pick gets a card on the right. Set it to Reference or Worktree.
- If a repository already has a branch of that name, its card offers to adopt it instead of making a new one.
- Click Create Topic.
The new Topic is selected straight away, with a chat draft at its home ready to type in, unless something is already open there. A Topic made here belongs to no space; to make one inside a space, see Topics in a space.
Worktrees are made under each repository’s .tori/worktrees/ folder (a plain
repo) or beside its other worktrees (a bare one). A member that fails to set up
is listed with Retry, and the rest of the Topic is still made.
Topics in a space
A Topic can belong to one space. It is then listed in that space’s tree, under a Topics heading above the space’s projects, and can hold that space’s projects only. A Topic that belongs to no space is listed in Home and can hold projects from any space.
To make one, open the space menu and pick New Topic (Groups worktrees from work’s projects), or click the + on the space’s Topics heading, New Topic in work. The dialog is titled New Topic in work and lists Projects in work only, with how many are picked, each project naming the branch its checkout is on, such as from main. Under the list: Only work’s projects can join. For projects from several spaces, make the Topic in Home. The new Topic opens in the space’s tree.
In the space’s tree:
- Click the Topics heading to collapse the group; each space remembers its own. Collapsed, the heading counts the Topics and carries a status bubble for them.
- While there is a Topics group, the projects below it get a Projects heading, which collapses the same way.
- Past six, Topics and projects fold into a N more row, see Long groups.
- The filter narrows both groups, and each heading counts what is left.
- The title bar reads the space, the Topic and the member in front, such as work > webhooks > api.
Adding a project from another space to a space’s Topic is refused, from the phone and the command line too: api is not in work, and webhooks holds work’s projects only. Use Move to… on the Topic to list it in Home first.
When a space’s folder is gone
A space is its folder, so renaming or deleting the folder outside Tori leaves its Topics with no tree to be listed in. Such a Topic shows in Home, with a note under its row: From work, which Tori can’t find. Its folder was renamed or deleted outside Tori. Keep in Home makes it a Topic of no space; Delete opens the usual delete. Until then its members can still be repaired.
Move a worktree into a Topic
Work that started as an ordinary worktree can join a Topic as it is. Right-click the worktree in Spaces and pick Move to topic…. The dialog has two tabs:
- Existing: one list, filtered with Search Topics, in two groups: In work, the Topics of the worktree’s own space, then Home, those that belong to no space. Topics of other spaces cannot take it, so they are not offered. Pick one and click Move.
- New: the New Topic form with this worktree already in it, shown as This worktree, on its branch. Branch starts as the worktree’s branch. Where puts the new Topic in the worktree’s space (Lives in work’s tree. Can hold work’s projects only.), the default, or in Home (Listed in Home. Can hold projects from any space.). Pick any other repositories and click Create and move. The dialog opens on New when there are no Topics yet, and switching tabs keeps what you typed.
After the move the sidebar opens the Topic where it is listed, the space’s tree or Home, with the moved worktree in front. Tabs open in the worktree move with it. A chat that was already started keeps working in that one repository, since it keeps the folders it launched with; the dialog says so before you move, for example 1 chat here moves with it and keeps working in this repo only. New chats in the Topic see every repo. A draft you have not sent yet moves to the Topic’s home and sees every repository.
Nothing in git changes: no checkout, no new branch, no commit, and the worktree’s changes stay where they are. The worktree keeps its own branch even when the Topic’s is a different one, and its member row then reads On that branch. Its pull request is looked up on that branch too.
Some moves are refused, and the dialog says why before you click: the first two as soon as it opens, the last once you pick that Topic.
| The dialog says | Why |
|---|---|
| … is not on a branch | The worktree has a detached HEAD |
| … is on main, the repository’s default branch | The default branch’s checkout is what references read, so it stays out of Topics |
| … is already in … with a worktree | That Topic already has a worktree in the repository. Only that Topic is refused |
If the Topic already has the repository as a reference, the worktree takes its place, Replaces the reference to the repository, and tabs open on the reference follow it.
A moved worktree’s branch is yours, not the Topic’s, so Tori never deletes it: its menu has no Remove worktree…, a missing folder offers no Recreate, and removing the repository or deleting the Topic offers the worktree without the branch. Remove repository is how it leaves.
Once moved, the worktree is listed under its Topic. Spaces lists it only with Show Topic worktrees in Spaces on, see Topic worktrees in Spaces.
References
A reference row wears a lock, says how far behind its remote it is, and warns when the checkout is off its default branch or has local changes. Tori never stages, commits, discards or pushes in a reference. Pull, on its menu, is fast-forward only.
The Topic in the sidebar
A Topic is a row with its members under it, like a project with its branches. Collapsed, it is one line with a chip per member and a status for the Topic’s chat. A new Topic opens expanded, and the list remembers which are open.
- Click a member to open the Topic with that member in front.
- An expanded member shows its pull request on a second line. A failing check lights that member’s chip and the Topic’s status.
- The Topic’s row shows its sync state beside the status.
The Topic menu
Right-click a Topic, or use its actions button:
| Item | What it does |
|---|---|
| Rename… | Changes the Topic’s name. The branch stays as it is |
| Move to… | Lists the Topic in Home or in a space’s tree, see Move a Topic |
| Add repository… | Opens the same picker to add members, Add to Topic |
| Delete… | Deletes the Topic, see below |
Move a Topic
Move to… on the Topic menu opens Move webhooks, which says where it is now, Now in Home or Now in work. Pick Home (Any space’s projects), listed first, or one of your spaces, then click the button, which names the choice: Move to work. The place it is now is marked Current.
A space can take the Topic only when every member is one of its projects. Any other space stays in the list, greyed, saying which members are elsewhere and where: api and web are in saga, or api is in saga; cms is in craft for members from more than one space. Moving changes nothing about the members. After the move the Topic opens where it now lives.
The member menu
Right-click a member:
| Item | What it does |
|---|---|
| Pull | References only: fast-forward the checkout |
| Create worktree | Turns a reference into a worktree on the Topic’s branch |
| Remove worktree… | Turns a worktree back into a reference. The branch is kept, so creating the worktree again picks the work back up. Not offered for a moved worktree |
| Rename… | Changes the name shown for the member. The repository and its worktree stay as they are |
| Move up, Move down | Reorders the members |
| Remove repository | Takes the repository out of the Topic, and asks what to do with its worktree. A Topic needs one member, so the last cannot be removed; delete the Topic instead |
Delete a Topic
Delete… lists every member with what git says about its worktree, clean, uncommitted changes or unpushed commits, before you confirm. Deleting the Topic itself loses nothing: make it again over the same repositories and the branches are still there. Deleting a space deletes its own Topics with it, see Delete a space.
The same dialog decides what goes with it, as a table of Repository, Worktree and Branch. Each member shows its branch, its folder and a tag: clean, merged, uncommitted, unpushed, or main checkout for a reference, which reads Not a worktree and offers nothing to remove.
Tick Worktree to remove that worktree, and Branch to delete its branch too; a branch can only go with its worktree. A clean or merged row starts ticked, and a row with work at risk starts unticked. Ticking one that would lose something says so under it, such as Uncommitted changes in this worktree will be lost. or Commits on feat/auth aren’t pushed and will be lost., and a worktree with terminals running in it says they will stop. A moved worktree never offers its branch, which reads Kept. Anything left unticked stays in its repository and shows up in Spaces.
The foot of the dialog sums it up, such as Removes 2 worktrees and 2 branches, and Delete Topic reads Deleting… until the record and what was ticked are gone. The record goes first; if Tori cannot delete it, nothing is removed. A worktree git refuses to remove opens again on its own, webhooks is deleted. Its worktrees?, with git’s reason, to retry or Keep all.
One workspace
A Topic opens as one workspace. Editor tabs, terminals, panes and search history belong to the Topic, while git, the file watcher and the shell follow whichever member you are in. The title bar reads Topics > webhooks, with the member chips beside it.
- Files, Changes and Pull requests show the members as a strip of chips; pick one to point the panel at it.
- Search always covers the whole Topic, one section per member, and can be narrowed to the members you pick.
- Quick open, breadcrumbs, tabs and menus name the member a file is in, so
the same
src/index.tsin two members can be told apart. - Committing shows a chip per member with staged changes, so one message can go out to all of them, or only the ones you leave ticked. See Commit across a Topic.
- Git commands in the palette each name the member they act on.
Chats in a Topic
A Topic chat starts in the Topic’s own home folder, with every member added to
it, along with each member’s permission rules and instruction file
(CLAUDE.md). The agent is told which Topic it is in and what its members
are: with its first message, after a compaction, and whenever the members
change. Those notes show in the transcript as Tori told this chat about its
Topic.
A Topic chat cannot write in a member’s repository outside the Topic’s own worktrees. When it needs to change a reference, it asks for a worktree, and When a chat needs a worktree, in Settings > Integrations under Topics, decides what happens. It is one setting for every Topic, and a chat already running follows a change at once:
| Setting | What happens |
|---|---|
| Ask me first (the default) | A question in the chat. The worktree is made if you agree |
| Create it | The worktree is made on the Topic’s branch without asking |
| Refuse | The agent is told no, and the member stays a reference |
A chat that is already running picks up members that are added or promoted.
Checkpoints across repositories
A checkpoint taken from a Topic chat covers every worktree member, so one prompt is one snapshot across all of them. A rewind checks every member before it writes anything, so a problem in one stops it before any of them is changed.
Topic worktrees in Spaces
A Topic’s worktrees live in their Topic, and do not show under their repository in Spaces. Turn on Show Topic worktrees in Spaces, in Settings
Integrations, to list them there too. Shown that way, a worktree wears a small Topic tag: hover it for the Topic’s name, click it to open the Topic.
The phone app has a Topics view of its own.