【ITニュース解説】Learn Bash Scripting With Me 🚀 - Day 7
2025年09月26日に「Dev.to」が公開したITニュース「Learn Bash Scripting With Me 🚀 - Day 7」について初心者にもわかりやすく解説しています。
ITニュース概要
Bashスクリプトの関数は、コードをひとまとまりにして名前をつけ、必要な時に繰り返し実行できる便利な機能だ。これにより、スクリプトの再利用性が高まり、効率的な開発が可能になる。関数の宣言方法や具体的な利用例を学ぶ。
ITニュース解説
Bashスクリプトにおける関数は、一度定義した一連のコマンドに名前を付け、スクリプトの様々な場所からその名前を呼び出すことで、定義したコマンド群を何度でも再利用できる仕組みである。これは、スクリプト全体の中に、特定の目的を持った小さなスクリプトを埋め込むようなものと捉えることができる。関数を活用することで、同じ処理を繰り返し記述する手間を省き、コードの重複をなくし、スクリプト全体の可読性や保守性を向上させることが可能になる。
関数を宣言するには主に二つの書き方がある。どちらのスタイルを採用する場合でも、関数は基本的にはその関数が呼び出される前に宣言されていなければならない。ただし、この原則には後述するBashのスクリプト処理方法に関連する例外が存在する。
一つ目のスタイルは「function」キーワードを使う方法である。このスタイルでは、「function 関数名 { コマンド; ... }」という形式で関数を定義する。「function」というキーワードは、これに続くものが関数定義であることをBashインタープリタに明示的に伝える役割を持つ。「関数名」は、その関数を識別するためのユニークな名前であり、スクリプト内でこの名前を記述することで、関数内に定義された処理を実行できる。波括弧「{...}」は、関数の本体、つまり関数が実行する一連のコマンド群を囲むブロックである。このブロック内のコマンドが、関数が呼び出された時に順次実行される。記述上の注意点として、開き波括弧「{」は関数名と同じ行に配置し、その直前にスペースを入れる必要がある。閉じ波括弧「}」は独立した行に記述することが推奨される。例えば、「function display_message { echo "これは関数からのメッセージです"; }」という形で宣言する。
二つ目のスタイルは「function」キーワードを使わず、括弧「()」を使う方法である。このスタイルでは、「関数名() { コマンド; ... }」という形式で関数を定義する。ここでは「function」キーワードは不要だが、関数名の直後に必ず空の括弧「()」を付ける必要がある。この括弧が、これが関数定義であることをBashに伝える重要な目印となる。波括弧「{...}」の役割は一つ目のスタイルと同様で、関数が実行するコマンド群を定義する。このスタイルでの記述上の注意点として、空の括弧「()」と開き波括弧「{」の間にスペースを入れる必要がある。関数内の各コマンドは個別の行に記述するか、セミコロン「;」で区切る。閉じ波括弧「}」は独立した行に記述することが推奨される。例えば、「greet_user() { echo "こんにちは、ユーザーさん"; }」という形で宣言する。
具体的な関数の利用例として、システム上の /etc/shadow ファイルの存在を確認するスクリプトを見てみよう。
まず、スクリプトの冒頭には「#!/bin/bash」という行がある。これは「shebang(シバン)」と呼ばれ、このスクリプトを /bin/bash にあるBashインタープリタを使って実行するようシステムに指示する役割を持つ。その後の「# The goal of this script...」のような行はコメントである。「#」記号で始まる行はBashによって無視され、スクリプトの実行には影響しない。これは、スクリプトの内容や目的を人間が理解しやすくするための説明やメモとして使われる。
次に、「function test_shadow { ... }」という部分で test_shadow という関数が宣言されている。この関数は、前述のスタイル1で記述されている。関数本体の最初の行「echo "---checking for shadow file---"」は、単にファイルチェックを開始することを示すメッセージを標準出力に表示するコマンドである。
その次に、「if [ -e /etc/shadow ]; then echo "shadow file exists"; fi」という条件分岐の構造がある。「if」は条件文の開始を示すキーワードである。角括弧「[ -e /etc/shadow ]」の中が条件式であり、ここでは「/etc/shadow というファイルが存在するかどうか」をチェックしている。「-e」は「指定されたファイルが存在する」という真偽を判定するテスト演算子である。この条件式が真、つまり /etc/shadow ファイルが存在する場合、「; then」の後に続くコマンドが実行される。ここでは「echo "shadow file exists"」というメッセージが表示される。条件文の終わりは「fi」というキーワードで示される。
この関数を実際に実行させるには、スクリプト内のどこか、通常は関数の定義ブロックの後に、関数名「test_shadow」を単独で記述して呼び出す。この呼び出しによって、関数 test_shadow の内部に定義された一連のコマンドが実行され、ファイルの存在チェックが行われ、その結果に応じたメッセージが表示される。
ここで、先に述べた「関数は呼び出される前に宣言されていなければならない」という原則について、より詳細な理解を深める必要がある。特に、ある関数が別の関数を呼び出すようなケースでは、宣言順序が厳密でなくても問題なく動作することがある。これは、Bashがスクリプトを実行する際に「パーシング(解析)」と「実行」という二段階の処理を行うためである。
まず「パーシング」の段階では、Bashはスクリプトのテキスト全体を最初から最後まで読み込み、その内容を構文的に解析する。この時、どの部分が通常のコマンドで、どの部分が変数定義で、そしてどの部分が関数定義であるかを識別し、スクリプト全体の構造を把握する。この段階ではまだ、具体的なコマンドの実行は行われない。Bashはこのパーシングの段階で、スクリプト内に定義されている全ての関数を認識し、その存在を記憶する。
次に「実行」の段階で、Bashはパーシングで得られた情報に基づき、スクリプトを上から順に一行ずつ実行していく。パーシングの段階で既に全ての関数定義が把握されているため、実行時には、たとえ呼び出される側の関数がスクリプトテキスト上では呼び出し元の関数よりも後で定義されていたとしても、Bashはそれが関数であることを知っており、正しく参照して実行できるのである。
この挙動を理解するには、実際に簡単なスクリプトを作成し、様々な宣言順序で関数を呼び出してみることが重要である。例えば、一つの関数が別の関数を呼び出すようなスクリプトを自分で書き、実行結果を観察することで、Bashのパーシングと実行の仕組みに対する理解を深めることができる。このような実践的な試行は、Bashスクリプトや関数を学ぶ上で非常に効果的な方法である。
関数は、複雑なスクリプトを小さな部品に分割し、それぞれの部品が特定の役割を果たすように設計することを可能にする。これにより、大規模なスクリプトでも管理しやすくなり、エラーの発見や修正も容易になる。システムエンジニアを目指す上で、Bashスクリプトにおける関数の概念と使い方をマスターすることは、日常的な作業の自動化や効率化に直結するため、非常に価値のあるスキルとなる。