Table of Contents

Programming Languages

Shell Script Cheat Sheet



How to execute

# chmod 755 xxxx.sh
# ./xxxx.sh

# bash xxxx.sh

Debug

# bash -x xxxx.sh


Grammar of Shell Script

Comment

Use # to comment out a line.

# This is a bash comment.


Variables

#!/bin/sh
dir=$(pwd)
echo $dir

Valid Variables

FIRSTLETTERS="ABC"
FIRST_THREE_LETTERS="ABC"
firstThreeLetters="ABC"
MY_SHELL="bash"
my_another_shell="my another shell"
My_Shell="My shell"

Invalid Variables

3LETTERS="ABC"   # The first letter is not available for numbers 
first-three-letters="ABC"   # you don't use '-'
first@Thtree@Letters="ABC"

ABC = "ABC"    # you don't use space.

My-SHELL="bash"   # you don't use '-'

Assigning the command output to a variable

You can use $(command) to store the command output in a variable.

$ LIST=$(ls /etc/ssh)

$ echo $LIST
moduli ssh_config ssh_config.d sshd_config sshd_config.d sshd_config.org ssh_host_dsa_key ssh_host_dsa_key.pub ssh_host_ecdsa_key ssh_host_ecdsa_key.pub ssh_host_ed25519_key ssh_host_ed25519_key.pub ssh_host_rsa_key ssh_host_rsa_key.pub ssh_import_id

WHO=$(whoami)
DATE=$(date +%Y%m%d)


Conditionals (-f,-d,=)

[ -d "$dir" ] || mkdir $dir
[ ! -d "$dir" ] && mkdir $dir
[ -z "$END" ] && END=$(date --date '1day ago' +"%Y%m%d"2359)

-d file  : True if file exists and is a directory.
-f file  : True if file exists and is a regular file.
-z arg   : True if argument is null

string1 = string2  : True if string1 and string2 are equal.
string == pattern  : True if string matches pattern.
string != pattern  : True if string does not match pattern.

A -eq B    :  A is equal  B
A -ne B    :  A is not equal  B
A -gt B    :  A is grater than  B
A -ge B    :  A is grate equal  B
A -lt B    :  A is less than  B
A -le B    :  A is little equal  B

#!/bin/sh

test -f  /tmp/tmp.txt
if [ "$?" -ne "0" ]; then
    echo "ERR : "
else
    echo "SUCCESS : "
fi

#!/bin/sh

if [ -z $1 ]; then
    echo "Error:  argument is null"
    exit 1
fi

test -f $FILE || exit 1

if cp from to; then
  echo "copy success"
else
  echo "copy failed"
fi

if ! cp from to; then
  echo "copy failed"
fi


Conditionals (if,case)

if statements

if [ "$?" -ne 0 ] ; then
   echo "ERROR : XXXXXX."
   exit 1
fi

if [ "${USER}" != "root" ] ; then
   echo "ERROR : Change root user."
   exit 1
fi

if [ -f /etc/sysconfig/httpd ]; then
        . /etc/sysconfig/httpd
fi

if [ ! -d ${DIR} ]; then
    mkdir -p ${DIR}
fi

if [ "$VERV_FLAG" == "true" ] ; then
    ECHO="on"
    SSHVERV=""
    BASHVERV=""
elif [ "$DEBUG_FLAG" == "true" ] ; then
    ECHO="on"
    SSHVERV="-v"
    BASHVERV="-x"
else
    SSHVERV="-q"
    BASHVERV=""
fi

and, or
-a and
-o or

if test xxx -a xxx; then
  echo "aaa"
fi

if [ "$?" -eq 0 -a "$a" = 1 ]; then

if test "$?" -eq 0 -a "$a" = 1 ; then

case statements

case "$VAR" in
  [qQ] )
        echo "Quit"
        ;;
  [yY]es | "YES" )
        echo "Yes"
        ;;
  [nN]o | "NO" )
        echo "No"
        ;;
  *) 
      echo "etc"
        ;;
esac


Loops (for,while,until)

for statements

for host in $(cat /tmp/hostlist.txt)
do
    scp tmp.sh ${host}:/tmp
    ssh -n ${host} "hostname;sudo su - -c '/tmp/tmp.sh'"
done

#!/bin/sh

FLAG=0

for i in aaa bbb
do
   echo  $i
   if [ "$?" -ne 0 ] ; then
      FLAG=1
      logger "ERR :  $i"
   fi
done

exit $FLAG

H="server1 server2"
date;for i in $H ; do echo "# $i"; echo $i ; done


while statements

while read i
do
    echo ${i} | awk '{ print $1 }' 
    HOST=$(echo ${i} | awk '{ print $1 }' )
done < /tmp/hostlist.txt

#!/bin/sh

NUM=1

while [ "${NUM}" -le 5 ]
do
    echo "${NUM}"
    NUM=$(( ${NUM} + 1 ))
    sleep 1
done

#!/bin/sh

FILE="test.txt"

cat $FILE |grep XXX | while read i
do
  echo $i
done

while : ; do date; /usr/sbin/ntpq -p ; df -h ; sleep 1 ; clear ; done


argument

#!/bin/sh
#./test.sh 192.168.0.10 test-server

IP=$(echo $1)
HOST=$(echo $2)
echo "$IP $HOST"

echo $0
echo $@
echo $#

DIR=$(dirname ${0})
echo $DIR

$0 : shellname
$1 : argument1
$2 : argument2

$@ : all argument      =  arg1  arg2   arg3  ....
$# : argument numbers

Application example

~]# ./test.sh 192.168.0.10 test-server
192.168.0.10 test-server
./test.sh
192.168.0.10 test-server
.
~]# /tmp/test.sh 192.168.0.10 test-server
192.168.0.10 test-server
/tmp/test.sh
192.168.0.10 test-server
/tmp
~]#


Function

#!/bin/sh

COMMAND1 () {
    echo "$1"
}

COMMAND1 192.168.0.10

#!/bin/bash

log() {
    local level="$1"
    shift
    echo "$(date '+%Y-%m-%d %H:%M:%S') [$level] $*"
}

log INFO "Script started"
log DEBUG "Processing file: $filename"
log ERROR "Failed to connect to the database"


Here Dcoument

#!/bin/sh

COMMAND1 () {
    echo "$1"
}

cat <<MENU
***************************************************************
TEST
---------------------------------------------------------------
   1) COMMAND1
   q) quit
***************************************************************
MENU

echo -n -e "\t >"
read NUM
case ${NUM} in
  1) echo "COMMAND1"
    COMMAND1 $IP
    ;;
  q|Q) echo "quit"
     exit ;;
  *) echo "exit : no selection is missed."
     exit
     ;;
esac

#!/bin/sh

cat << EOT > tmp.txt
  test1
  test2
EOT


Array

#!/bin/bash

arrays=(
"test.sh arg1"
"test2.sh arg1 arg2"
"test3.sh"
)
arrays+=("test4.sh arg1")

for array in "${arrays[@]}"
do
     "${array}"
done

#!/bin/bash

arrays=(
"aaa 111"
"bbb 222 333"
"ccc"
)

for array in "${arrays[@]}"
do
    echo "${array}"
    for hoge in "${array}"
    do
        echo "${hoge}"
    done
done


Calc(expr)

i=2
v1=$(( (i + 1) * 5 ))    #recommend
v2=$(expr \( $i + 1 \) \* 5)




Tips

Idempotency

# /usr/bin/id user01 > /dev/null 2>&1  || echo "useradd user01"
# /usr/bin/id user01 > /dev/null 2>&1  || /usr/sbin/useradd user01

# /usr/bin/id user01 > /dev/null 2>&1  && echo "userdel user01"
# /usr/bin/id user01 > /dev/null 2>&1  && /usr/sbin/userdel -r user01

# command 1>/dev/null 2>/dev/null

get the row

# cat test.txt
1
2
3
4
5

# sed -n '2p' test.txt
2

# sed -n '$p' test.txt
5

# sed -e '1,4d' test.txt
5

# sed -e '1,3d' test.txt
4
5

# sed -e '3,$d' test.txt
1
2

Delete the line of line breaks only

# cat test.txt
1
2

4
5
#sed '/^ *$/d' test.txt
1
2
4
5


get the column

Operation Command
1st column awk '{ print $1 }' FILE
1,4 column awk '{ print $1 $4 }' FILE
2 column , “:” is filed sepalater awk -F: '{ print $2 }'

#echo "1 2 3 4 5" | awk '{ print $1,$3 }'
1 3
#

#echo "1 2 3 4 5" | awk '{ print $1","$3 }'
1,3
#

#echo "1 2 3 4 5" | awk '{ print $NF }'
5
#

#echo "1 2 3 4 5 6 7 8" | awk '{ {for(i=2;i<NF;i++)printf("%s ",$i) }print($NF) }'
2 3 4 5 6 7 8
#

#echo "1 2 3 4 5" | awk '{print $1 "        " $4 }'
1        4
#

#echo "1 2 3 4 5" | awk '{print $1 "\t" $4 }'
1       4
#

#echo "1 2 : 3 4 : 5" | awk -F: '{ print $2 }'
 3 4
#


mail

cat  test.txt | mail -s "TITLE" test@example.com

#!/bin/bash

mailaddr="user1@example.com, user2@example.com"
cat <<EOM | mail -s "$(hostname): TEST" $mailaddr
Dear testuser

This is test mail


$(date)

-----------------------
$(cat /tmp/test.txt)

EOM


Database

MySQL

mysql -u root -pPASS << EOF
use mysql;
show tables;
EOF


Change pre tag

sed -e 's/\&/\&amp;/g' -e 's/>/\&gt;/g' -e 's/</\&lt;/g' -e 's/"/\&quot;/g' -e "s/'/\&\#039;/g"  sample.txt > sample.txt

-------------------------
<  :  &lt;
>  :  &gt;
&  :  &amp;
"  :  &quot
'  :  &#039;




Sample




References