Omniscio documentation
Browse all documentation
  1. Getting Started13
  2. Sessions & Agents121
  3. Inbox & Notifications65
  4. Projects & Tasks95
  5. Automation & Scheduling82
  6. Knowledge & Memory26
  7. AI Features66
  8. Integrations101
  9. Plugins & Marketplace34
  10. Cloud & Teams57
  11. Settings & Customization62
  12. Account & Billing28
  13. Troubleshooting86
  14. CLI & API Reference24
  15. Legal & Policies4
  16. Uncategorised17

Undo a session action (Ctrl+Z)

Press Ctrl+Z to reverse the last thing you did to a session — pause, snooze, archive, move, rename, close, bookmark — and Ctrl+Y to put it back. The history is a shared 25-step stack, so you can walk back through a burst of actions rather than just the last one. While a text box has focus, Ctrl+Z belongs to that box; the app-level undo fires everywhere else.

What it is

Ctrl+Z is the session list's "put that back". It reverses the last undoable action you took — the row returns to where it was and to the state it was in — and Ctrl+Y re-applies what you just undid.

It is deliberately not a reset, and it is not per-row: it is one history of recent actions in the order you took them.

  • What it covers: pause / unpause, snooze / unsnooze, archive / unarchive, move to project, rename, close, and bookmarking a session. Pausing or archiving a whole selection records one entry that undoes the whole batch.
  • What it does not cover: pinning a session (see session-pinning.md — a failed pin simply reverts), Stop and Restart (relaunching an agent costs real tokens, so it is never on the undo stack), and deleting a project (permanent, confirmed separately — see delete-a-project.md).
  • The history is shared, not session-only. The same stack also holds app-level actions from other surfaces (removing a composer attachment, a recipe edit, a mail-cleanup change), so Ctrl+Z reverses whatever was registered last, whichever screen it came from.

Where to find it

  • Ctrl+Z anywhere in the app — not just the sidebar. Ctrl+Y redoes.
  • The Undo toast, when you have turned it on: it appears right after the action and carries a clickable Undo button with the shortcut hint. The button is the focus-independent path — it works even when a text box has focus and Ctrl+Z would go to that box instead.
  • Settings → Keyboard shortcuts — both keys are listed, rebindable, and the new binding shows up immediately in the toast hint and in the ? cheat-sheet.

The toast is off by default and has its own switches under Settings → Notifications:

Switch Covers Default
Session actions pause, unpause, snooze, move Off
Session archived archive from the row, menu or keyboard Off
Deletions item removals (most cannot be undone) On

Turning them off hides only the toast. Ctrl+Z keeps working either way.

How it behaves

How far back it goes. The history holds your last 25 undoable actions. Take a 26th and the oldest falls off the bottom. Redo works in the same way — but only until you do something new: a fresh action clears the redo chain, exactly like a text editor, so you cannot redo forward past a new decision.

While you are typing, the text box wins. If a text box has focus — a search field, a reply dialog, the chat composer once it holds text — Ctrl+Z undoes your typing there, because that box keeps its own undo. The app-level undo fires only when no text box is claiming the key. The chat composer is the one place that does both: with text in it, Ctrl+Z walks back your typing; once there is no typing left to undo, it falls through to the session-level undo. That is why the toast always carries a clickable Undo button — it is the one path that works regardless of where your cursor is.

Undoing a pause does not restart the agent. Pausing ends the running CLI process; the undo returns the row to ended rather than pretending a live agent came back. The session is exactly as resumable as any other finished one: send it a message and it picks up again. The same honesty applies when the undo is of an archive or a close — the row comes back, the process does not.

Failed undos do not trap you. If the inverse action cannot be carried out, the entry has already been taken off the stack, so your next Ctrl+Z moves on to the action before it rather than retrying the same one forever.

Every open client sees the result. An undone action is applied through the same session writes as the original, so the row moves back on the phone as well as the desktop.

For agents

The stack

One module owns the history: undo-store.ts. MAX_UNDO_HISTORY = 25 is the cap, applied on push ([...undoStack, pair].slice(-MAX_UNDO_HISTORY)); registerUndo(entry, redoEntry?, tag?) pushes a pair and clears redoStack; performUndo() pops before awaiting execute() so a throwing inverse cannot strand the slot and a concurrent call cannot pop twice; performRedo() re-pushes the pair onto the undo stack. Only entries registered with a redo become redoable. A tag allows clearUndoByTag(tag) to drop a producer's entries from both stacks (F008 — the composer's attachment closures capture large PendingImage payloads). 71 files call registerUndo — one shared stack, not one per surface.

Session actions go through the single chokepoint session-action-undo.ts: registerSessionActionUndo({ label, undo, reselect?, toastCategory? }) registers the pair and shows the toast in one call so the two can never drift. The undo method must not itself register an undo (the store lifecycle methods like unpauseSession / unsnoozeSession are registration-free by design — otherwise the undo would re-arm a fresh undo). reselect re-focuses the acted-on row only when it was the active surface. The toast's category defaults to sessionActions; archive paths pass sessionArchived.

Keys and the field arbiter

undoLastAction → Ctrl+Z and redoLastAction → Ctrl+Y are declared in core.keybindings.ts with passthroughInputs: false. That flag is the arbiter: shouldStandDownForInput in useKeyboardShortcuts.ts stands the action down in any editable field, so the focused editor owns Ctrl+Z. The handlers are thin — global-actions.ts calls performUndo() / performRedo().

The composer is the exception, in ComposerInput.tsx: Ctrl+Z/Ctrl+Y go through the shared handleTextUndoRedoKeydown intercept, which does text undo/redo first (React's rendering destroys Chromium's native history) and falls through to performUndo() / performRedo() only when there is no text history left, consuming the key solely if lastUndo / lastRedo is set. lastUndo / lastRedo exist precisely so a composer keydown can ask that question.

Honest reversal

unpauseSession in session-store.ts patches status: 'ended' optimistically (LIVE-ONLY, onFailure: 'plain-restore'), which is what makes the undo of a pause land on ended rather than a fabricated live state. reselect is the only focus side effect — the undo never navigates you anywhere you did not already have open.

Toast defaults

ToastCategory and DEFAULT_TOAST_PREFERENCES live in notifications.ts: sessionActions: false and sessionArchived: false (both off out of the box, group confirmations), deletions: true. The keyboard path is the always-on one — the toast is only a receipt.

Related

Last verified 2026-10-06