20

I use a specific "PS1" prompt that I like. I share a few logins with other other people on a few different servers. I was wondering if there was a way to specify in my local bash profile a remote prompt, or any other way other then copy and pasting each time I remote in.

11 Answers 11

18

Upload a file on each remote machine, say ~/.my_custom_bashrc, with your custom bash configuration, (in this case PS1=...) then launch ssh with:

ssh user@host -t "bash --rcfile ~/.my_custom_bashrc -i"

You can easily use a bash function as wrapper for readability.

1
  • There's an answer, currently way at the bottom, that has an elegant, no-file-upload way to just cat together system bashrc and current-shell-variables... no file uploads, no altering system files. Very clean. superuser.com/a/1542498/539101
    – Ajax
    Jul 7 at 6:30
12

If you just want to send the PS1 variable, and it doesn't contain a ' (single quote), try:

ssh targethost -t "PS1='$PS1'; exec bash"

The local .bashrc may well overwrite PS1 though (thanks to Dennis Williamson for pointing this out).

There are ways to transmit environment variables over ssh, but they're typically disabled in the server configuration. If the PermitUserEnvironment directive is enabled in the server configuration and each user has their own key pair (yeah, you might not be so lucky), you can add environment="PS1=…" to the line in ~/.ssh/authorized_keys corresponding to your key.

If you'd like to keep your own configuration on a shared user account, you can create your own configuration file directory and set the HOME environment variable to point to that directory.

ssh targethost mkdir mrstatic.home
scp .bashrc targethost:mrstatic.home/

Create symbolic links in the mrstatic.home directory pointing back to the corresponding entry in the parent directory when you want to share a file with the other users.

Then, log in with

ssh targethost -t 'HOME=~/mrstatic.home; exec bash'`

If you're willing to modify the remote .profile (or other initialisation file), you can probably automate your settings. Many sites allow LC_* environment variables through (normally they are used for locale settings). If both these conditions are met, you can set a variable that isn't actually used for locales, say LC_USER, on the client side, and test it in the server .profile.

(Of course shared accounts are a bad idea, but I realize you may not be in a position to change that situation.)

3

Put your PS1 prompt in ~/.ssh/environment and ssh session will carry it to every host you login. It works for me with openssh 4.3p2 .

1
  • 1
    This only works if the server's configuration has enabled PermitUserEnvironment, which is off by default.
    – Flimm
    Jul 3, 2013 at 16:44
3
ssh -t user@host "remote='$PS1' bash -i"

Then, at the prompt:

PS1=$remote
3
  • 1
    A sophisticated bash prompt is likely to break if it's not quoted (coming from you, I'm surprised). And why the extra command, and not just "PS1='$PS1' bash -i" (and why not exec, too)? Dec 11, 2010 at 23:35
  • 1
    @Gilles: Missing quoting: sloppiness. Extra command: it wouldn't be unusual for PS1 to be overwritten during shell startup. No exec: during testing on my system it didn't seem to make any difference - no extra process. Dec 12, 2010 at 2:19
  • 1
    Oh, yes, that's a good point, the local .bashrc is likely to overwrite PS1. Dec 12, 2010 at 14:11
1

you can specify environment variables on the client side and if the ssh-server allows it (check man sshd-config), these variables are copied to the session when you log into the machine.

so, you would have to configure the .bashrc on the server to check an existing PS1 (or whatever variable) and only set PS1 if it is not set already.

or, which make things simpler, you bundle your settings into a function .. and deploy that function either as a special file your source on demand (source joes_bashrc) or directly to the .bashrc. having your own file seems a bit more robust. the other folks might use your settings but are not forced to do so.

3
  • export PS1="${PS1:-$my_default_PS1}" - only set if PS1 is empty
    – Ajax
    Jul 7 at 6:13
  • export PS1="${PS1:+$new_prefix $PS1 $new_suffix}" - only build new string if PS1 is already set, and use current PS1 value in new result.
    – Ajax
    Jul 7 at 6:15
  • If you're running over ssh, will want to escape the \$PS1 to read the value on the server. You could get dirty w/ sed or whatever else you want inside the string. export PS1=\${PS1:+ \$(alter_server_ps1 "\$PS1") }
    – Ajax
    Jul 7 at 6:18
1

Do not share logins. SSH as yourself, then do sudo -su shareduser (-s means "shell").

Make sudo keep your home directory:

Defaults env_keep += "HOME"
1
  • When I get promoted I will try and enact that policy but for now I am stuck with this. Dec 11, 2010 at 20:30
1

If you wanna do it without needing an extra scp you can do something like this:

ssh -t srvname ' cp ~/.bashrc ~/.bashrc.n &>/dev/null ; echo "LS_COLORS=\"no=00:fi=00:ETC:ETC:ETC\";" >> ~/.bashrc.n ; echo "export LS_COLORS" >> ~/.bashrc.n ; echo "alias ls=\"ls --color=auto\";" >> ~/.bashrc.n ; exec bash --rcfile ~/.bashrc.n'

That'll generate a .bashrc.n that's based on the servers bashrc but with your overrides.

2
  • This is why some people are afraid of terminals.
    – user111228
    Nov 11, 2012 at 20:57
  • just fyi... echo is perfectly happy w/ multiline strings. Stackoverflow comments, however, don't support them but you can do: echo "$(< ~/.bashrc) <newline>THING='blah'<newline>" > ~/.bashrc.n
    – Ajax
    Jul 7 at 6:11
1

To restore arbitrary environment variables from your client on the server use the following bash command to connect to your ssh-server. In The following example we restore PS1 and PS2.
If you want to send more variables to the server simply add their names without a $ after PS2.

ssh -t user@server "exec bash --rcfile <(cat /etc/bash.bashrc ~/.bashrc 2> /dev/null; printf '%s\n' $(printf %q "$(declare -p PS1 PS2)"))"

This command sets the given variables (here PS1 and PS2) after the original rc-files from the server were sourced (you may have to adapt this list, for instance by adding ~/.profile). Therefore you end up with your usual environment from the server (if the default shell on the server is bash) and the given variables from the client (these may overwrite variables set by server's rc-files).

  • No scp or temporary files needed.
  • No restrictions on the content of the variables to be pushed.
  • No special requirements on the ssh server settings.
1
  • This is a really, really good way to solve this problem... cat the existing files together, then use printf to print current shell variables into assignment statements. Clever!
    – Ajax
    Jul 7 at 6:24
0

The easiest way is IMHO :

ssh user@server 'PROMPT_COMMAND=export PS1="changeme $" bash -li;'
1
  • I’m not sure that works; it seems to be missing a layer of quotes.  Even if it did, setting PROMPT_COMMAND (which executes every time the shell issues a prompt) seems to be a very heavy-handed way of solving this problem.  And, since it’s somewhat arcane, any answer that suggests it really should have an explanation of how it works. Mar 19, 2019 at 17:38
0

If you’re willing to intrude imperceptibly on your colleagues, and you can trust them not to interfere with your preference, then I suggest a combination of cYrus’s answer, akira’s answer and Dennis Williamson’s answer.

  1. On each server, edit ~/.bashrc and add
    if [ "$Unf" = 1 ]                       # Special code for Unfundednut
    then
        PS1="(your desired prompt)"
        (any other customizations you want)
    fi
    at the end.  While your colleagues “would not appreciate [you] writing over the base profile”, they won’t be aware of this unless they go looking for it.
  2. When you login to a remote server, do
    ssh -t user@host "Unf=1 bash -i"
    While you will probably want to put that into an alias or shell function in your local account, it is short enough — shorter than any of the other answers — that you could easily just type it manually.

I believe that this is fairly clear, but:  the ssh command causes the Unf variable to be set on the remote server when you log into it.  That will invoke your code in the remote .bashrc, which will put your customization(s) into effect.  Since you put your code at the end of .bashrc, it will override the general settings earlier in the file.

Disclosure: I have not tested this.

-2

You could do stuff like mounting your home over sshfs/nfs, but the easiest solution is to scp your bashrc across to the new machine. This also brings aliases and stuff.

3
  • As I stated in my question I share these logins with other people. I am quite sure they would not appreciate me writing over the base profile. Dec 11, 2010 at 19:19
  • 1
    Mounting $HOME over NFS is insane. Just sayin'. Dec 11, 2010 at 20:35
  • lol, mounting user HOME over NFS or other shared drive technology is very common if you want to have a home directory that comes with you to all machines...
    – Ajax
    Jul 7 at 6:26

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.