0

I am attempting to customize my PS1, in the following way (I have removed the colours):

PS1='\u@\h:\w$(git_branch)$(useExitCode)\$ '

where

git_branch()
{
    git branch 2> /dev/null | sed -e '/^[^*]/d' -e 's/* \(.*\)/(\1)/'
}

As for exit status, I would like to pick it up before the git_branch function is executed, and use it in useExitCode . How can I do that? The latter function could look like this:

useExitCode()
{
    local exitCode=${1}

    if [[ ${exitCode} == 0 ]]; then
        echo ':)'
    else
        echo ':('
    fi
}

The question is, how can I store the exitcode in PS1 and use it later ?

Something like the following does not work, but gives an idea of the geenral direction:

PS1='exitCode=$?\u@\h:\w$(git_branch)$(useExitCode ${exitCode})\$ '

The above echo's the "exitCode=0" (or =1) part but it is not stored, so it is empty at its invocation "${exitCode}" later.

1

I would use the PROMPT_COMMAND variable for that:

PROMPT_COMMAND='lstatus=$?'
PS1='$(false)$(exit 3)<$lstatus> '

<0> sh -c 'exit 17'
<17> echo $?
17
<0>

From the bash(1) manpage:

PROMPT_COMMAND If set, the value is executed as a command prior to issuing each primary prompt.

1

I do something similar with my prompt, and here is how I go a "get the git branch in my prompt while still showing the last command's exit code" thing:

 parse_git_branch() {
     exit_code=$?
     local stdcolor
     local branchcolor
     local lines
     stdcolor="^[[0;32m"
     if [[ -d ./.git ]] || $( git status > /dev/null 2>&1 ); then
        lines=$(git status -s | wc -l)
        if [[ 0 -eq ${lines} ]]; then
           # Working copy is clean
           branchcolor="^[[1;32m"
        elif git status -s 2> /dev/null | grep -q '^A'; then
           # If we have staged commits waiting, red; else yellow
           branchcolor="^[[1;31m"
        else
           branchcolor="^[[1;33m"
        fi
        git branch 2> /dev/null | sed -e '/^[^*]/d' -e "s/* \(.*\)/ $stdcolor($branchcolor\1$stdcolor)/"
     fi
     return $exit_code
  }
  export PS1='\[\e]0;\u@\h: \w\a\]\[\e[38;5;14m\]\u\[\e[38;5;8m\]@\[\e[38;5;6m\]\h\[\e[38;5;8m\]:\[\e[38;5;10m\]\w'"\$(parse_git_branch) \e[31m\${?##0}\n"'\[\e[$(((($?>0))*31))m\]\$\[\e[0m\] '

The (sanitized) resultant prompt and how it looks while in a git workspace:

me@host:~/src/project (devel)
$ false
me@host:~/src/project (devel)  1
$ true
me@host:~/src/project (devel) 
$

The upshot of all that is that:

  • If I am in a git workspace, my current branch is shown. Green if clean, yellow if dirty, and red if there are staged files waiting for a commit
  • If the last command's exit code was nonzero, it is shown (in red) in the prompt, and I still have access to $?.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.