ウィンドウズインストーラとWiX
Windows Installerはmsiの拡張子を持ったファイルで、アプリケーションのインストールパッケージとして使われる。使う利点は、インストール/アンインストールがシステムの"プログラムの追加と削除"で管理できることでしょう。特にアンインストールが保証されているのでユーザに安心してもらえる。この意味ではMSIに拘る必要はなく、対応するsetup.exeでもOKですね。
Windowsのインストーラ(MSIファイル)を作成する方法は幾つかあるみたいです。商用のSDKには付属するようですが、なるべく安価に上げたいものです。無料で利用できるものとして、Visual C# Express 2008付属のインストーラ作成機能とWiXがある。Visual Studio付属のものではsetup.exeが作られるが、実行した本人の個人環境にインストールすることしかできないみたいで、"Documents and Settings"の下の隠しディレクトリにインストールされてしまいます。その点、WiXは汎用なので申し分ないのですが、仕様が良く解らないのが難点。
WiXの使い方
ここでは、自動インストールできるだけの簡単な自動インストーラを作る。奇妙なパスを決め打ちしたりするのでなければ、ユーザも色々な設定を必要としないでしょうから。情報が少なくて、ネット上には少ししか解説がないのだけれど、その僅かな解説も、前提とされる知識が私には欠けているのか、読んでも良く分らない(こことかここ)。手っ取り早く、できているものベースで解説します。
まず、使い方。
photostand.msiを作成する場合、基本的な手順としては、
- photostand.wxsファイルを作成する。
- WiXのcandle.exe、light.exeを実行する。candleでphotostand.wxobjができ、lightでphtostand.msiができる。
コマンドラインベースのツールであり、複数に分れているのだけど、提供されている画面ライブラリを利用する場合以外は意味がないですので、バッチ処理一発にする。(パスは合わせて下さい)
これで、"wixbuild.pl photostand.wxs"とやることで"photostand.msi"を得ることができます。
wixbuild.pl
-------
#!/usr/perl/bin/perl
$Usage = "Usage: $0 file.wxs";
# print "@ARGV\n";
$Wix = "C:\\usr\\Wix\\";
if (!defined($ARGV[0]) || $ARGV[0] eq "" || $ARGV[0] !~ /\.[Ww][Xx][Ss]$/) {
print $Usage;
exit 1;
}
$Wxs = $ARGV[0];
$Obj = $Wxs;
$Obj =~ s/\.wxs/.wixobj/i;
$ret = system("${Wix}candle \"$Wxs\"");
if ($ret) {
exit 1;
}
$ret = system("${Wix}light \"$Obj\"");
exit 0;
さて、次に本題のphotostand.wxsを作成しましょう。
実のところ、中身が良く分らない。適当にいじった結果動くようになった、というのが本当のところ。間違っていると、wixbuild.plしたときにエラーが出るので、それを見て修正して下さい。
以下の例は、私が使っているphotostand.wxsです。(IDは伏せ字にしてあります)。これからビルドされるphotostand.msiで次のことができます。
- C:\Program Files\Nikep/photostandのフォルダを作成し、実行ファイルとphotostand.exeとリソースファイルen\photostand.dllを配置する。
- "全てのアプリケーション"のメニューの中に"photostand"のカテゴリーを作成し、実行ファイルのメニューを作成する。
- "スタートアップ"の中にphotostand.exeのショートカットを設置する。これにより、PC起動時に自動実行されるようになる。
- デスクトップにアイコンランチャーを表示する。
- 加えて、自動ですが、"アプリケーションの削除"メニューに"photostand"が加わり、アンインストールできるようになる。
"photostand.wxs"です。赤字は注意点で、後ろに解説があります。
<?xml version="1.0" encoding="UTF-8"?>
<Wix xmlns="http://schemas.microsoft.com/wix/2003/01/wi">
<Product Id="xxxxx-xxxxx-xxxxx-xxxxxx"
Name="Photostand" Version="2.00.0000"
Manufacturer="Nikep Software Lab." Language="1041" Codepage="932">
<Package Id="????????-????-????-????-????????????"
Description="Photostand Wallpaper Changerインストーラ"
Comments="Photostand Wallpaper Changerインストーラ" InstallerVersion="200"
Compressed="yes" Platforms="Intel" Manufacturer="nikep"
ShortNames="no" Keywords="Installer,MSI,Database"
Languages="1041" SummaryCodepage="932" />
<!--
<Condition Message="この Windows では [ProductName] のインストールはできません">
<![CDATA[VersionNT64 >= 501 Or VersionNT > 502 Or
(VersionNT = 502 And ServicePackLevel >= 1) Or
(VersionNT = 501 And ServicePackLevel >= 2) Or
(VersionNT = 500 And ServicePackLevel >= 4)]]>
</Condition>
-->
<Media Id="1" Cabinet="photostand.cab" EmbedCab="yes" />
<Directory Id="TARGETDIR" Name="SourceDir">
<Directory Id="ProgramFilesFolder" SourceName="PFILE" LongSource="Program Files">
<Directory Id="CORPORATEDIR" Name="Nikep">
<Directory Id="INSTALLLOCATION" Name="photostd" LongName="photostand">
<Directory Id="RESOURCE_EN" Name="en" />
</Directory>
</Directory>
</Directory>
<Directory Id="ProgramMenuFolder">
<Directory Id="AppMenuFolder" Name="photostd" LongName="photostand" />
</Directory>
<Directory Id="DesktopFolder"/>
<Directory Id="StartupFolder"/>
</Directory>
<DirectoryRef Id="INSTALLLOCATION">
<Component Id="photostand" Guid="yyyy-yyyy-yyyyy">
<File Id="photostand" Name="photostd.exe" LongName="photostand.exe" KeyPath="yes" DiskId="1"
Source="photostand\bin\release\photostand.exe">
<Shortcut Id="photostand" Directory="AppMenuFolder" Name="photostd" LongName="photostand"
Description="Photostand Wallpaper Changer" Show="normal" WorkingDirectory="INSTALLLOCATION" />
<Shortcut Id="photostand_dt" Directory="DesktopFolder" Name="photostd" LongName="photostand"
Description="Photostand Wallpaper Changer" Show="normal" WorkingDirectory="INSTALLLOCATION" />
<Shortcut Id="photostand_startup" Directory="StartupFolder" Name="photostd" LongName="photostand"
Description="Photostand Wallpaper Changer" Show="normal" WorkingDirectory="INSTALLLOCATION" />
</File>
</Component>
</DirectoryRef>
<DirectoryRef Id="RESOURCE_EN">
<Component Id="photostand_dll" Guid="zzzz-zzzz-zzzz-zzzz">
<File Id="photostand_dll" Name="phstden.dll" LongName="photostand.resources.dll" KeyPath="yes" DiskId="1"
Source="photostand\bin\release\en\photostand.resources.dll" />
</Component>
</DirectoryRef>
<Feature Id="photostand" Level="1" >
<ComponentRef Id="photostand" />
<ComponentRef Id="photostand_dll" />
</Feature>
<!--
<UIRef Id="WixUI_ErrorProgressText" />
<UIRef Id="WixUI_Minimal" />
-->
</Product>
</Wix>
順不動な解説です。
- Product IDの記入は必須です。
ですがこれをどこから入手すれば良いか分りません。商用SDKからなら取得できるのでしょうか。とりあえず適当に桁の合う数字を入れてクリアするしかありません。ここには、"AssemblyInfo"になにやら付いているのを使えば良いでしょう。 Guidも設定が必須です。
プロジェクトには、"AssemblyInfo"になにやら付いているのを使うとして、他のコンポーネントに付けるGuidもどこから取ってくるのか分りません。こちらも適当に設定して切り抜けます。これは分りました。GUIDに関してはこちらをご覧下さい。- Languages="1041" SummaryCodepage="932"で日本語になります。インストーラも日本語で表示されます。
- <Directory>は全てを記載しないとなりません。上記"StartupFolder"のようにシステム定義のものはダミー定義になってしまうのですが、これがないとエラーしてしまいます。
- <Component>は<DirecotryRef>の内包になるので、配置ディレクトリが異なるものは別コンポーネントにしないとなりません。(本当ですか?) この辺りのポリシーが良く分らないですねぇ。
国際化
最後に国際化の話。上記で作成したMSIファイルでインストールすると、日本語のインストール画面が出てくる。これは英語版のWindowsでも日本語になる。英語版Vistaでは日本語文言が表示されるが、英語版XPでは□□□になってしまう。でも、いずれにしても外人には理解できないですので、英語で表示されるようにしないとなりませんね。
<Package Id="????????-????-????-????-????????????"
Description="Photostand Wallpaper Changer Installer"
Comments="Photostand Wallpaper Changer Installer" InstallerVersion="200"
Compressed="yes" Platforms="Intel" Manufacturer="nikep"
ShortNames="no" Keywords="Installer,MSI,Database"
Languages="1033" SummaryCodepage="437" />
結局、LanguageとSummaryCodePageを英語にしておけば良いというのが結論です。これにより、定形の英語文言のインストーラ画面が表示されるようになります。WXSファイルの中に文言を書く場合は、それも英語にしておくことも必要です。
取り敢えずはこれでOKですが、不満もあります。アプリケーション本体は実行時に動的に言語が切り替わるのに対し、インストーラは言語毎に別ファイルを作成しないとならない。作る手間は大したことないけど、ずっと管理していかないとならないのは嫌だなぁ。自動で環境に合わせた文言を表示して欲しいものです。