Step By Step

30代会社員。人生を一歩ずつ、歩いています。

【スポンサーリンク】

PowerShellで日付と時刻ログ出力を改行させない方法

Windows7から標準搭載されているPowerShellは、スクリプト言語でありながら、一般的なデータ構造や標準で便利なコマンドが用意されていたりと、いろんなことができるのが魅力なツールです。
なによりも、実行環境が標準搭載されているというのが便利ですね。PowerShellスクリプトを開発・実行する環境を用意しなくても、WindowsOSを使っていれば誰でもすぐに利用可能という手軽さです。PowerShell自体は独立したソフトウェアなので、Macにもインストールできます。

今回はなぜかググってもあまり見当たらない、日付と時刻をログ出力する方法について説明してみます。

基本的には、Start-transcriptを使おう

ログ出力内容に特にこだわりがなければ、ひとまずStart-transcriptを使っておけば間違いないでしょう。このコマンドレットを使うと、コンソールに出力される内容が全て記録されます。今回はStart-transcriptの解説がメインではないので、詳細は割愛します。

ログ出力したければStart-transcriptを使う、これで終了かと思うじゃないですか。ところがどっこい、このコマンドレットはいかんせん「情報が多すぎる」うえに、「整形されていない」のです。

ログ出力の際は情報が少なすぎると何もわからないので、基本的には多すぎたほうがまだマシなのですが、ちょっとしたスクリプトを書く際にがっつりログ出力されてしまうと見にくいことこの上ないのです。

情報が多すぎるときは、自前でログ出力する

ではどうするかというと、Write-Outputでログ出力内容をコントロールするのです。これなら、ログ出力したい内容を続けて書くだけで、その内容が指定したログファイルに出力されます。ただしログファイルで重要な「日付と時刻」の出力にはちょっと工夫が必要です。

Write-Outputでは変数の展開で改行されてしまう

実際に試してみるとわかりますが、Write-Outputコマンドレットは変数を出力したタイミングで改行されてしまいます。Write-Hostではそんなことはないので、なかなか気づきにくいですが。
例えば以下のコードでは、変数str1とstr2の間で改行が挟まれます。

$str1 = "改行"
$str2 = "されちゃうなあ"
Write-Output $str1 $str2 >> ./test.log
# test.logをみると出力はこうなる↓
# 改行
# されちゃうなあ

これを回避するには、Write-Outputでの出力内容をまるっとダブルクォートにしてしまって、文字列として扱います。

$str1 = "改行"
$str2 = "されちゃうなあ"
Write-Output "${str1} ${str2}" >> ./test.log
# test.logをみると出力はこうなる↓
# 改行 されちゃうなあ

文字列中で変数を展開するには、PowerShellでは変数を${}でくくるか、$()でくくります。
$()でくくった場合は、()内部の式を評価した結果が展開されます。

改行させない日付と時刻は(Get-Date).toString(<指定の書式>)で出力すればいい

これを応用すると、ログ出力内容の先頭に日付と時刻を出力して、かつ改行させないという方法が実現できます。
具体的にはこんな感じで書きます。

$str1 = "改行"
$str2 = "されちゃうなあ"
Write-Output "$( (Get-Date).toString('yyyy-MM-dd HH:mm:ss.fff') ) ${str1} ${str2}" >> ./test.log
# test.logをみると出力はこうなる↓
# 2019-03-28 22:47:29.082 改行 されちゃうなあ

Get-Dateは日付を表すオブジェクト(正確には.NET FrameworkのSystem.DateTimeオブジェクトです)、toStringはその文字列表現です。シングルクォートで囲って書式を指定しています。

ここはダブルクォートで囲っても良いのですが、先頭のダブルクォートが閉じられていると誤解しやすいので、シングルクォートとしています。

Get-Dateを()でくくっているのは、Get-DateオブジェクトをtoStringで文字列表現化した結果を表示したいからです。

文字列中の変数展開についてはこちらの記事がわかりやすいので、合わせてどうぞ。

ではでは。