Bourne-Again Shell (bash) for interactive use and scripting

The Bourne-Again Shell (bash) is ubiquitous in the Linux world. It is excellent for both interactive use and scripting. However we don't suggest you use bash for complex scripting unless you have to. Most of the time you should use a much more powerful scripting language such as Perl, Python or Ruby that has many built-in functions and modules and is very easy to debug. Still you can write some bash scripts to increase your productivity. Following is a collection of useful examples. You can also download the complete bash rc file that contains all the aliases and functions discussed below.

Common aliases

Following are aliases that you can use to reduce the number of key strokes for commonly used commands.

alias ..='cd ..'
alias ...='cd ../..'
alias ....='cd ../../..'
alias p=pushd
alias m=more
alias h=history

Useful bash functions

In addition to aliases, functions can also increase your productivity. Because they have access to all the bash's scripting capabilities, they are much more versatile than aliases.

Many functions can be implemented without using any additional scripting languages. Since you can just define them in your $HOME/.bashrc file, you don't need to create many small files that scatter around your directories. Even if you use some other scripting languages, you can still put them in one directory and then create simple bash functions as wrappers for those scripts.

When writing bash functions, please keep the Bash Reference Manual ready. Following are some useful examples.

Find a process (psx)

You know the ps command can list all the processes that the current shell session creates. More often you want to search all the processes and you will almost do something like ps auxwww |grep <myprocess> | more repeatedly. You can lessen the chore with the following handy function:

# find a process quickly
function psx()
{
  ps auxwww | grep $1 | more
}
 

Check whether a name exists as a function or an alias (check)

To check whether a name exists as a function or an alias, you need to run typeset -f <name>. If it doesn't show any function definition for the given name, then you need to run alias <name>. You can define a simple function to do it:

function check()
{
  typeset -f $1
  if [[ $? == 0 ]]
  then
   return 0;
  fi
  alias $1
}

Function to search a string in source files (findx)

You may often need to search a string in some source files (e.g., *.cc for C++ files ) under a certain directory recursively. Typically you will type something like the following:

find . -name "*.c" |xargs grep estrdup |more

However this has just too many keystrokes. What you can do is to define a function that accepts 1-3 parameters for doing the search.

If there is only one parameter which is the string to search, then it searches all the .h in the current directory recursively for that.

If there are two parameters, then the first parameter provides the suffix of the files to search and the second one provides the string to search.

In case of three parameters, then the first parameter is the directory to start search, the second the suffix of the files to search from and the third the string to search.

Please note that depending on the number of parameters in the function call, parameters at the same position don't have the same meaning. This is to mimic the usual flow when you work with find and xargs.

Or you can think of it another way. The string to search is always the last parameter. Then file suffix comes before it.

The following shows how the findx function is defined:

# findx : find <dir> <suffix> <search_string>
findx()
{
  if [ -n "$3" ]
  then
   find "$1" -name "*.$2" | xargs grep "$3" | more
  elif [ -n "$2" ]
  then
   find . -name "*.$1" | xargs grep "$2" | more
  elif [ -n "$1" ]
  then
   find . -name "*.h" | xargs grep "$1" | more
  else
   echo "Usage:"
   echo " findx <string>"
   echo " findx <file suffix> <string>"
   echo " findx <dir> <file suffix> <string>"
  fi
}
 
 

Return human-readable string from a Unix timestamp

Oftentimes you need to know quickly what time it is given a Unix timestamp and the time should be in a human-readable format.

The standard date command doesn't help much because different Unix variants accept different options. A Perl one-liner really shines in this case. Following we define two functions. One function, datex, returns the local time. The other function, dategmt returns the time in GMT format.

function datex()
{
  perl -le "print scalar localtime $1"
}
 
function dategmt()
{
  perl -le "print scalar gmtime $1"
}
 

Back to articles on development