# bash setup



## ph0enix (Mar 7, 2009)

I have some users setup with bash as their default shell.  I placed a .bashrc in their home directories but it's not being read when they first login.  If they execute bash again, .bashrc gets processed correctly.  The funny thing is, that if I change root's default shell to bash, his .bashrc gets processed during login.  What gives?

Thanks!

J.


----------



## DutchDaemon (Mar 7, 2009)

bash(1):

[font="Courier New"]When an interactive shell _that is not a login shell_  is  started,  bash reads  and executes commands from ~/.bashrc, if that file exists.[/font]

See *FILES* for other options.


----------



## ph0enix (Mar 7, 2009)

So is there a way to have it process .bashrc at login?  It's doing it for root - just not any other users.


----------



## DutchDaemon (Mar 7, 2009)

Why not use ~/.bash_profile as suggested? Or /etc/profile if you want identical settings for everybody using bash. By the way: are you su'ing to root? Then it's probably treated as an interactive shell (honouring .bashrc).


----------



## ph0enix (Mar 7, 2009)

Ah, that did the trick (.bash_profile).  Yes, I was su'ing to root.  You're probably right about it being an interactive shell.


----------



## keramida@ (Mar 8, 2009)

ph0enix said:
			
		

> Ah, that did the trick (.bash_profile).  Yes, I was su'ing to root.  You're probably right about it being an interactive shell.



Of course it is 

A trick that I use to have all my settings in both .bash_profile and .bashrc is to write something like this in my .bash_profile file:


```
# Startup file for login instances of the bash(1) shell.

# First of all, run a .bashrc file if it exists.
test -f ~/.bashrc && . ~/.bashrc

# The following section should be pretty minimal, if present at all.
mesg y >/dev/null 2>&1
/usr/bin/true
```

This way I can keep all my settings in .bashrc.

One important detail when your .bash_profile is set up like this is that .bashrc must be idempotent, so that you can launch multiple instances of bash without odd effects.  Idempotency in this case means that you should be careful about constructs like:


```
PATH="$PATH:/foo"
```

If this runs in a login shell when PATH="/bin:/usr/bin" and then you launch a subshell within the login shell, your PATH will end up being "/bin:/usr/bin:/foo:/foo", with "/foo" duplicated.

Bash includes advanced features like arrays which you can use to write functions like addpath().  This way you can craft a custom .bashrc file that can be loaded multiple times and avoid the duplicate path entry problem.  You can even write elaborate checks about when, why and how a path entry is added.

Another nice trick to keep in bash notes when you are constructing your .bashrc file in a way that makes it re-loadable is to use conditional variable expansion and assignment as in:


```
FOO="${FOO:-value}"
```

When FOO is already defined the construct ${FOO:-value} expands to its current value.  When FOO is undefined, it expands to 'value', so this way you can keep environment settings from any parent process of the shell, but override them with your own defaults if they are unset.

I use this, for example, to set BLOCKSIZE, CVSROOT, and TMPDIR in my .bashrc:


```
BLOCKSIZE="${BLOCKSIZE:-1024}"
CVSROOT="${CVSROOT:-/home/ncvs}""
TMPDIR="${TMPDIR:-/tmp}"
```


----------



## Mel_Flynn (Mar 8, 2009)

I only set PATH when it's unset and actually hate it that /usr/share/skel doesn't do so. It negates /etc/login.conf, which is so convenient for shell-independent environment variables.


----------

