systemdのログ管理

システム化されたジャーナル



systemd初期化デーモンは、最新のLinuxシステムの事実上の標準になっています。 多くの一般的なディストリビューションがDebian、RHEL / CentOS、Ubuntu(バージョン15.04以降)に切り替わりました。 Systemdは、根本的に異なる(従来のsyslogツールと比較して)ロギングアプローチを使用します。

集中化に基づいています。専門のジャーナルコンポーネントは、すべてのシステムメッセージ(カーネル、さまざまなサービス、アプリケーションからのメッセージ)を収集します。 同時に、送信ログを特別に設定する必要はありません。アプリケーションは単にstdoutとstderrに書き込むことができますが、ジャーナルはこれらのメッセージを自動的に保存します。 このモードはUpstartでも可能ですが、すべてのログを個別のファイルに保存し、systemdはそれらをバイナリデータベースに保存するため、システム化と検索が大幅に簡素化されます。



また、ログをバイナリファイルに保存することで、さまざまな種類のログにパーサーを使用する際の問題を回避できます。 必要に応じて、ログを他の形式に簡単に変換できます(これについては以下で説明します)。

ジャーナルは、syslogの両方で機能し、完全に置き換えられます。

ログを表示するには、journalctlユーティリティを使用します。 この記事では、機能を使用する際の機能と微妙な点について説明します。





時間設定





syslogの主な欠点の1つは、タイムゾーンが保存されないことです。 ジャーナルはこの欠点を解消しました。ログに記録されたイベントには、現地時間と協定世界時(UTC)の両方を指定できます。 時間は、timedatectlユーティリティを使用して設定されます。

次のコマンドを使用して、タイムゾーンのリストを表示できます。



 $ timedatectl list-timezones




目的のタイムゾーンの設定は次のとおりです。



 $ timedatectl set-timezone <タイムゾーン>


インストールが完了したら、すべてが正しく行われていることを確認すると便利です。



 $ timedatectl status
現地時間:木2015-07-30 11:24:15 MSK
世界時:木2015-07-30 08:24:15 UTC
 RTC時間:木2015-07-30 08:24:15
タイムゾーン:ヨーロッパ/モスクワ(MSK、+ 0300)
 NTPが有効:いいえ
 NTP同期:なし
ローカルTZのRTC:いいえ
アクティブなDST:n / a




最初の行(現地時間)には、正確な現在の時刻と日付が表示されます。



Journalctl:ログの表示





ログを表示するには、journalctlユーティリティを使用します。

引数なしでjournaltlコマンドを入力すると、コンソールに巨大なリストが表示されます。



 -ログは2015年7月29日水曜日17:12:48 MSKから始まり、2015年7月30日木曜日11:24:15 MSKで終わります。  -
 7月29日17:12:48 host-10-13-37-10 systemd-journal [181]:ランタイムジャーナルは4.0Mを使用しています(最大許容20.0M、195.9Mなしで30.0Mを空けようとしている→現在の制限20.0M )
 7月29日17:12:48 host-10-13-37-10 systemd-journal [181]:ランタイムジャーナルは4.0Mを使用しています(最大許容20.0M、195.9Mなしで30.0Mを空けようとしている→現在の制限20.0M )
 7月29日17:12:48 host-10-13-37-10カーネル:cgroup subsys cpusetの初期化
 7月29日17:12:48 host-10-13-37-10カーネル:cgroup subsys cpuの初期化
 7月29日17:12:48 host-10-13-37-10カーネル:cgroup subsys cpuacctの初期化
 7月29日17:12:48 host-10-13-37-10カーネル:Linuxバージョン3.16.0-4-amd64(debian-kernel@lists.debian.org)(gccバージョン4.8.4(Debian 4.8.4- 1))#1 SMP Debian 3.16.7-ckt11-1 + deb8u2(2015-07-17)
 7月29日17:12:48 host-10-13-37-10カーネル:コマンドライン:BOOT_IMAGE = / boot / vmlinuz-3.16.0-4-amd64 root = UUID = b67ea972-1877-4c5b-a328-29fc0d6c7bc4 roコンソール= tty1コンソール= ttyS0ビデオ= 640x480コンソール空白= 0パニック= 15 c




ここでは、その小さな断片のみを示しました。 実際、膨大な量のレコードが含まれています。



ログフィルタリング





journalctlユーティリティには、ログをフィルタリングし、ログから必要な情報をすばやく抽出できるオプションがあります。



現在のダウンロードのログを表示する





-bオプションを使用すると、システムの最後のブート以降に収集されたすべてのログを表示できます。



 $ journalctl -b




以前のセッションのログを表示する





journalctlを使用すると、システム内の以前のセッションに関する情報を表示できます-場合によっては便利です。

ただし、以前のセッションに関する情報の保存は、すべてのLinuxディストリビューションでデフォルトでサポートされているわけではないことに注意してください。 時々それをアクティブにする必要があります



これを行うには、journald.conf構成ファイルを開き、その中の[Journal]セクションを見つけて、storageパラメーターの値をpersistentに変更します。



 $ sudo nano /etc/systemd/journald.conf
 ...
 [ジャーナル]
ストレージ=永続的




次のコマンドを使用して、以前のダウンロードのリストを表示します。



 $ journalctl --list-boots

 0 9346310348bc4edea250555dc046b30c木2015-07-30 12:39:49 MSK —木2015-07-30 12:39:59 MSK




彼女の結論は4つのコラムで構成されています。 それらの最初はダウンロードのシリアル番号を示し、2番目はそのIDを示し、3番目は日付と時刻を示します。 特定のダウンロードのログを表示するには、1列目と2列目の両方の識別子を使用できます。



 $ journalctl -b 0




または



 $ journalctl -b 9346310348bc4edea250555dc046b30c




日付と時刻でフィルター





Journalctlには、特定の期間のログを表示する機能もあります。 これには、-sinceおよび-untilオプションが使用されます。 2015年7月20日の午後17時15分からログを表示する必要があるとします。 これを行うには、次のコマンドを実行する必要があります。

 $ journalctl --since "2015-07-20 17:15:00"




sinceオプションで日付が指定されていない場合、現在の日付から始まるログがコンソールに表示されます。 日付が指定されているが、時刻が指定されていない場合、デフォルトの時刻値「00:00:00」が適用されます。 秒もオプションです(この場合、デフォルト値は00です)。



このような人間が読める構造を使用することもできます。



 $ journalctl ---昨日から
 $ journalctl --since 09:00 --until now
 $ journalctl --since 10:00 --until "1 hours ago"




アプリケーションとサービスによるフィルタリング





特定のアプリケーションまたはサービスのログを表示するには、-uオプションを使用します。次に例を示します。



 $ journalctl -u nginx.service




上記のコマンドは、nginx Webサーバーのログをコンソールに出力します。

多くの場合、一定期間サービスのログを表示する必要があります。 これは、次の形式のコマンドを使用して実行できます。



 $ journalctl -u nginx.service-昨日から




-uオプションを使用すると、日付と時刻によるフィルタリングも使用されます。次に例を示します。



 $ journalctl -u nginx.service -u php-fpm.service —今日から




これにより、さまざまなサービスの相互作用を追跡し、それぞれのプロセスを個別に追跡することでは取得できなかった情報を受け取ることができます。



プロセス、ユーザー、グループによるフィルタリング





journalctlコマンドで識別番号(PID)を指定することで、プロセスのログを表示できます。次に例を示します。

 $ journalctl _PID = 381




特定のユーザーまたはグループに代わって起動されたプロセスのログを表示するには、それぞれ_UIDフィルターと_GIDフィルターが使用されます。 www-dataユーザーの代わりにWebサーバーが実行されているとします。 まず、このユーザーのIDを定義します。

 $ id -u www-data

 33


これで、このユーザーに代わって実行されているすべてのプロセスのログを表示できます。



 $ journalctl _UID = 33




ログにエントリがあるコンソールでユーザーのリストを表示するには、次のようにします。



 $ journalctl -F _UID




ユーザーグループの同様のリストを表示するには、次のコマンドを使用します。



 $ journalctl -F _GUID




journalctlコマンドで他のフィルターを使用できます。 次のコマンドを実行して、使用可能なすべてのフィルターのリストを表示できます。

 $ man systemd.journal-fields




パスによるフィルタリング





また、プロセスへのパスを指定することにより、プロセスのログを表示することもできます。例:



 $ journalctl / usr / bin / docker




この方法で、より詳細な情報を取得できる場合があります(たとえば、すべての子プロセスのレコードを表示する)。



カーネルメッセージを表示する





カーネルメッセージを表示するには、-kまたは−-dmesgオプションを使用します。



 $ journalctl -k




上記のコマンドは、現在のブートのすべてのカーネルメッセージを表示します。 以前のセッションのカーネルメッセージを表示するには、-bオプションを使用して、セッション識別子(リスト内のシリアル番号またはID)のいずれかを指定する必要があります。



 $ journalctl -k -b -2




エラーレベルでメッセージをフィルタリングする





システムの診断および問題の修正中に、多くの場合、ログを調べて、重大なエラーに関するメッセージが含まれているかどうかを確認する必要があります。 このために、journalctlはエラーレベルでフィルタリングする機能を提供します。 -pオプションを使用して、システムで発生したすべてのエラーに関するメッセージを表示できます。



 $ journalctl -p err -b




上記のコマンドは、システムで発生したすべてのエラーメッセージを表示します。



これらのメッセージはレベルでフィルタリングできます。 Journalは、syslogと同じエラーレベルの分類を使用します。







エラーレベルコードは、-pオプションの後に指定されます。



標準出力へのロギング





デフォルトでは、journalctlはログメッセージを表示するためにless外部ユーティリティを使用します。 この場合、テキストデータの処理に標準ユーティリティ(grepなど)を使用することはできません。 この問題は簡単に解決できます。--no-pagerオプションを使用すると、すべてのメッセージが標準出力に書き込まれます。



 $ journalctl --no-pager




その後、他のユーティリティに転送してさらに処理したり、テキストファイルに保存したりできます。



出力形式を選択





-oオプションを使用すると、ログデータをさまざまな形式に変換できます。これにより、たとえば次のような解析と追加処理が容易になります。



 $ journalctl -u nginx.service -o json

 { "__CURSOR": "S = 13a21661cf4948289c63075db6c25c00は、iが116f1 =; B = 81b58db8fd9046ab9f847ddb82a2fa2d; M = 19f0daa; T = 50e33c33587ae; X = e307daadb4858635"、 "__REALTIME_TIMESTAMP": "1422990364739502"、 "__MONOTONIC_TIMESTAMP": "27200938"、 "_BOOT_ID" : "81b58db8fd9046ab9f847ddb82a2fa2d"、 "優先度":6、_UID:0、_GID:0、_CAP_EFFECTIVE:3fffffffff、_MACHINE_ID desktop "、" SYSLOG_FACILITY ":" 3 "、" CODE_FILE ":" src / core / unit.c "、" CODE_LINE ":" 1402 "、" CODE_FUNCTION ":" unit_status_log_starting_stopping_reloading "、" SYSLOG_IDENTIFIER ":"システムMESSAGE_ID ":" 7d4958e842da4a758f6c1cdc7b36dcc5 "、" _TRANSPORT ":"ジャーナル "、" _PID ":" 1 "、" _COMM ":" systemd "、" _EXE ":" / usr / lib / systemd / systemd "、" _CMDLINE ": "/ usr / lib / systemd / systemd"、 "_SYSTEMD_CGROUP": "/"、 "UNIT": "nginx.service"、 "MESSAGE": "高性能Webサーバーとリバースプロキシサーバーの起動..."、 「_SOURCE_REALTIME_TIMESTAMP」:「1422990364737973」}




jsonオブジェクトは、json-prettyまたはjson-sse形式を指定することにより、より構造化された人間が読める形式で表すことができます。



 $ journalctl -u nginx.service -o json-pretty

 {
     「__CURSOR」:「s = 13a21661cf4948289c63075db6c25c00; i = 116f1; b = 81b58db8fd9046ab9f847ddb82a2fa2d; m = 19f0daa; t = 50e33c33587ae; x = e307daadb4858635
     「__REALTIME_TIMESTAMP」:「1422990364739502」、
     「__MONOTONIC_TIMESTAMP」:「27200938」、
     「_BOOT_ID」:「81b58db8fd9046ab9f847ddb82a2fa2d」、
     「優先度」:「6」、
     「_UID」:「0」、
     「_GID」:「0」、
     「_CAP_EFFECTIVE」:「3fffffffff」、
     「_MACHINE_ID」:「752737531a9d1a9c1e3cb52a4ab967ee」、
     「_HOSTNAME」:「デスクトップ」、
     「SYSLOG_FACILITY」:「3」、
     「CODE_FILE」:「src / core / unit.c」、
     「CODE_LINE」:「1402」、
     「CODE_FUNCTION」:「unit_status_log_starting_stopping_reloading」、
     「SYSLOG_IDENTIFIER」:「systemd」、
     「MESSAGE_ID」:「7d4958e842da4a758f6c1cdc7b36dcc5」、
     「_TRANSPORT」:「ジャーナル」、
     「_PID」:「1」、
     「_COMM」:「systemd」、
     「_EXE」:「/ usr / lib / systemd / systemd」、
     「_CMDLINE」:「/ usr / lib / systemd / systemd」、
     「_SYSTEMD_CGROUP」:「/」、
     「UNIT」:「nginx.service」、
     "MESSAGE": "高性能Webサーバーとリバースプロキシサーバーを起動しています..."、
     「_SOURCE_REALTIME_TIMESTAMP」:「1422990364737973」
 }




JSONに加えて、ログデータは次の形式に変換できます。







最近のイベントを見る





-nオプションは、システム内の最近のイベントに関する情報を表示するために使用されます。



 $ journalctl -n




デフォルトでは、コンソールには最新の10個のイベントに関する情報が表示されます。 -nオプションを使用すると、必要なイベント数を指定できます。



 $ journalctl -n 20




ログをリアルタイムで表示する





ログからのメッセージは、保存されたファイルの形式だけでなく、リアルタイムでも表示できます。 これを行うには、-fオプションを使用します。



 $ journalctl -f 




ロギング管理





ログの現在の量を決定する





時間が経つにつれて、ログの量は増加し、ハードドライブ上のスペースをますます占有します。 次のコマンドを使用して、現在利用可能なログのボリュームを確認できます。



 $ journalctl --disk-usage
ジャーナルはディスク上で16.0Mを占有します。




ログローテーション





ログローテーションは、-vacuum-sizeオプションと--vacuum-timeオプションを使用して設定されます。

最初のものは、ディスクに保存されるログの最大許容サイズを設定します(この例では1 GB):



 $ sudo journalctl --vacuum-size = 1G




ログの量が指定された数を超えると、超過したファイルは自動的に削除されます。

--vacuum-timeオプションも同様に機能します。 ログの保存期間を設定すると、ログは自動的に削除されます。



 $ sudo journalctl --vacuum-time = 1years




構成ファイルでのログローテーションの設定





ログローテーション設定は、構成ファイル/tc/systemd/journald.confで指定することもできます。このファイルには、とりわけ次のパラメーターが含まれます。







集中ログストレージ





システム管理者の作業で最も一般的なタスクの1つは、複数のマシンからのログの収集を構成し、中央のリポジトリに配置することです。

Systemdには、この問題を解決するための特別なコンポーネントsystemd-journal-remotesystemd-journal-uploadおよびsystemd-journal-gatewaydがあります。



systemd-journal-remoteコマンドを使用すると、リモートホストからログを受信して​​保存できます(これらの各ホストでsystemd-journal-gatewaydデーモンが実行されている必要があります)。例:



 $ systemd-journal-remote −−url https://some.host:19531/




上記のコマンドの結果、ホストsome.hostからのログはvar / log / journal / some.host / remote-some〜host.journalディレクトリに保存されます。



systemd-journal-remoteコマンドを使用して、ローカルマシンのログを別のディレクトリに追加することもできます。次に例を示します。



 $ journalctl -o export |  systemd-journal-remote -o / tmp / dir-




systemd-journal-uploadコマンドを使用して、ローカルマシンからリモートストレージにログをアップロードします。



 $ systemd-journal-upload --url https://some.host:19531/




上記の例からわかるように、集中ロギングをサポートする「ネイティブ」systemdユーティリティはシンプルで使いやすいです。 しかし、残念ながら、これまでのところすべてのディストリビューションには含まれていませんが、FedoraとArchLinuxにのみ含まれています。



他のディストリビューションのユーザーは、ログをsyslogまたはrsyslogに転送する必要があります。その後、ログをネットワーク経由で転送します。 公式のsystemdリポジトリに含まれるjournal2gelfユーティリティの開発者は、集中ログの問題に対する別のソリューションを提案しました。JSON形式のjournaltl出力はGELF形式に変換され、Graylogログを収集および分析するためのアプリケーションに渡されます。 この解決策はあまり便利ではありませんが、現在の状況ではこれ以上優れたものはありません。 「ネイティブ」コンポーネントがすべてのディストリビューションに追加されるのを待つだけです。



おわりに





議論からわかるように、systemdジャーナルは、システムデータとアプリケーションデータを収集するための柔軟で便利なツールです。 高度な柔軟性と利便性が達成されました。第一に、ロギングに対する集中化されたアプローチのおかげで、第二に、ログ内の詳細なメタデータの自動記録のおかげです。 journalctlを使用して、ログを表示し、作業を分析してさまざまなシステムコンポーネントをデバッグするために必要な情報を取得できます。

質問や追加がある場合-コメントへようこそ。 systemdとそのコンポーネントの議論は、今後の出版物で継続されます。



何らかの理由でここにコメントを残すことができない読者は、 私たちのブログを歓迎します



All Articles