ブログ

Armadillo-X1, Armadillo-IoT G3/G3L: systemdでアプリを自動起動する方法(その2)〜起動順序を設定する〜

at_keita.mogaki
2017年11月6日 17時15分

以前掲載しました「Armadillo-X1, Armadillo-IoT G3/G3L: systemdでアプリを自動起動する方法(その1)」に続いてsystemdで起動順序を持たせてアプリを自動起動させる方法を紹介します。今回は特定のUnitが起動した後に任意のUnitを起動させる手順を説明します。

1.はじめに

自動起動するアプリに起動順序を持たせるためには、Unitファイルの[Unit]セクションに「Before = [Unit名]」または「After = [Unit名]」を追加し、[Unit名]より先か後に起動するという設定を行う事で実現することができます。

今回は以前作成した「system_init_test.service」に起動順序の設定を追加して、新たに「before_test.service」を作成し、 before_test.service -> system_init_test.service の順番で起動処理を行う手順を紹介します。

2.先に起動するUnitの作成

先に起動させるUnit「before_test.service」と、シェルスクリプト「before_test.sh」を新たに作成します。

2-1.起動するシェルスクリプトの作成

「before_test.service」で起動設定をするためのシェルスクリプト「before_test.sh」を作成します。このシェルスクリプトは3秒間スリープし、終了するという簡単な処理を行うものです。

root@armadillo:~# vi before_test.sh

シェルスクリプトは以下のように実装します。

#!/bin/bash

sleep 3

exit 0

作成したシェルスクリプトに実行権限を与えます。

root@armadillo:~# chmod +x before_test.sh
2-2.Unitファイルの作成

「before_test.sh」に関連付いたUnitファイル「before_test.service」を作成します。Unitファイルについての詳細は以前掲載したブログに記載していますので、そちらも参照して下さい。

root@armadillo:~# vi /etc/systemd/system/before_test.service

before_test.serviceは以下のように実装します。

[Unit]
Description = before_test.service daemon

[Service]
ExecStart = /root/before_test.sh
Type = oneshot

[Install]
WantedBy = multi-user.target
2-3.Unitファイルの自動起動の設定

systemctlコマンドを用いて自動起動するUnitの設定をします。
・Unitリストに追加したbefore_test.serviceが追加されている事を確認します。

root@armadillo:~# systemctl list-unit-files | grep before_test.service
before_test.service                    disabled

・before_test.serviceの自動起動を有効にします。

root@armadillo:~# systemctl enable before_test.service
Created symlink /etc/systemd/system/multi-user.target.wants/before_test.service → /etc/systemd/system/before_test.service

・before_test.serviceの自動起動が有効になったことを確認します。

root@armadillo:~# systemctl list-unit-files | grep before_test.service
before_test.service                    enabled

3.後に起動するUnitの修正

「before_test.service」の後に起動させるUnit「system_init_test.service」を修正します。まだ「system_init_test.service」を作成していない場合は、以前掲載したブログを参考にしてUnitを作成して下さい。

3-1.起動しているUnitの停止

Unitファイルを修正する際は、今動いているUnitを停止してから作業を行います。

root@armadillo:~# systemctl stop system_init_test.service
3-2.Unitファイルの修正

system_init_test.serviceの修正を行います。

root@armadillo:~# vi /etc/systemd/system/system_init_test.service

system_init_test.serviceは以下のように修正します。

[Unit]
Description = system_init_test daemon
After = before_test.service   # この行を追加

[Service]
ExecStart = /root/system_init_test.sh
Restart = always
Type = simple

[Install]
WantedBy = multi-user.target

[Unit]セクションに「After = before_test.service」を追加しました。これはbefore_test.serviceの後に自分のUnit(system_init_test.service)が起動するという意味になります。

「After = before_test.service」ではなく「Before = [Unit名]」と設定して[Unit名]の前に起動するという起動順序の設定を行うこともできます。このように[Unit]セクションにBefore/Afterの設定を行う事でsystemdが各Unitを起動する際の起動順序を決めることができます。

3-3.Unitの再起動

system_init_test.serviceの修正が完了したので、systemctlコマンドを用いてUnitを再読み込みします。

root@armadillo:~# systemctl daemon-reload

Unitを起動します。

root@armadillo:~# systemctl start system_init_test.service

4.起動順序の確認

Unitに正しく起動順序が設定されいるか確認します。

4-1.起動順序の設定を確認

「systemctl list-dependencies」に「--before/--after」オプションと[Unit名]を付けて実行する事で[Unit名]の起動順序を調べることができます。(Armadilloのデフォルトの設定でコマンドを実行すると文字化けを起こすため"LANG=C"を付けて実行します。)

root@armadillo:~# LANG=C systemctl list-dependencies --after system_init_test.service
system_init_test.service
* |-before_test.service                  # before_test.serviceが表示される。
* |-system.slice
* |-systemd-journald.socket
* `-basic.target
*   |-paths.target
*   | |-systemd-ask-password-console.path
*   | `-systemd-ask-password-wall.path

このコマンドの実行結果よりsystem_init_test.serviceはbefore_test.serviceより後(after)である事がわかります。

4-2.Armadilloの再起動

実際に正しい起動順序でUnitが起動されるか確認するために、Armadilloを再起動します。

root@armadillo:~# reboot

Armadilloの再起動が完了したらjournalctlコマンドを用いてSystemdの起動ログを表示し、正しい順番で起動が行われたかを確認します。

root@armadillo:~# journalctl -o short-precise | grep _test
Nov 09 17:39:27.564304 armadillo systemd[1]: Starting before_test.service daemon...
Nov 09 17:39:30.852456 armadillo systemd[1]: Started before_test.service daemon.
Nov 09 17:39:30.863599 armadillo systemd[1]: Starting system_init_test daemon...
Nov 09 17:39:30.892468 armadillo systemd[1]: Started system_init_test daemon.

※Unitの起動開始(Starting)と起動完了(Started)の時刻が表示されます。
このコマンドの実行結果よりbefore_test.serviceを起動開始してから3秒以上経過して起動完了し、その後before_test.service -> system_init_test.service の順番で起動している事がわかります。

このように起動順序を設定する事でその環境に合ったアプリの起動を行うことができます。

5.起動順序についての注意点

Unitファイルの値を変更することで起動順序のタイミングを変更することができますが、もし誤った値を設定した場合には意図しないタイミングでの起動や、他のUnitの起動タイミングが変わってしまうなどの問題も発生します。自作アプリの起動順序を設定する際は十分に注意をした上で環境に合った設定を行いましょう。

関連ページ