Bash mode (! commands) runs non-interactive shells, breaking history, oh-my-zsh, and other interactive shell features

Resolved 💬 2 comments Opened Apr 1, 2026 by cnavarro165 Closed Apr 1, 2026

Summary

Claude Code's inline bash mode (! <command>) executes commands in a non-interactive, non-login shell, which breaks a wide range of shell features that users rely on daily. This makes the bash mode feel unreliable compared to just opening a terminal.

What Breaks

Shell History

Running ! history or any history-dependent command fails:

omz_history:fc:13: no such event: 1

Root cause: HISTFILE is empty and SAVEHIST=0 in the shell spawned by Claude Code. The history builtin (and oh-my-zsh's omz_history wrapper) depends on fc, which requires a populated history file. With no history loaded, even fc -l 1 fails because event 1 doesn't exist.

oh-my-zsh / zsh Interactive Features

  • hgrep (and similar history-search aliases that wrap fc) silently fail or error
  • Functions that check [[ -o interactive ]] to conditionally set up state won't initialize
  • Some prompt-related functions and completions break

Environment Variables Set Only for Interactive Shells

  • HISTFILE, HISTSIZE, SAVEHIST — not set to user values
  • Any exports in .zshrc guarded by interactivity checks are skipped

Shell Snapshot Workaround Has Limits

Claude Code does create shell snapshots (e.g. ~/.claude/shell-snapshots/snapshot-zsh-*.sh) that capture functions and aliases from the user's environment. This helps — be, custom functions, etc. do work. But it doesn't solve stateful or interactive-only features because each ! command still runs in a fresh, isolated, non-interactive shell.

Expected Behavior

Ideally, bash mode commands should run in an environment that matches the user's interactive shell as closely as possible — same HISTFILE, same shell options, same initialization path. At minimum:

  1. Load the user's actual history file so history, fc, and history-search tools work
  2. Respect HISTFILE / HISTSIZE / SAVEHIST from the user's shell config
  3. Optionally launch the shell as interactive (zsh -i) so that oh-my-zsh and similar frameworks initialize fully, matching what the user experiences in their own terminal

Environment

  • OS: macOS (Darwin 25.3.0)
  • Shell: zsh with oh-my-zsh
  • Claude Code: latest
  • History file: ~/.zsh_history (3,000+ entries, works fine in normal terminals)

Workaround

Users can search history directly from the file:

! grep "pattern" ~/.zsh_history

But this shouldn't be necessary — the bash mode should just work like a normal shell.

View original on GitHub ↗

This issue has 2 comments on GitHub. Read the full discussion on GitHub ↗