スクリプトに署名したいけれど、証明書を取得するのにお金をかけたくない場合は自己署名証明を作成することで解決できます。
自分に対する覚え書きという意味合いも込めて、その方法を公開いたします。
下記順番で説明します
自己署名証明書作成ツール
自己署名証明書を作成するには makecert.exe というツールを使用します。
このツールは、Visual Studio.NETをお持ちの方であれば、すでにインストールされています。
もしVisual Studio.NETを持っていないのであれば、無償のSDKをインストールすることで手に入れることができます。
(というかできるはずです。というのも自分はVisual Studioを有しており無償のSDKによる確認は行っていないからです)
今回はVisual Studio 2008 コマンドプロンプトを使用して、makecert.exeを実行する手順を紹介します。
なおOSはXPを使用しましたがVistaやWindows7でも同様の手順でいけると思います。(これもまた未確認です。すみません)
ローカル証明機関の作成方法
まずは、[スタート]-[すべてのプログラム]-[Microsoft Visual Studio 2008]-[Visual Studio Tools]-[Visual Studio 2008 コマンドプロンプト]を起動します。
そして、次のコマンドを入力します。
makecert -n "CN=PowerShell Local Certificate Root" -a sha1 -eku 1.3.6.1.5.5.7.3.3 -r -sv root.pvk root.cer -ss Root -sr localMachine
上記のコマンドを実行すると数のようにパスワードの入力を求められますが、空のままで OKを押します。
すると、「パスワードで保護されません。よろしいですか?」と聞かれるので、ここでは「いいえ」を選択します。
コマンドの実行が成功すると「Succeeded」と表示されます。
再度証明機関を作成し直したい場合の手順も記しておきます。
先ほどのコマンドを実行すると makecert を実行したディレクトリに root.pvk と root.cer という2つのファイルが作成されます。
この2つを削除すれば、最初からやり直すことが可能です。
署名証明書の作成方法
自己署名機関が作成されたので、次は自分宛に署名証明書を発行する必要があります。
これには、Visual Studio 2008 コマンドプロンプトで、次のように入力して実行します。
makecert -pe -n "CN=PowerShell User" -ss MY -a sha1 -eku 1.3.6.1.5.5.7.3.3 -iv root.pvk -ic root.cer
コマンドの実行が成功すると、こちらも「Succeeded」と表示されます。
ここまで成功したら、PowerShellを起動して、次のコマンドを実行してみましょう。
PS> dir cert:\CurrentUser\My
証明書が作成されていれば、次の図のようにサムプリントが表示されます。
スクリプトへの署名方法
スクリプトに署名するには、証明書オブジェクトを取得する必要があります。
これにはPowerShell上で次のようにコマンドを入力します。[0]というのは証明書が1つしかない場合です。複数ある場合は必要な証明書を示す番号に変更します。
PS> $cert = @(dir cert:\CurrentUser\My -CodeSigningCert)[0]
この時点で、取得した証明書オブジェクトは$cert変数に入っています。
最後に、この証明書オブジェクトを使用して、スクリプトに署名します。
PS> Set-AuthenticodeSignature SampleScript.ps1 $cert
おまけ:スクリプトへの署名する関数
スクリプトに署名するために、毎回先ほどのようなコードを入力するのは面倒なので、関数としてまとめました。このコードは以前、[Tips]任意のファイルにデジタル署名するで紹介したものです。
#===============================================================================
# Set-Cert: 指定したファイルにデジタル署名を行う
#
# 使用例:
# PS > Set-Cert ./Test.ps1
#
# copyright PowerShell from Japan!!(http://powershell.hiros-dot.net/)
#
#===============================================================================
function global:Set-Cert([string]$path)
{
try
{
$cert = Get-ChildItem cert:\CurrentUser\My -CodeSigningCert | ?{$_.Subject -match "PowerShell User"}
Set-AuthenticodeSignature -FilePath $path -cert $cert
"デジタル署名に成功しました"
}
catch [Exception]
{
"デジタル署名に失敗しました"
}
}
使用方法は次の通りです。
PS > Set-Cert "デジタル署名するファイルのパス"
*この関数は PowerShell User という名前の証明書がある前提で作成しています。