前提
この記事は,discord botでminecraft serverを操作したいアドベントカレンダーの記事です.
そもそもdaemonというものの私の認識は,PCが起動している間はずっと裏で動いてて,PCを再起動しても勝手に起動してくれるよ,程度です.この認識が間違っていた李,齟齬があるかもしれませんので,この記事では
- 裏でずっと動いてる
- 起動時に自動的にプログラムが実行される
という意味合いでdaemonを使います.
また,タイトルにdiscord botをdaemonにしたい書きましたが,どこかのサーバーにおいて起動させるわけではなく,ローカルの環境でdaemonにします.つまり,本当の意味でdiscord botを常駐させるわけではありません.PCを起動したらdiscord botも勝手に起動する,という感じになります.
また,環境は
- WSL, Ubuntu22.04.1
です.
daemonのための準備
まず,プログラムをコンピュータが実行できるようにする必要があります.そのために,ファイルに実行権限をchmod
を使って追加します.権限の変更については,Linuxの権限確認と変更(chmod)(超初心者向け),という記事を見つけたのでこちらを見るといいと思います.
実行権限を付与しての実行
まずは実験ということで適当なファイルを作り,実行させたいシェルスクリプトを仕込んでおきます.
$ touch somefile
$ echo "echo \"this is runnable?\"" > somefile
$ cat somefile
echo "this is runnable?"
このsomefile
に実行権限を与えます.
$ ls -l
-rw-r--r-- 1 user user 18 Dec 16 21:13 somefile
$ chmod +x somefile
$ ls -l
total 4
-rwxr-xr-x 1 user user 18 Dec 16 21:13 somefile
付与されました.
実行してみましょう.実行にはそのファイルまでの相対パスを指定するのだと理解しています.自分のディレクトリのsomefile
というファイルを指定すればいいです.
$ ./somefile
this is runnable?
文字列が返ってきました.つまりはecho
コマンドが実行されたということですね.
ここで,この状態でpythonのファイルを実行しようとしても,シェルスクリプトとして解釈されるのでエラーが発生します.
$ cat pyfile.py
import os
print(os.getenv("EXAMPLE"))
$ ./pyfile.py
./pyfile.py: line 1: import: command not found
./pyfile.py: line 3: syntax error near unexpected token `os.getenv'
./pyfile.py: line 3: `print(os.getenv("EXAMPLE"))'
そのため,どのコマンドでこのファイルを実行するかを指定する必要があります.これに必要なのがShebangです
Shebang
Shebangについては,手を動かして理解するshebangという記事を見てください.私は,そのファイルを実行するコマンドを記述できる,程度の認識です.
とりあえず,pythonのファイルを動かせるようにしましょう.
#! /usr/bin/env python3
import os
print(os.getenv("EXAMPLE"))
$ ./pyfile.py
None
実行できました.EXAMPLE
という環境変数は存在しないのでNone
が表示されています.
/usr/bin/env
この/usr/bin/env
は何者かは実行すればわかります.
$ /usr/bin/env
SHELL=/bin/bash
WSL2_GUI_APPS_ENABLED=1
WSL_DISTRO_NAME=Ubuntu-22.04
......
とこんな感じで,単体で利用すれば環境変数を表示してくれるものです.ちなみに,このenv
については私が書いた環境変数の設定を説明した記事でちょっと触れていますので読んでいただけると嬉しいです.
このenv
では,環境変数を設定しつつコマンドを実行することができます.
一旦,shebangを使わないpythonファイルを用意しました.
import os
print(os.getenv("EXAMPLE"))
これに対して,env
でEXAMPLE
の値を設定して実行します.
$ env EXAMPLE=example python3 pyfile_nosb.py
example
このように,EXAMPLE
に値を入れて実行することができました.
これをShebangを使ってすることもできます.ただし,Shebang内で複数引数を渡すときは最初に-S
オプションを付ける必要があります.
#! /usr/bin/env -S EXAMPLE=example python3
import os
print(os.getenv("EXAMPLE"))
$ ./pyfile.py
example
環境変数が設定されて実行されましたね.
本題に戻ると,env
をShebangで利用すると,環境に依存したpython3
を探して実行してくれます.他のコマンドでも同様です.
これでdaemonにする準備ができました.