Bash · 2899 bytes Raw Blame History
1 #!/bin/bash
2
3 # Parrot shell hook - source this in your .bashrc or .zshrc
4
5 # Path to parrot binary - update this if needed
6 PARROT_BIN="parrot"
7
8 # Function to check if parrot binary exists
9 parrot_check() {
10 if ! command -v "$PARROT_BIN" &> /dev/null; then
11 echo "⚠️ Parrot binary not found. Make sure 'parrot' is in your PATH."
12 return 1
13 fi
14 return 0
15 }
16
17 # Function called after each command in bash
18 parrot_prompt_command() {
19 local exit_code=$?
20 local last_cmd=$(history 1 | sed 's/^[ ]*[0-9]*[ ]*//')
21
22 # Only mock if command failed and we have a command
23 if [ $exit_code -ne 0 ] && [ -n "$last_cmd" ] && parrot_check; then
24 # Run parrot in background to avoid blocking shell if PARROT_ASYNC is set
25 if [ "${PARROT_ASYNC:-}" = "true" ]; then
26 "$PARROT_BIN" mock "$last_cmd" "$exit_code" &
27 else
28 "$PARROT_BIN" mock "$last_cmd" "$exit_code"
29 fi
30 fi
31 }
32
33 # Function called before each command in zsh
34 parrot_preexec() {
35 PARROT_LAST_CMD="$1"
36 }
37
38 # Function called after each command in zsh
39 parrot_precmd() {
40 local exit_code=$?
41
42 # Only mock if command failed and we have a command
43 if [ $exit_code -ne 0 ] && [ -n "$PARROT_LAST_CMD" ] && parrot_check; then
44 # Run parrot in background to avoid blocking shell if PARROT_ASYNC is set
45 if [ "${PARROT_ASYNC:-}" = "true" ]; then
46 "$PARROT_BIN" mock "$PARROT_LAST_CMD" "$exit_code" &
47 else
48 "$PARROT_BIN" mock "$PARROT_LAST_CMD" "$exit_code"
49 fi
50 fi
51 }
52
53 # Setup based on shell type (only show messages if not already initialized)
54 if [ -z "$PARROT_INITIALIZED" ]; then
55 if [ -n "$BASH_VERSION" ]; then
56 # Bash setup
57 PROMPT_COMMAND="parrot_prompt_command${PROMPT_COMMAND:+;$PROMPT_COMMAND}"
58 echo "🦜 Parrot is now watching your bash commands..."
59 elif [ -n "$ZSH_VERSION" ]; then
60 # Zsh setup
61 autoload -Uz add-zsh-hook
62 add-zsh-hook preexec parrot_preexec
63 add-zsh-hook precmd parrot_precmd
64 echo "🦜 Parrot is now watching your zsh commands..."
65 else
66 echo "⚠️ Parrot: Unsupported shell. Only bash, zsh, and fish are supported."
67 echo "💡 For fish shell, use parrot-hook.fish instead."
68 fi
69
70 # Show performance tip
71 if [ "${PARROT_ASYNC:-}" != "true" ]; then
72 echo "💡 Tip: Set PARROT_ASYNC=true to prevent terminal hangs on slow networks"
73 fi
74
75 # Mark as initialized for this shell session
76 export PARROT_INITIALIZED=1
77 else
78 # Silent re-initialization (e.g., when sourcing .zshrc again)
79 if [ -n "$BASH_VERSION" ]; then
80 PROMPT_COMMAND="parrot_prompt_command${PROMPT_COMMAND:+;$PROMPT_COMMAND}"
81 elif [ -n "$ZSH_VERSION" ]; then
82 autoload -Uz add-zsh-hook
83 add-zsh-hook preexec parrot_preexec
84 add-zsh-hook precmd parrot_precmd
85 fi
86 fi