3

I am following https://lifehacker.com/add-a-handy-separator-between-commands-in-your-terminal-5840450 to create a nice separator between commands in the terminal in Linux. Specifically, CentOS 8.

I am trying to modify the script to output the username of the user who ran the command.

Here is what I came up with.

# Fill with minuses
# (this is recalculated every time the prompt is shown in function prompt_command):
fill="--- "

reset_style='\[\033[00m\]'
if [ -z "$VIM" ];
then status_style=$reset_style'\[\033[0;90m\]' # gray color; use 0;37m for lighter color
else status_style=$reset_style'\[\033[0;90;107m\]'
fi
prompt_style=$reset_style
command_style=$reset_style'\[\033[1;29m\]' # bold black
# Prompt variable:

OLD_PS1="$PS1"
PS1="$status_style"'$fill $USER \t\n'"$prompt_style$OLD_PS1$command_style"

# Reset color for command output
# (this one is invoked every time before a command is executed):
trap 'echo -ne "\e[0m"' DEBUG


function prompt_command {

    # create a $fill of all screen width minus the time string and a space and USER and a space:
    let fillsize=${COLUMNS}-10-${#USER}
    fill=""
    while [ "$fillsize" -gt "0" ]
    do
        fill="-${fill}" # fill with underscores to work on 
        let fillsize=${fillsize}-1
    done

    # If this is an xterm set the title to user@host:dir
    case "$TERM" in
    xterm*|rxvt*)
        bname=`basename "${PWD/$HOME/~}"`
        echo -ne "\033]0;${bname}: ${USER}@${HOSTNAME}: ${PWD/$HOME/~}\007"
        ;;
    *)
        ;;
    esac

}
PROMPT_COMMAND=prompt_command

Line 15 added " " and $USER to what is generated.

Line 25 changed to include an extra space and the length of the variable $USER

It looks just like I want it to.

Terminal Screenshot

But, I would like to update the code to output if I ran a command as sudo or not. Ideally, it would change the name to root or whatever the root user name is.

I have tried several things, mainly I tried using whoami but this always returns my username not root. If I run sudo whoami I get root but not from the script. I also tried EUID No dice.

At this point, I have left the code in working condition with the $USER reference but I am willing to change it to whatever it needs to be.

Solution provided by u/pLumo

Solution Limitations:

  • There are cases not covered, for example sudo --user=some_user .... I think it's fairly easy to further enhance the awk script.
  • As it relies on the history, it won't work with commands you do not have in history, e.g. when using HISTCONTROL=ignoreboth and issue a command with a space in front.
# Fill with minuses
# (this is recalculated every time the prompt is shown in function prompt_command):
fill="--- "

reset_style='\[\033[00m\]'
if [ -z "$VIM" ];
then status_style=$reset_style'\[\033[0;90m\]' # gray color; use 0;37m for lighter color
else status_style=$reset_style'\[\033[0;90;107m\]'
fi
prompt_style=$reset_style
command_style=$reset_style'\[\033[1;29m\]' # bold black
# Prompt variable:

OLD_PS1="$PS1"
PS1="$status_style"'$fill $name \t\n'"$prompt_style$OLD_PS1$command_style"

# Reset color for command output
# (this one is invoked every time before a command is executed):
trap 'echo -ne "\e[0m"' DEBUG


function prompt_command {

    # create a $fill of all screen width minus the time string and a space and USER and a space:
    name=$(fc -l -1 | awk -v u="$USER" '{if ($2=="sudo") { if ($3=="-u") u=$4; else u="root"; }; printf "%s",u}')
    let fillsize=${COLUMNS}-10-${#name}
    fill=""
    while [ "$fillsize" -gt "0" ]
    do
        fill="-${fill}" # fill with underscores to work on 
        let fillsize=${fillsize}-1
    done

    # If this is an xterm set the title to user@host:dir
    case "$TERM" in
    xterm*|rxvt*)
        bname=`basename "${PWD/$HOME/~}"`
        echo -ne "\033]0;${bname}: ${USER}@${HOSTNAME}: ${PWD/$HOME/~}\007"
        ;;
    *)
        ;;
    esac

}
PROMPT_COMMAND=prompt_command

Terminal Output - Solution

  • (classic example) -- on your system does /bin/id -u yield different results with/without sudo? – forest Jun 2 at 20:15
  • Yes, it does. Running /bin/id -u returns 1000 my id. Running sudo /bin/id -u returns 0 the root id. – Alejandro Colon Jun 2 at 22:47
  • OK, thought so; I'll update the answer section. Please mark as up-vote / accepted as you can. – forest Jun 2 at 22:53
  • If it works I will mark it as the solution. But, I might have already tried it previously and it did not work. – Alejandro Colon Jun 2 at 22:55
  • As I thought. This does not work. If I run it from the CLI then it outputs as I stated. The code I am using is being run by .bashrc not by me in the CLI. – Alejandro Colon Jun 2 at 22:58
1

From prompt_command you don't know which user ran the last command. prompt_command is always run by your normal users session.

As a workaround. you can read and parse the history.

E.g.: Using fc -l -1 to print the last command, awk ... to parse it.


In line #15 change $USER to $name

In line #23 , add this:

name=$(fc -l -1 | awk -v u="$USER" '{if ($2=="sudo") { if ($3=="-u") u=$4; else u="root"; }; printf "%s",u}')

In line #25, change ${#USER} to ${#name}


This will print root for sudo some command and some_user for sudo -u some_user some command.

But please note, that this solution has some limitations:

  • There are cases not covered, for example sudo --user=some_user .... I think it's fairly easy to further enhance the awk script.
  • As it relies on the history, it won't work with commands you do not have in history, e.g. when using HISTCONTROL=ignoreboth and issue a command with a space in front.
| improve this answer | |
  • I will try this and report back. Just to clarify, this will return my user name when I am not using sudo and return root when using sudo? – Alejandro Colon Jun 2 at 22:48
  • I tried it and it seems to be working. Thank you so much. Any ideas on how to pull the other user names when using sudo -u some_user some command – Alejandro Colon Jun 2 at 23:02
  • Added that. It's still not failsafe, e.g. this is not covered --user=user. I think it's fairly easy to further enhance the awk script. – pLumo Jun 3 at 6:43
  • Thank you so much. You further clarification was what I needed as I am a novice and I did not understand what the fc was doing. I will try and modify the awk code to extend it further. – Alejandro Colon Jun 3 at 15:24
0

print the effective user-id (euid)

/bin/id -u
| improve this answer | |

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.