Unix Shell
From Shrubbery
Contents |
[edit] Other Pages
- How to generate and use ssh keys.
- Setting up Java classpath using a shell script Classpath using shell.
- sed one liners
- Reading a file line by line with shell
- Finding a property in a Java-style properties file with shell
- Bash Reference Manual
[edit] One liners
[edit] Diff two directories, only show which files are different
diff -rq somedir someotherdir
[edit] Merge stderr into stdout
Use 2>&1, for example:
somecommand 2>&1 > someoutput.log
[edit] Shell Programming
[edit] Start with a shebang!
- Shell scripts should begin with a 'shebang'. Usually #!/bin/sh<tt> or <tt>#!/bin/bash.
- To make the script executable, simply chmod +x myscript
- File extensions don't matter in Linux and Unix. You can name the script 'myscript.sh' or just 'myscript' and it will make no difference, other than the fact that you will have to type the whole file name to execute it.
- Shell scripts must use Unix/Linux-style line feeds! Even under Cygwin this is true. To convert a shell script file to Unix line feed format, use dos2unix.
[edit] Launching a nested shell from a shell script
Nested shells can be really useful for setting up environment variables, PATH, and LD_LIBRARY_PATH in a clean way. You could just source in a shell script that sets environment varaibles, etc, but in the nested shell it is much easier to return to the un-touched environment by typing exit.
#!/bin/bash ... set up environment variables and PATH ... ... exports ... exec $SHELL
[edit] Cygwin compatibility
If you are using Cygwin, you need to do a few extra things to 'path names' and other structures before invoking non-Cygwin commands. ANT is a good example because it is run under Java, which doesn't know about Cygwin paths.
Here is an example of setting ANT_HOME from a shell script:
#!/bin/sh ANT_HOME=/cygdrive/c/java/apache-ant-1.6.5 JAVA_HOME=/cygdrive/c/java/jdk1.5.0_10 PATH=$ANT_HOME/bin:$JAVA_HOME/bin:$PATH ANT_HOME=`cygpath --mixed "$ANT_HOME"` JAVA_HOME=`cygpath --mixed "$JAVA_HOME"` export ANT_HOME export JAVA_HOME
Of course, this won't work on Linux, so it could be made more portable like this:
#!/bin/sh
UNAME=`uname`
case "$UNAME" in
CYGWIN*)
ANT_HOME=/cygdrive/c/java/apache-ant-1.6.5
JAVA_HOME=/cygdrive/c/java/jdk1.5.0_10
;;
*)
ANT_HOME=/opt/apache-ant-1.6.5
JAVA_HOME=/usr/java/jdk1.5.0_10
;;
esac
PATH=$ANT_HOME/bin:$JAVA_HOME/bin:$PATH
case "$UNAME" in
CYGWIN*)
ANT_HOME=`cygpath --mixed "$ANT_HOME"`
JAVA_HOME=`cygpath --mixed "$JAVA_HOME"`
;;
*)
# Nothin' doin on linux.
;;
esac
export ANT_HOME
export JAVA_HOME
Note:
- PATH is not converted. That's because Cygwin uses PATH.
- JAVA_HOME and ANT_HOME are converted 'after' PATH is set because ant doesn't know about Cygwin's path system, but Cygwin bash does.
[edit] Script name and script path
It is often useful to have the name of the currently running script and the path it is located in as shell variables. Here is an example:
#!/bin/sh
SCRIPT_NAME=${0##*/}
SCRIPT_DIR=`dirname $0`
[edit] Full path names
To get the full path name from a relative path name:
RELATIVEPATH=".." ABSPATH=`cd $RELATIVEPATH && pwd`
Note that the 'cd' command inside the back-ticks does not affect the current directory of the running script.
To get the full path of the parent directory of the current script:
#!/bin/sh SCRIPT_DIR=`dirname $0` PARENT_DIR=`cd $SCRIPT_DIR/.. && pwd`
Categories: Linux | Shell

