Get-EventLogの使い方から覚えていこう
Powershell を活用したいと思うなら、まず、Windowsのログを確認できる Get-EventLog の使い方を覚えるのがいいと思う。このコマンドレットは、使い方を覚えたらすぐに活用できる。また、Powershellの使い方のコツを覚えるのに、非常にやりやすい。
Get-EventLog の出力結果を Select-Object にパイプで渡してフィルタをかけたり、 Format-List や Format-Table で表示を変えるたりと、非常に汎用性が高い。GUIでWindows の Log を確認するより、大幅に効率よくログの確認ができるようになる。
また、リモートで他のサーバからログを取得できたり、取得するログの条件を設定できたりと、Windows のコマンドだけではできないような操作を一行で書くこともできる。
Get-EventLogの基本的な使い方
管理者権限を持つユーザでログインしてPowerShellのプロンプトから以下のコマンドを打ち込んで実行する。
↓↓↓↓↓↓↓ あなたの記事の内容
Get-Eventlog -LogName System
───────
Get-EventLog -LogName System
↑↑↑↑↑↑↑ 編集リクエストの内容
↓↓↓↓↓↓↓ あなたの記事の内容
Get-Eventlog の後に -LogName のパラメータに表示するログを指定する。こでだけで、Winndows の System ログがそのまま出力される。Windows のイベントログには何種類かある。-LogName の後に Ctrl + Space で補完をすると、閲覧できるログの一覧が表示される。
───────
Get-EventLog の後に -LogName のパラメータに表示するログを指定する。こでだけで、Windows の System ログがそのまま出力される。Windows のイベントログには何種類かある。-LogName の後に Ctrl + Space で補完をすると、閲覧できるログの一覧が表示される。
↑↑↑↑↑↑↑ 編集リクエストの内容
PS > Get-EventLog -LogName #ここまで入力して Ctrl + Space を入力
Application Internet Explorer OAlerts System
HardwareEvents Key Management Service Security Windows PowerShell
最新のLogを表示する
Get-EventLogを実行すると大量のログが出力される。-Newest のパラメータをつけると、に指定した個数のログが、新しい順に出力される。
PS C:\Users\Main> Get-EventLog -LogName System -Newest 3
Index Time EntryType Source InstanceID Message
----- ---- --------- ------ ---------- -------
22315 1 18 11:52 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
22314 1 18 11:49 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
22313 1 18 11:48 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
# 最新の3件のログが出力される。
Get-EventLogのパラメータ
Get-EventLog で以下のパラメータが使用できる。
PS C:\Users\Main> Get-EventLog -LogName System -ComputerName
ComputerName InstanceId AsBaseObject InformationAction OutBuffer
Newest Index Verbose ErrorVariable PipelineVariable
After EntryType Debug WarningVariable
Before Source ErrorAction InformationVariable
UserName Message WarningAction OutVariable
-EntryType というパラメータを使うと、 エラーやインフォメーションなど出力するログを選ぶことができる。-EntryType の後に以下のログの種類を指定すると、指定した種類のログが出力される。
PS > Get-EventLog -LogName System -EntryType #ここでCtrl + Space を入力
Error FailureAudit Information SuccessAudit Warning
# 指定できるログの種類が表示されるので、矢印で選んで決定し、コマンドレットを実行する。
-Source や -Massage のパラメータも同様に、入力した文字列でフィルタをかけてログを出力する。文字列にはワイルドカードを使用できる。
PS > Get-EventLog -LogName System -Newest 3 -Source ser* #ser* でヒットしたログを表示
Index Time EntryType Source InstanceID Message
----- ---- --------- ------ ---------- -------
22315 1 18 11:52 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
22314 1 18 11:49 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
22313 1 18 11:48 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
これらのオプションを使えるようになると、コマンドレットでの出力に対してフィルタをかける感覚が掴めてくる。難しい書き方を覚えなくても、欲しい出力がえられるようになる。
時間帯を指定してログを出力する
Get-EventLog には -After と -Before というパラメータがある。これは、時刻を指定して、出力されるログの時間帯をフィルタリングできる。このパラメータの使い方を覚えると、他のコマンドでも時間でのフィルタする方法が分かるようになる。
まず、時刻でログをフィルタする場合は、文字列でyyyy/MM/DD hh:mm:ss
の形式で日付を指定する。
PS C:\Users\Main> Get-EventLog -LogName System -After "2020/01/18 12:00:00"
Index Time EntryType Source InstanceID Message
----- ---- --------- ------ ---------- -------
22352 1 18 19:52 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
22351 1 18 19:49 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
22350 1 18 19:47 Information Service Control M... 1073748864 Background
・
・
・
-after のパラメータで"2020/01/18 12:00:00"を指定して、"2020/01/18 12:00:00" 以降のログを取得する。ただ、所定の日付や現在の時刻から○日前のようなログを取得したい場合はどうすればいいのだろうか。まず、パラメータに渡した値が文字列なので、**[datetime]**の型を指定して、プロパティで日付を計算する。
PS > ([datetime]"2020/1/18").AddDays(-1)
#文字列の頭間に"[datetime]"を付けて日時のデータに変換する。
2020年1月17日 0:00:00
Get-Date で現在の時刻を出力すると、[datetime]の形式でデータが出力される。[datetime]を指定したのと同様に、**.AddDays()*のようなプロパティを使用することができる。書き方を覚えて動かしてみて、その後に仕組を追うと分かりやすい。
PS > (get-date).AddDays(-1)
2020年1月17日 20:07:52 #一日先の時刻になる
このやり方で日時を指定して、今日の日付で出力されたログをフィルタリングしてみる。
↓↓↓↓↓↓↓ あなたの記事の内容
PS > get-eventlog -logName system -after (get-date).AddDays(-1)
───────
PS > Get-EventLog -LogName system -after (get-date).AddDays(-1)
↑↑↑↑↑↑↑ 編集リクエストの内容
Index Time EntryType Source InstanceID Message
----- ---- --------- ------ ---------- -------
22353 1 18 19:54 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
22352 1 18 19:52 Information Service Control M... 1073748864 Background Intelligent Transfer Service サービ...
・
・
・
パラメータに -before を指定すると、指定した日付より前の日付でデータをフィルタリングする。
一般的なコマンドレットでのフィルタリング
Get-EventLog のパラメータで出力されるデータのフィルタリングを行ったが、Powershell のコマンドレットの出力は、 ? を使って以下のような書き方で出力にフィルタをかけることができる。
<コマンドレット> | ? { $_.<オブジェクトのメンバー> <演算子> <値> }
詳しい説明は省くが、まず使ってみてやり方を覚えておこう。このやり方で Get-EventLog の EntryType (ログの種類) が Error のデータをフィルタリングすると以下のようになる。
PS > Get-EventLog -LogName system | ?{ $_.EntryType -eq "Error"}
Index Time EntryType Source InstanceID Message
----- ---- --------- ------ ---------- -------
22324 1 18 19:40 Error ACPI 3221553165 : 埋め込みコントローラー (EC) が指定されたタイ...
22219 1 18 11:40 Error volmgr 3221487662 クラッシュ ダンプを初期化できませんでした。
・
・
・
? でフィルタリングをする際に、$_. の後に、Get-EventLog の出力に含まれるメンバの EntryType を指定する。コマンドレットの出力にどのようなメンバが含まれているかは、Get-Member のコマンドレットで調べることができる。
PS C:\Users\Main> Get-EventLog -LogName system -Newest 1 | Get-Member
TypeName: System.Diagnostics.EventLogEntry#system/DCOM/10016
Name MemberType Definition
---- ---------- ----------
Disposed Event System.EventHandler Disposed(System.Object, System.EventArgs)
CreateObjRef Method System.Runtime.Remoting.ObjRef CreateObjRef(type requestedType)
Dispose Method void Dispose(), void IDisposable.Dispose()
Equals Method bool Equals(System.Diagnostics.EventLogEntry otherEntry), bool Equals(Syste...
GetHashCode Method int GetHashCode()
GetLifetimeService Method System.Object GetLifetimeService()
GetObjectData Method void ISerializable.GetObjectData(System.Runtime.Serialization.Serialization...
GetType Method type GetType()
InitializeLifetimeService Method System.Object InitializeLifetimeService()
ToString Method string ToString()
Category Property string Category {get;}
CategoryNumber Property int16 CategoryNumber {get;}
Container Property System.ComponentModel.IContainer Container {get;}
Data Property byte[] Data {get;}
EntryType Property System.Diagnostics.EventLogEntryType EntryType {get;} # 今回指定したメンバ
Index Property int Index {get;}
InstanceId Property long InstanceId {get;}
MachineName Property string MachineName {get;}
Message Property string Message {get;}
ReplacementStrings Property string[] ReplacementStrings {get;}
Site Property System.ComponentModel.ISite Site {get;set;}
Source Property string Source {get;}
TimeGenerated Property datetime TimeGenerated {get;}
TimeWritten Property datetime TimeWritten {get;}
UserName Property string UserName {get;}
EventID ScriptProperty System.Object EventID {get=$this.get_EventID() -band 0xFFFF;}
フィルタリングする際に使用する演算子は、基本的なもので以下のようなものがある。
演算子 | 内容 |
---|---|
-eq | 等しいか比較 |
-ne | 等しくないか比較 |
-like | ワイルドカードを使ったLike検索にヒットするか |
-notlike | ワイルドカードを使ったLike検索にヒットしない |
-gt | より大きいか(>)比較 |
-ge | 以上か(>=)比較 |
-lt | より小さいか(<)比較(大文字小文字を区別する) |
-le | 以下か(<=)比較(大文字小文字を区別する) |
メンバーを指定して出力する
Powershellのコマンドレットでは、出力されたオブジェクトのメンバー全ての情報が画面に出力される訳ではない。Get-Member のメンバーを全て表示すると以下のようになる。
PS > Get-EventLog -LogName System -Newest 1 | Select-Object *
EventID : 10016
MachineName : horus
Data : {}
Index : 22358
Category : (0)
CategoryNumber : 0
EntryType : Warning
Message : ソース 'DCOM' のイベント ID '10016' の説明が見つかりません。必要なレジストリ情報またはメッセージを
表示するメッセージ DLL ファイルがローカル コンピューターに存在しない可能性があります。または、これ
らのデータへのアクセス許可がユーザーに与えられていない可能性があります。次の情報はイベントの一部で
す:'コンピューターの既定', 'ローカル', 'アクティブ化', '{C2F03A33-21F5-47FA-B4BB-156362A2F239}', '
{316CDED5-E4AE-4B15-9113-7055D84DCC97}', 'HORUS', 'Main', 'S-1-5-21-4290914949-3746008403-17899708
94-1001', 'LocalHost (LRPC 使用)', 'Microsoft.Windows.ShellExperienceHost_10.0.18362.449_neutral_n
eutral_cw5n1h2txyewy', 'S-1-15-2-155514346-2573954481-755741238-1654018636-1233331829-3075935687-2
861478708'
Source : DCOM
ReplacementStrings : {コンピューターの既定, ローカル, アクティブ化, {C2F03A33-21F5-47FA-B4BB-156362A2F239}...}
InstanceId : 10016
TimeGenerated : 2020/01/18 20:38:47
TimeWritten : 2020/01/18 20:38:47
UserName : HORUS\Main
Site :
Container :
Select-Object にコマンドレットの出力をパイプで渡すことで、オブジェクトのメンバーを指定して出力することができる。*(アスタリスク) を指定すれば、全てのオブジェクトが出力される。TimeGenerated と EntryType のメンバーだけを出力したい場合は以下のようにメンバを指定する。
PS > Get-EventLog -LogName System -Newest 1 | Select-Object TimeGenerated ,EntryType
TimeGenerated EntryType
------------- ---------
2020/01/18 20:38:47 Warning
コマンドレットの出力で表示したいメンバーを指定してデータをフィルタリングできれば、欲しいデータを出力できるようになる。コマンドレットの出力から必要な箇所を探すより効率的に確認することができる。
表示形式の変更
コマンドレットの出力を Format-Table にパイプで渡すと、データがテーブル形式で出力される。Format-List に渡すとリスト形式で出力される。
PS C:\Users\Main> Get-EventLog -LogName System -Newest 3 | Format-Table
Index Time EntryType Source InstanceID Message
----- ---- --------- ------ ---------- -------
22426 1 19 19:24 Information Microsoft-Windows... 44 Windows Update は更新プログラムのダウンロードを...
22425 1 19 19:24 Information Microsoft-Windows... 44 Windows Update は更新プログラムのダウンロードを...
22424 1 19 19:24 Information Microsoft-Windows... 44 Windows Update は更新プログラムのダウンロードを...
PS C:\Users\Main> Get-EventLog -LogName System -Newest 3 | Format-List
Index : 22426
EntryType : Information
InstanceId : 44
Message : Windows Update は更新プログラムのダウンロードを開始しました。
Category : (1)
CategoryNumber : 1
ReplacementStrings : {9NBLGGH3FRZM-Microsoft.VCLibs.140.00, {5f87c2b0-d4fd-4df1-97bf-5a69007f813f}, 1}
Source : Microsoft-Windows-WindowsUpdateClient
TimeGenerated : 2020/01/19 19:24:58
TimeWritten : 2020/01/19 19:24:58
UserName : NT AUTHORITY\SYSTEM
Index : 22425
EntryType : Information
InstanceId : 44
・
・
・
コンソールに表示される形は変わるが、データの内容自体は変わらない。List形式で表示された時に項目が多くなるのは、Table形式で出力されたときに画面に表示されていないメンバーが表示されているため。
Powershellでは、コマンドレットを実行したときに取得したデータが全て画面に出力される訳ではない。出力されたデータを調べる事で、欲しいデータが含まれていることがある。コマンドレットを実行して出力されるのは、結果の文字列ではなく、オブジェクトだ。これが分かると、Powershellの使い方が広がる。