起きている問題
前提
Amazon EC2のインスタンス上にあるUbuntu18.04において、Nginx + uWSGIでDjangoのサーバを立てようとしている。
各種バージョン
Nginx: 1.14.0
uWSGI: 2.0.18
Python: 3.7.5
Django: 2.2.11
まずuWSGIを起動するため、以下のようなuwsgi-hogehoge.serviceというファイルを作った。
[Unit]
Description=uWSGI service for mysite
[Service]
User=ubuntu
ExecStart=/bin/bash -c 'sh /hogehoge/start.sh'
ExecStartPre=/bin/bash -c 'sh /hogehoge/start_pre.sh'
Restart=always
KillSignal=SIGQUIT
Type=notify
StandardError=syslog
NotifyAccess=all
[Install]
WantedBy=multi-user.target
start.shにuwsgiを起動するための処理が含まれています。
そして何が起きたか
uWSGIとNginxを起動するためのserviceファイルを作成し、systemdにシンボリックリンクを貼った。そして、
$ systemctl start uwsgi-hogehoge.service
でサービスを起動しようとすると、どうやらstatusを見る限りできていない。
$ journalctl -xe
でログを確認すると、以下のエラーが出ていた。
uwsgi: command not found
確認したこと
・普通にuwsgiのパスは通っている。
・パーミッションなどの権限周りに関係したエラーではない。
・そもそも権限周りのエラーだったとしてもファイルやユーザーにちゃんとしかるべき権限は与えてる。
以上のことから、どうやら、普通にするとuwsgiのパスは通っているが、systemdくんが起動時コマンドとして実行する時だけパスが通ってないのでは、という仮説の疑問を立てた。
解決策
やはりどんな事にも偉大なる先人様はいますね。
以下の神記事を見つけて全ては解決。
上の記事から引用すると、
調べてみると、systemdは.barshrcや.bash_profileに
定義した環境変数を読んでくれないということがわかりました。
ということらしい....
解決のためにしたこと
$ echo $PATH
でパスを表示させる。
そしたら、
/home/ubuntu/.local/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin:/home/ubuntu/.local/bin
みたいな感じで表示された。
そしたら、/etcにsysconfigディレクトリを作成し、適当な名前でファイルを作った。私の場合は、ubuntuという名前のユーザーだったのでファイル名もubuntuにした。
そして、ubuntuファイルを以下のように編集した。
# cat <_EOF_ > /etc/sysconfig/ubuntu
PATH=/home/ubuntu/.local/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin:/home/ubuntu/.local/bin/usr/local/bin
_EOF_
次に、uwsgi-hogehoge.serviceファイルに、先ほど作ったファイルへのパスを設定する。
[Unit]
Description=uWSGI service for mysite
[Service]
User=ubuntu
EnvironmentFile=/etc/sysconfig/ubuntu <--ここを追加!!
ExecStart=/bin/bash -c 'sh /hogehoge/start.sh'
ExecStartPre=/bin/bash -c 'sh /hogehoge/start_pre.sh'
Restart=always
KillSignal=SIGQUIT
Type=notify
StandardError=syslog
NotifyAccess=all
[Install]
WantedBy=multi-user.target
これで、systemdでサービスを起動する時にちゃんと環境変数も読み込めるようになった。
$ systemctl daemon-reload
でserviceファイルの更新をちゃんと読み込ませて、再び
$ systemctl start uwsgi-hogehoge
今度はちゃんと起動しました。