ZSH prompt

06 February 2012 || tags: GIT ZSH

Here is my ZSH config to achieve two aims :

  1. Clearly separates the results of commands :
screenshot
  1. Integrate GIT status in the prompt when working in a GIT repository :
screenshot

To do that, I have added to my .zshrc the following lines :

 1 autoload -Uz vcs_info
 2 #zstyle ':vcs_info:*' stagedstr 'Staged'
 3 #zstyle ':vcs_info:*' unstagedstr 'Unstaged'
 4 zstyle ':vcs_info:git*' formats "%{$fg_bold[blue]%}[%s] %{$fg_bold[green]%}(%b)%{$reset_color%} %{$fg[red]%}%u %{$fg[yellow]%}%c"
 5 zstyle ':vcs_info:*' check-for-changes true
 6 zstyle ':vcs_info:*' enable git
 7 precmd() {
 8   vcs_info
 9 
10   local STATUS="`git status 2>&1`"
11   if [[ "$STATUS" == *'Not a git repository'* ]] then
12     GITINFO=""
13   else
14     GITINFO="------ ${vcs_info_msg_0_}"$'\n'
15   fi
16 }
17 setopt prompt_subst
18 
19 export PS1=$'\n'"%{$fg[green]%}"-----------------------------------------------------------------------$'\n''${GITINFO}'"%{$fg[green]%}""------ [%~] %*"$'\n'-----------------------------------------------------------------------"%{$reset_color%}"$'\n\n\n'"%{$fg_bold[green]%}%n@%m:%#%{$reset_color%} "

More information about vcs_info can be found at http://zsh.sourceforge.net/Doc/Release/User-Contributions.html#Version-Control-Information

1 autoload -Uz vcs_info loads the vcs_info module.
2 
3 zstyle ':vcs_info:git*' formats "%{$fg_bold[blue]%}[%s] %{$fg_bold[green]%}(%b)%{$reset_color%} %{$fg[red]%}%u %{$fg[yellow]%}%c" defines the output format :
  • %s : the VCS used (= git)
  • %b : the current branch
  • %u : unstaged status (= there are unstaged files in the repository)
  • %c : staged status (= there are staged files in the repository)

If you want to change the default U and S for unstaged and staged, you can use :

1 zstyle ':vcs_info:*' stagedstr 'Staged'
2 zstyle ':vcs_info:*' unstagedstr 'Unstaged'
  • zstyle ':vcs_info:*' check-for-changes true to monitor changes.
  • zstyle ':vcs_info:*' enable git to enable it for GIT VCS.

I want to show the GIT status only inside a GIT repository, not in a ordinary directory. This is done in the precmd() by testing the STATUS variable which contains the GIT STATUS output :

1 precmd() {
2 vcs_info
3 local STATUS="`git status 2>&1`"
4 if [[ "$STATUS" == *'Not a git repository'* ]] then
5   GITINFO=""
6 else
7   GITINFO="------ ${vcs_info_msg_0_}"$'n'
8 fi
9 }

The prompt itself is build inside PS1 :

1 export PS1=$'n'"%{$fg[green]%}"-----------------------------------------------------------------------$'n''${GITINFO}'"%{$fg[green]%}""------ [%~] %*"$'n'-----------------------------------------------------------------------"%{$reset_color%}"$'nnn'"%{$fg_bold[green]%}%n@%m:%#%{$reset_color%} "

Note : you have to make a first commit before the staged and unstaged status become active.