序章

この2部構成のチュートリアルでは、再起動またはクラッシュ後に自動的に再起動するようにLinuxサービスを構成する方法を学習します。 systemd.

パート1では、次のような一般的なLinuxサービス管理の概念について説明します。 init デーモンとランレベル。 最後に、サービス管理のデモンストレーションを行います。 systemd. ここで調べます targets, wants, requires、 と unit ファイル。

パート2は、実用的で一般的なものを完了するためのステップバイステップのチュートリアルを提供します systemd 仕事。 具体的には、クラッシュまたは再起動後に自動的に起動するようにMySQLデータベースサーバーを構成します。

注:systemctlを使用してsystemdサービスとユニットを制御するための非常に人気のあるチュートリアルを読むことも検討してください

前提条件

このチュートリアルを完了するには、次のものが必要です。

サービス管理デーモンの紹介

Linuxサービスは、サービス管理デーモン(別名、サービス管理デーモン)による処理方法を変更することで、主に自己回復させることができます。 init デーモン。

init は、マシンが起動してカーネルがメモリにロードされた後、Linuxシステムで開始される最初のプロセスです。 特に、ユーザープロセスまたはシステムサービスをロードする方法、順序、および自動的に開始するかどうかを決定します。

Linuxが進化するにつれて、 init デーモン。 もともと、LinuxはSystemVから始まりました init、Unixで使用されたものと同じです。 それ以来、LinuxはUpstartを実装しています init デーモン(Ubuntuによって作成された)、そして今はsystemd init デーモン(Fedoraによって最初に実装されました)。

最近のほとんどのLinuxディストリビューションは、System Vから徐々に移行し、現在systemdを使用しています。 古いスタイル init (使用する場合)下位互換性のためにのみ保持されます。 UNIXの変種であるFreeBSDは、BSDと呼ばれる別のSystemV実装を使用します。 init.

systemdは、今日のLinuxディストリビューションで使用されている最新の一般的なサービスマネージャーであるため、この記事で取り上げます。 ただし、必要に応じてSystem VとUpstartについても説明し、そこからsystemdがどのように進化したかを確認します。 あなたにアイデアを与えるために:

  • SystemVが最も古い init システム、で使用される
  • Debian6以前
  • Ubuntu9.04以前
  • CentOS5以前
  • UpstartはSystemVの後に登場し、
  • Ubuntu14.04を含むUbuntu9.10からUbuntu14.10
  • CentOS 6
  • systemd は、で使用されている最新のLinuxサービスマネージャーです。
  • Debian7以降
  • Ubuntu15.04以降
  • CentOS7以降

を理解するには init デーモン、runlevelと呼ばれるものから始めましょう。

ランレベル

ランレベルは、Linuxシステムの現在の状態を表します。 たとえば、ランレベルは、Linuxサーバーのシャットダウン状態、シングルユーザーモード、再起動モードなどです。 各モードは、その状態で実行できるサービスを決定します。

一部のサービスは1つ以上のランレベルで実行できますが、他のサービスでは実行できません。 ランレベルは、0〜6の値で示されます。 次のリストは、これらの各レベルの意味を示しています。

  • ランレベル0:システムのシャットダウン
  • ランレベル1:シングルユーザー、レスキューモード
  • ランレベル2、3、4 :マルチユーザー、ネットワーキングが有効なテキストモード
  • ランレベル5:マルチユーザー、ネットワーク対応、グラフィカルモード
  • ランレベル6:システムの再起動

ランレベル2、3、および4は、ディストリビューションによって異なります。 たとえば、一部のLinuxディストリビューションはランレベル4を実装していませんが、他のディストリビューションは実装しています。 一部のディストリビューションでは、これら3つのレベルが明確に区別されています。 一般に、ランレベル2、3、または4は、Linuxがマルチユーザーのネットワーク対応のテキストモードで起動した状態を意味します。

サービスの自動開始を有効にすると、Linuxは実際にそのサービスをランレベルに追加します。 たとえば、System Vでは、OSは特定のランレベルで起動します。 そして、起動すると、そのランレベルに関連付けられているすべてのサービスを起動しようとします。 systemdでは、ランレベルがターゲットになり、サービスが自動開始されると、ターゲットに追加されます。 ターゲットについては、この記事の後半で説明します。

SystemVの紹介 init デーモン

SystemVは inittab 後でファイル init メソッドは下位互換性を維持しています。 SystemVの起動シーケンスを実行してみましょう。

  1. The init デーモンはバイナリファイル/sbin/initから作成されます
  2. 最初のファイル init デーモンの読み取りは/etc/inittabです
  3. このファイルのエントリの1つは、マシンが起動するランレベルを決定します。 たとえば、ランレベルの値が3と指定されている場合、Linuxはネットワークが有効になっているマルチユーザーのテキストモードで起動します。 (このランレベルはデフォルトのランレベルと呼ばれます)
  4. 次に、 init デーモンは/etc/ inittabファイルをさらに調べて、何を読み取りますか init そのランレベルで実行する必要のあるスクリプト

だから、 init デーモンは何を見つけます init 特定のランレベルで実行する必要のあるスクリプト。実際には、起動する必要のあるサービスを見つけています。 これらは init スクリプトは、個々のサービスの起動動作を構成できる場所です。

アン init スクリプトは、SystemVの特定のサービスを制御するものです。 init サービスのスクリプトは、アプリケーションのベンダーによって提供されたか、Linuxディストリビューション(ネイティブサービス用)に付属しています。 独自に作成することもできます init カスタム作成されたサービスのスクリプト。

MySQLサーバーなどのプロセスまたはサービスがSystemVで起動する場合、そのバイナリプログラムファイルをメモリにロードする必要があります。 サービスの構成方法によっては、このプログラムはバックグラウンドを継続的に実行する(そしてクライアント接続を受け入れる)場合があります。 このバイナリアプリケーションの開始、停止、または再読み込みのジョブは、サービスの init 脚本。 それはと呼ばれています init これは、サービスを初期化するためのスクリプトです。

System Vでは、 init スクリプトはシェルスクリプトです。 彼らはまた呼ばれます rc (コマンドを実行)スクリプト。 スクリプトは、 /etc/init.d ディレクトリ。 これらのスクリプトは、 /etc/rc ディレクトリ。 以内 /etc ディレクトリ、いくつかあります rc ディレクトリ。それぞれの名前に番号が含まれています。 数字はさまざまなランレベルを表しています。 だから私たちは /etc/rc0.d, /etc/rc1.d, /etc/rc2.d 等々。

クラッシュまたは再起動後にサービスを再起動するには、通常、次のような行をに追加できます。 init 脚本:

  1. ms:2345:respawn:/bin/sh /usr/bin/service_name

System Vサービスをシステムの起動時に開始できるようにするには、次のコマンドを実行します。

  1. sudo chkconfig service_name on

無効にするには、次のコマンドを実行します。

  1. sudo chkconfig service_name off

ステータス(実行中または停止中)を確認するには、このコマンドを実行します

  1. sudo service service_name status

Upstartデーモンの紹介

ジョブとサービスをロードするシリアル化された方法がSystemVでより時間がかかり、複雑になるにつれて init、Upstartデーモンは、OSのより高速なロード、クラッシュしたサービスの適切なクリーンアップ、およびシステムサービス間の予測可能な依存関係のために導入されました。

アップスタート init SystemVよりも優れていた init いくつかの方法で:

  • サービスをロードおよび管理するための難解なシェルスクリプトは処理しませんでした。 代わりに、理解と変更が容易な単純な構成ファイルを使用します
  • System Vのようにサービスがシリアルにロードされなかったため、システムの起動時間が短縮されました
  • 柔軟なイベントシステムを使用して、さまざまな状態でのサービスの処理方法をカスタマイズしました
  • Upstartには、クラッシュしたサービスがどのようにリスポーンするかを処理するためのより良い方法がありました。
  • すべて同じスクリプトを指す、冗長なシンボリックリンクを多数保持する必要はありませんでした。

物事を単純にするために、UpstartはSystemVと下位互換性があります。 The /etc/init.d/rc スクリプトは引き続き実行され、ネイティブのSystemVサービスを管理します。 その主な違いは、複数のイベントをサービスに関連付ける方法です。 このイベントベースのアーキテクチャにより、Upstartは柔軟なサービスマネージャーになることができました。 Upstartを使用すると、各イベントは、そのイベントを処理するシェルスクリプトを起動できます。 これらのイベントには次のものが含まれます。

  • 起動
  • 開始
  • 停止
  • 停止

これらのイベントの合間に、サービスは、待機、事前開始、開始、実行、事前停止、停止など、さまざまな状態になる可能性があります。 Upstartは、これらの各状態に対してもアクションを実行し、非常に柔軟なアーキテクチャを作成できます。

起動時に、Upstartは任意のSystemVを実行します init 通常のスクリプト。 その後、下を見ていきます /etc/init ディレクトリを作成し、各サービス構成ファイルでシェルコマンドを実行します。 特に、これらのファイルはサービスの起動動作を制御していました。

ファイルの命名スタイルは service_name.conf、およびスタンザと呼ばれるさまざまなセクションを持つプレーンテキストコンテンツがあります。 各スタンザは、サービスのさまざまな側面とその動作方法を説明します。 クラッシュまたは再起動後にサービスを自動的に開始するには、 respawn cronサービスについて以下に示すように、サービス構成ファイルのコマンド。

/etc/init/cron.conf

...

description "regular background program processing daemon"

start on runlevel [2345]

stop on runlevel [!2345]

expect fork

**respawn**

exec cron

の紹介 systemd デーモン

Linuxの最新版 init デーモンはsystemdです。 実際、それは単なる init デーモン:systemdは、最新のLinuxシステムの多くのコンポーネントを網羅するフレームワークです。

その機能の1つは、Linuxのシステムおよびサービスマネージャーとして機能することです。 この容量では、systemdは、サービスがクラッシュしたり、マシンが再起動したりした場合のサービスの動作を制御します。 ここでsystemdのsystemctlについて読むことができます。

systemdは、SystemVコマンドおよび初期化スクリプトと下位互換性があります。 つまり、SystemVサービスもsystemdで実行されます。 これが可能なのは、ほとんどのUpstartおよびSystemV管理コマンドがsystemdで機能するように変更されているためです。

systemd構成ファイル:ユニットファイル

systemdの中心にはユニットファイルがあります。 各ユニットファイルは、特定のシステムリソースを表します。 リソースに関する情報は、ユニットファイルで追跡されます。 サービスユニットファイルは、宣言型構文の単純なテキストファイル(Upstart .confファイルなど)です。 これにより、ファイルの理解と変更が容易になります。

systemdと他の2つの主な違い init メソッドは、systemdがサービスデーモンと、デバイスのオペレーティングシステムパス、マウントポイント、ソケットなどの他のタイプのリソースの初期化を担当することです。 ユニットファイルの命名スタイルは次のとおりです。 service_name.unit_type. したがって、次のようなファイルが表示されます dbus.service, sshd.socket、 また home.mount.

ディレクトリ構造

CentOSのようなRedHatベースのシステムでは、ユニットファイルは2つの場所にあります。 主な場所は /lib/systemd/system/. カスタム作成されたユニットファイルまたはシステム管理者によって変更された既存のユニットファイルは、 /etc/systemd/system.

同じ名前のユニットファイルが両方の場所に存在する場合、systemdは以下のものを使用します /etc. サービスが起動時またはその他のターゲット/ランレベルで開始できるようになっているとします。 その場合、そのサービスユニットファイルのシンボリックリンクが、の適切なディレクトリの下に作成されます。 /etc/systemd/system. 下のユニットファイル /etc/systemd/system 実際には、同じ名前のファイルへのシンボリックリンクです。 /lib/systemd/system.

systemd init シーケンス:ターゲットユニット

特殊なタイプのユニットファイルは、ターゲットユニットです。

ターゲットユニットのファイル名には、.targetという接尾辞が付いています。 ターゲットユニットは、特定のリソースを表していないため、他のユニットファイルとは異なります。 むしろ、それらはいつでもシステムの状態を表します。 ターゲットユニットは、その状態の一部である必要がある複数のユニットファイルをグループ化して起動することによってこれを行います。 したがって、systemdターゲットは、同じではありませんが、SystemVランレベルと大まかに比較できます。

各ターゲットには、番号ではなく名前があります。 たとえば、 multi-user.target それ以外の runlevel 3 また reboot.target それ以外の runlevel 6. Linuxサーバーが次のように起動すると、 multi-user.target、それは本質的にサーバーを runlevel 2, 3, or 4、ネットワークが有効になっているマルチユーザーテキストモードです。

サーバーをその段階に引き上げる方法が違いです。 System Vとは異なり、systemdはサービスを順番に起動しません。 途中で、他のサービスやリソースの存在を確認し、それらのロードの順序を決定できます。 これにより、サービスを並行してロードできるようになります。

ターゲットユニットとランレベルのもう1つの違いは、System Vでは、Linuxシステムは1つのランレベルにしか存在できないことです。 ランレベルを変更することはできますが、システムはその新しいランレベルにのみ存在します。 systemdを使用すると、ターゲットユニットを包括的にすることができます。つまり、ターゲットユニットがアクティブになると、他のターゲットユニットがその一部としてロードされるようになります。

たとえば、グラフィカルユーザーインターフェイスで起動するLinuxシステムでは、graphical.targetがアクティブ化されます。これにより、multi-user.targetも自動的にロードされ、アクティブ化されます。 System Vの用語では、ランレベル3と5を同時にアクティブ化するようなものです。

次の表は、ランレベルとターゲットを比較しています。

ランレベル(System V init) ターゲットユニット(Systemd)
ランレベル0 poweroff.target
ランレベル1 resuce.target
ランレベル2、3、4 multi-user.target
ランレベル5 graphics.target
ランレベル6 restart.target

systemd default.target

systemd default.target SystemVのデフォルトのランレベルと同等です。

System Vには、inittabというファイルで定義されたデフォルトのランレベルがありました。 systemdでは、そのファイルはdefault.targetに置き換えられます。 デフォルトのターゲットユニットファイルは、/ etc / systemd/systemディレクトリにあります。 これは、/ lib / systemd/systemの下にあるターゲットユニットファイルの1つへのシンボリックリンクです。

デフォルトのターゲットを変更すると、基本的にそのシンボリックリンクが再作成され、システムのランレベルが変更されます。

System Vのinittabファイルは、Linuxが実行するディレクトリも指定しました。 init からのスクリプト:それはrcn.dディレクトリのいずれかである可能性があります。 systemdでは、デフォルトのターゲットユニットによって、起動時にロードされるリソースユニットが決まります。

ユニットがアクティブ化されると、それらはすべて並行して、またはすべて順番にアクティブ化されます。 リソースユニットのロード方法は、必要または必要な他のリソースユニットによって異なる場合があります。

systemdの依存関係:必要なものと必要なもの

systemd wantsおよびrequiresは、systemdがサービスデーモン間の依存関係に対処する方法を制御します。

前述のように、Upstartは、構成ファイルを使用してサービスの並列ロードを保証します。 System Vでは、サービスは特定のランレベルで開始できますが、別のサービスまたはリソースが使用可能になるまで待機させることもできます。 同様の方法で、systemdサービスを1つ以上のターゲットにロードするか、別のサービスまたはリソースがアクティブになるまで待機することができます。

systemdでは、別のユニットを必要とするユニットは、必要なユニットがロードされてアクティブ化されるまで起動しません。 最初のユニットがアクティブなときに必要なユニットが何らかの理由で故障した場合、最初のユニットも停止します。

これにより、システムの安定性が確保されます。 したがって、特定のディレクトリが存在する必要があるサービスは、そのディレクトリへのマウントポイントがアクティブになるまで待機させることができます。 一方、別のユニットが必要なユニットは、そのような制限を課しません。 発信者がアクティブなときに目的のユニットが停止しても停止しません。 この例としては、グラフィカルターゲットモードで表示される必須ではないサービスがあります。

実用例:systemdの起動シーケンスを理解する

systemdでのサービスの起動動作を理解するために、CentOS8.3ドロップレットを使用しています。 可能な限り.targetrabbit-trailをたどります。 systemdの起動シーケンスは、依存関係の長いチェーンに従います。

まず、次のコマンドを実行して、デフォルトのターゲットユニットファイルを一覧表示します。

  1. sudo ls -l /etc/systemd/system/default.target

これは、次のような出力を示しています。

Output
lrwxrwxrwx. 1 root root 37 Dec 4 17:42 /etc/systemd/system/default.target -> /lib/systemd/system/multi-user.target

ご覧のとおり、デフォルトのターゲットは、実際には/ lib / systemd /system/の下にあるマルチユーザーターゲットファイルへのシンボリックリンクです。 したがって、システムはmulti-user.targetで起動することになっています。これは、SystemVinitのランレベル3に似ています。

multi-user.target.wants

次に、次のコマンドを実行して、multi-user.targetファイルが必要とするすべてのサービスを確認します。

  1. sudo ls -l /etc/systemd/system/multi-user.target.wants/*.service

これにより、/ usr / lib / systemd /system/の下にある実際のユニットファイルを指すシンボリックリンクファイルのリストが表示されます。

Output
lrwxrwxrwx. 1 root root 38 Dec 4 17:38 /etc/systemd/system/multi-user.target.wants/auditd.service -> /usr/lib/systemd/system/auditd.service lrwxrwxrwx. 1 root root 39 Dec 4 17:39 /etc/systemd/system/multi-user.target.wants/chronyd.service -> /usr/lib/systemd/system/chronyd.service lrwxrwxrwx. 1 root root 37 Dec 4 17:38 /etc/systemd/system/multi-user.target.wants/crond.service -> /usr/lib/systemd/system/crond.service lrwxrwxrwx. 1 root root 42 Dec 4 17:39 /etc/systemd/system/multi-user.target.wants/irqbalance.service -> /usr/lib/systemd/system/irqbalance.service lrwxrwxrwx. 1 root root 37 Dec 4 17:41 /etc/systemd/system/multi-user.target.wants/kdump.service -> /usr/lib/systemd/system/kdump.service ...

以外 multi-user.target、次のようなさまざまなタイプのターゲットがあります system-update.target また basic.target. マルチユーザーターゲットが依存しているターゲットを確認するには、次のコマンドを実行します。

  1. sudo systemctl show --property "Requires" multi-user.target | fmt -10

出力は次のとおりです。

Output
Requires=basic.target

basic.target

次のコマンドを実行して、basic.targetに必要なユニットがあるかどうかを確認できます。

  1. sudo systemctl show --property "Requires" basic.target | fmt -10

結局のところ、basic.targetにはsysinit.targetが必要です。

Output
Requires=sysinit.target -.mount

また、いくつかのターゲットも必要です。

  1. sudo systemctl show --property "Wants" basic.target | fmt -10

このコマンドは次を返します。

Output
Wants=slices.target paths.target timers.target microcode.service sockets.target sysinit.target

再帰的に実行すると、sysinit.targetで他のターゲットも実行する必要があるかどうかを確認できます。

  1. sudo systemctl show --property "Requires" sysinit.target | fmt -10

ありません。 ただし、sysinit.targetが必要とする他のターゲットがあります。

  1. systemctl show --property "Wants" sysinit.target | fmt -10

次のような出力が表示されます。

Output
Wants=systemd-random-seed.service dev-mqueue.mount rngd.service systemd-modules-load.service proc-sys-fs-binfmt_misc.automount local-fs.target sys-fs-fuse-connections.mount systemd-sysusers.service systemd-update-done.service systemd-update-utmp.service systemd-journal-flush.service dev-hugepages.mount dracut-shutdown.service swap.target systemd-udevd.service import-state.service sys-kernel-debug.mount nis-domainname.service systemd-journald.service selinux-autorelabel-mark.service kmod-static-nodes.service loadmodules.service ldconfig.service cryptsetup.target systemd-sysctl.service systemd-ask-password-console.path systemd-journal-catalog-update.service systemd-udev-trigger.service systemd-tmpfiles-setup.service systemd-hwdb-update.service sys-kernel-config.mount systemd-binfmt.service systemd-tmpfiles-setup-dev.service systemd-machine-id-commit.service systemd-firstboot.service

調べて systemd ユニットファイル

さらに一歩進んで、sshd用のサービスユニットファイルの内部を見てみましょう。

  1. sudo vi /etc/systemd/system/multi-user.target.wants/sshd.service

次のようになります。

/etc/systemd/system/multi-user.target.wants/sshd.service
[Unit]
Description=OpenSSH server daemon
Documentation=man:sshd(8) man:sshd_config(5)
After=network.target sshd-keygen.target
Wants=sshd-keygen.target

[Service]
Type=notify
EnvironmentFile=-/etc/crypto-policies/back-ends/opensshserver.config
EnvironmentFile=-/etc/sysconfig/sshd
ExecStart=/usr/sbin/sshd -D $OPTIONS $CRYPTO_POLICY
ExecReload=/bin/kill -HUP $MAINPID
KillMode=process
Restart=on-failure
RestartSec=42s

[Install]
WantedBy=multi-user.target

サービスユニットファイルがクリーンでわかりやすいことがわかります。

最初の重要な部分は、 [Unit] セクション。 これは、network.targetとsshd-keygen.targetがロードされた後にsshdサービスをロードする必要があることを示しています。

The [Install] セクションは、サービスがmulti-user.targetによって必要とされていることを示しています。 これは、multi-user.targetがsshdデーモンをロードすることを意味しますが、ロード中にsshdが失敗しても、シャットダウンまたはクラッシュすることはありません。

以来 multi-user.target はデフォルトのターゲットであり、sshdデーモンは起動時に起動することになっています。 の中に [Service] セクション、 Restart パラメータの値は on-failure. この設定により、sshdデーモンがクラッシュしたり、終了がクリーンでない場合に再起動できます。

結論

この記事では、System V、Upstart、およびsystemdサービス管理デーモンについて学習しました。 スタートアップスクリプトと構成ファイル、重要なパラメーター、スタートアップシーケンス、およびサービスのスタートアップ動作を制御するコマンドについて説明しました。

この記事のパート2では、これらのスキルを実際の例に適用し、systemdを使用してMySQLを構成します。 完了すると、MySQLインスタンスは再起動またはクラッシュ後に自動的に再起動します。 また、サンプルアプリケーションとしてMySQLを使用しますが、NginxやApacheWebサーバーなどの任意の数のサービスを置き換えることができます。