Linux基礎 #8 - バッシュスクリプト

Last Edited: 1/12/2025

このブログ記事では、バッシュスクリプトの基礎を紹介します。

DevOps

これまで、bashでのさまざまなコマンドについて説明してきましたが、それらを個別に入力して実行していました。しかし、時にはこれらのコマンドを組み合わせてロジックを追加し、 プロセスを自動化したいこともあります。本記事では、それを可能にするbashスクリプトについて説明します。

シェルスクリプトの作成

bashスクリプトは、.shという拡張子を持つシェルスクリプトファイルを作成することで記述できます。このファイルは、touch test.shやVimを使ったvim test.shで作成できます。 シェルスクリプトでは、ファイル内のコマンドを実行するためのシェルバイナリを指定する必要があり、それをシバン(#!)とその後にバイナリのパスを書くことで行います。以下の例を試してみてください:

test.sh
#! /bin/bash
 
echo "Hello World!"

シェルスクリプトは、bash test.shまたは./test.shで実行できます。(chmodを使用してtest.shの実行権限を変更する必要があります。権限に関して不明な場合はLinux基礎 #6 - ユーザー管理と権限をご覧になることをお勧めします。) シェル上にHello World!という出力が表示されるはずです。

変数と引数

シェルスクリプトでは、大文字で変数を定義し、$記号を使って参照できます。例えば、OUTPUT_DIR="/root"を設定し、echo "OUTPUT_DIR: $OUTPUT_DIR"で出力できます。 また、./test.sh arg_1 arg_2のようにユーザーから引数を受け取り、スクリプト内で$<arg_number>を使って参照することも可能です。

test.sh
#! /bin/bash
 
OUTPUT_DIR="/root"
echo "OUTPUT_DIR $OUTPUT_DIR"
echo "ARGUMENTS $1, $2"

上記は、シェルスクリプトでの変数と引数の動作を示した例です。 これを再現して、任意の引数で./test.sh arg_1 arg_2を実行し、出力を確認してみてください。

ロジック

複数のコマンドを実行し、変数や引数を使用するだけでなく、forループ、whileループ、およびif文を使用してコマンド実行にロジックを追加することができます。 例えば、以下のようにforループを設定できます:

for i in {1..10}
do
     touch "$OUTPUT_DIR/$i.txt"
done

whileループは、readコマンドとcase文を組み合わせることでユーザー入力を取得するのに便利です。read -p "<プロンプト>" <変数>というコマンドを使用すると、 プロンプトを表示してユーザー入力を変数に保存できます。入力の有効性に応じて、whileループでユーザー入力を継続的に促すことが可能です。

while true; do
     read -p "Would you like to continue?" yn
     case $yn in
          [Yy]*) break;;
          [Nn]*) exit;;
          *) echo "Please answer in Y[y] or N[n]";;
     esac
done

上記は、ユーザーにプロセスを続行するかどうかを尋ねる実装例です。 case文と正規表現を使用して、breakでループを終了する、exitでプロセスを終了する、またはユーザー入力を再度促すかを判断します。 if文は、以下のように引数のチェックに役立ちます。

if [ $1 -lt 2 ]; then
     echo "The argument cannot be less than 2."
     exit
else
     echo "Creating $1 number of .txt files in $OUTPUT_DIR"
fi

これらのステートメントを組み合わせることで、以下のようにテキストファイルを作成する数を引数として指定し、実行を確認するスクリプトを作成できます:

# Argument validation
if [ $1 -lt 2 ]; then
     echo "The argument cannot be less than 2."
     exit
else
     echo "Creating $1 number of .txt files in $OUTPUT_DIR"
fi
 
# User validation
while true; do
     read -p "Would you like to continue?" yn
     case $yn in
          [Yy]*) break;;
          [Nn]*) exit;;
          *) echo "Please answer in Y[y] or N[n]";;
     esac
done
 
# File creation
for i in $(seq $1)
do
     touch "$OUTPUT_DIR/$i.txt"
done

上記の例では、seq(シーケンス)コマンドを使用して、引数からの数字のシーケンスを作成しています。 このスクリプトを再現し、実行してテキストファイルが正しく作成されていることを確認してください。 課題として、作成されたファイルをすべて削除する別のスクリプトを書いてみてください。

結論

この記事では、複数のコマンドをロジックとともに自動化することを可能にするbashスクリプトの基本について説明しました。 &を使用して遅いプロセスをバックグラウンドで実行するなど、他にも便利な構文がたくさんありますので、 興味がある方はぜひ調べてみてください。(bashがC言語で書かれているため、C言語の関数名と重複しているものがあることに驚くかもしれません。)

リソース