Shell mode¶
carrier shell is alpha-quality.
It starts your shell inside a PTY and injects shell hooks so carrier can detect command start and end. Each detected command becomes a run grouped under the current session.
Warning
Shell mode is useful for experiments and interactive work. Use carrier run for precise stdout/stderr capture, reliable exit-code handling, and CI-like command records.
When to use it¶
Use shell mode when:
- you want multi-command tracking under a single session
- commands are interactive
- stdout/stderr separation is not important
- convenience matters more than precision
Use carrier run when:
- exit code preservation is critical
- stdout and stderr must be separate
- you need reliable output capture
- you are recording CI-like commands
Supported shells¶
Shell mode is best-effort for:
- zsh
- bash
carrier doctor reports whether the configured shell looks supported.
How it works¶
Architecture:
For zsh, carrier uses preexec and precmd hooks.
After sourcing your .zshrc, carrier disables zsh's warn_create_global option inside the tracked shell. This avoids prompt helper warnings from being printed on every command when prompt functions assign globals.
For bash, carrier starts bash with a generated --rcfile; support is best-effort through DEBUG and PROMPT_COMMAND hooks. Existing PROMPT_COMMAND content is preserved and run before carrier finishes the tracked command.
carrier guards its hook internals so internal carrier internal ... commands and _carrier_* helper functions are not recorded as user commands.
Sessions¶
Every carrier shell invocation creates a shell session. All runs recorded during that shell are linked to the session.
Label a session at start¶
Pass a label as a positional argument or with --label:
View sessions¶
Output includes session ID, start time, label, and duration:
Label a session after starting¶
From inside the tracked shell, $CARRIER_SESSION_ID is set automatically. Omit the ID argument to target the current session:
From outside, pass the session ID explicitly:
Labeling a run with carrier label also propagates the label to the run's session automatically.
Grouped history¶
carrier history shows session runs as a tree:
5 ┬── 2026-05-18 12:01 session: backend-debug
3 ├── failed 1.2s make test
2 └── success 0.4s go vet ./...
1 failed 2.1s make lint
Filter to one session:
Show only session headers:
Attaching to an existing session¶
carrier attach re-opens a session and starts a new PTY shell that records into it:
This is useful when you want to continue a labeled debugging session from a different terminal, or after a disconnect. Runs recorded during the attached shell appear under the same session in history.
What gets recorded¶
Shell mode creates one run per detected command. Shell runs use:
- mode:
shell - status:
running,success, orfailed - command text from the shell hook
- cwd
- Git metadata
- terminal output log path
- session ID
Unlike carrier run, shell mode stores terminal output instead of separate stdout and stderr logs.
TUI applications¶
TUI programs (alternate-screen apps like neovim, lazygit, noteui) run normally inside a carrier shell session — their output appears on screen as usual. Carrier detects the alternate-screen escape sequences (\x1b[?1049h / \x1b[?1049l) and suppresses the enclosed content from the terminal log, because cursor-movement-heavy TUI output cannot be replayed as plain text. When you run carrier show on a run that involved a TUI application, the output section displays (TUI session — terminal output suppressed) instead of replaying the log. Run metadata (command, exit code, duration, etc.) is fully recorded regardless.
Limitations¶
- stdout and stderr may be merged
- prompts and shell plugins can affect detection
- aliases may change displayed commands
- TUI (alternate-screen) output is suppressed from terminal logs and cannot be replayed
- hook internals may behave differently across shell versions
- bash hook behavior can vary when other tools also modify
DEBUGorPROMPT_COMMAND carrier shellis not a drop-in replacement for shell history
Inspect shell runs¶
From another terminal:
Shell runs use terminal_output_path instead of separate stdout/stderr paths.
Show only terminal output:
Ignore noisy commands¶
Configure commands that shell mode should not track:
Interactive full-screen programs are ignored by default because their terminal output is usually noisy.
Choose a shell¶
Leave program empty to use $SHELL:
Set a shell explicitly:
Current recommendation¶
Use carrier run for important records. Treat carrier shell as an experimental convenience layer. When a session matters, label it at start and use carrier attach to return to it.