《-- Pro*CからPythonへの移行で学んだこと④:Bash・引数・終了コード編 --》
Introduction / はじめに
During the migration, I learned that a batch program is not only about Python code.
今回の移行を通して、バッチ処理ではPythonのコードだけを理解すればよいわけではないことを学びました。
In many systems, Python programs are started from shell scripts.
システムによっては、Pythonプログラムをシェルスクリプトから起動します。
Because of this, understanding Bash, arguments, and exit codes is also useful.
そのため、Bash・引数・終了コードについて理解することも重要です。
Running Python from Bash(BashからPythonを実行する)
A shell script can start a Python program like this:
シェルスクリプトからPythonプログラムを次のように起動できます。
python batch.py
A simple shell script may look like this:
シンプルなシェルスクリプトであれば、次のようになります。
#!/usr/bin/env bash
python batch.py
What Does $1 Mean?($1とは?)
In Bash, $1 represents the first argument passed to the shell script.
Bashでは、$1はシェルスクリプトに渡された1つ目の引数を表します。
For example:
例えば、
sh batch.sh 202608
Then:
この場合、
$0 → batch.sh
$1 → 202608
If we want to pass the first argument to Python:
1つ目の引数をPythonへ渡す場合は、
python batch.py "$1"
Python can receive it using sys.argv.
Python側ではsys.argvを使って受け取れます。
import sys
print(sys.argv[1])
The output will be:
出力結果は次のようになります。
202608
What Does $? Mean?($?とは?)
In Bash, $? contains the exit code of the command that was executed immediately before it.
Bashの$?には、直前に実行したコマンドの終了コードが入っています。
For example:
例えば、
python batch.py
RC=$?
RC now contains the exit code returned by the Python process.
この場合、Pythonプロセスの終了コードがRCに格納されます。
Returning an Exit Code from Python(Pythonから終了コードを返す)
Python can return an exit code using sys.exit().
Pythonではsys.exit()を使用して終了コードを返せます。
For successful completion:
正常終了の場合、
import sys
sys.exit(0)
For an error:
異常終了の場合、
import sys
sys.exit(1)
The shell can then check the result.
シェル側では、その終了コードを確認できます。
python batch.py
RC=$?
if [[ $RC -ne 0 ]]; then
exit 1
fi
exit 0
Checking the Exit Code(終了コードを確認する)
After running a shell script, we can check its exit code with:
シェルを実行した後、次のコマンドで終了コードを確認できます。
echo $?
A result of 0 generally means success.
一般的に0は正常終了を表します。
A non-zero value, such as 1, generally indicates an error.
1などの0以外の値は、一般的に異常終了を表します。
Function Return Values and Process Exit Codes Are Different(関数の戻り値とプロセスの終了コードは別物)
This was one of the most important things I learned.
ここは今回、特に重要だと感じたポイントです。
Suppose we have the following Python code:
例えば、次のPythonコードがあるとします。
def main():
return 1
if __name__ == "__main__":
rc = main()
In this case, rc becomes 1 inside the Python program.
この場合、Pythonプログラム内の変数rcには1が格納されます。
However, this does not automatically mean that the Python process exits with code 1.
しかし、これだけではPythonプロセス自体が終了コード1を返すとは限りません。
To return the value as the process exit code, we can use sys.exit().
プロセスの終了コードとして返すには、sys.exit()を使用します。
import sys
def main():
return 1
if __name__ == "__main__":
rc = main()
sys.exit(rc)
Now the shell can receive the exit code.
これで、シェル側からPythonの終了コードを受け取れるようになります。
Key Point / ポイント
return 1returns a value from a Python function, whilesys.exit(1)returns an exit status from the Python process to the shell.
return 1はPythonの関数から値を返す処理で、sys.exit(1)はPythonプロセスからシェルへ終了コードを返す処理です。
Overall Flow(全体の流れ)
The overall flow can be visualized like this:
全体の流れを整理すると、次のようになります。
Shell
↓
Pass argument / 引数を渡す
↓
Python
↓
Run batch logic / バッチ処理を実行
↓
sys.exit(0 or 1)
↓
Shell
↓
Read $? / $?で終了コードを取得
↓
Success or Error / 正常終了・異常終了
Once I understood this flow, shell scripts became much easier to read.
この流れを理解すると、シェルスクリプトの処理もかなり読みやすくなりました。
What I Learned / 学んだこと
At first, expressions such as $1, $?, and RC=$? were unfamiliar to me.
最初は、$1、$?、RC=$?といった記述が何を意味しているのか分かりませんでした。
However, once I understood the relationship between Bash and Python, the entire batch execution flow became much clearer.
BashとPythonの関係を理解することで、バッチ処理全体の流れが見えやすくなりました。
A batch program is not only the Python file itself.
バッチ処理は、Pythonファイルだけで完結しているとは限りません。
It is also important to understand how the program is started, what arguments are passed to it, and how the result is returned to the caller.
**「どのように起動されるのか」「どんな引数が渡されるのか」「実行結果をどのように呼び出し元へ返すのか」**まで確認することが重要だと学びました。