うっかりはまって半日以上潰しました。
その顛末を書きます。
ADSI経由でIISの仮想ディレクトリをASP.NETで実行可能な状態に作成するプログラムを書いていました。
で、どこから引いてきたかも忘れたサンプルソースを頼りに、こんなコードを書いてみました。
using( DirectoryEntry VDir = IISAdmin.Children.Add(vDirName, "IIsWebVirtualDir") )
{
VDir.Properties["AccessRead"][0] = true;
VDir.Properties["AccessExecute"][0] = true;
VDir.Properties["AccessWrite"][0] = false;
VDir.Properties["AccessScript"][0] = true;
VDir.Properties["EnableDefaultDoc"][0] = true;
VDir.Properties["Path"][0] = physicalPath;
VDir.Properties["AppIsolated"][0] = (System.Int32)2;
VDir.CommitChanges();
VDir.Invoke("AppCreate", false);
}
ところが、AppIsolatedの値(2)だけが設定されません。
この値を設定することにより、IISの管理ダイアログで見たとき、アプリケーション保護と表記された部分を「中(プール)」にしたいのですが、そうなりません。
(System.Int32)2がいけないのか。他のサンプルソースではキャスト無しで2と書いたものもあるし。それとも本当は"2"なのか、等と悶々といろいろ調べていたのですが。
全く筋違いの勘違いに始まる調査で、InvokeされているAppCreateの説明を読んでいるうちに、はたと気付きました。こいつの引数は、AppIsolatedと同じ趣旨のように見えるじゃないか。ただ、指定可能な種類がAppIsolatedよりも少なく見えます。(AppIsolatedは3種類。この引数は2種類)
つまり、AppCreateはAppIsolatedに値を書き込む効能があるはずだ、と気付きました。ですから、いくらAppIsolatedの値を書き込もうとも、その後でAppCreateをInvokeすれば上書きされて消失。
と言うことは、対策は簡単。AppCreateをInvokeしたあとで、AppIsolatedを設定してCommitChangesを呼んでコミットしてやるだけ。
以下のようなコードで上手く行ったようです。
using( DirectoryEntry VDir = IISAdmin.Children.Add(vDirName, "IIsWebVirtualDir") )
{
VDir.Properties["AccessRead"][0] = true;
VDir.Properties["AccessExecute"][0] = true;
VDir.Properties["AccessWrite"][0] = false;
VDir.Properties["AccessScript"][0] = true;
VDir.Properties["EnableDefaultDoc"][0] = true;
VDir.Properties["Path"][0] = physicalPath;
VDir.CommitChanges();
VDir.Invoke("AppCreate", false);
VDir.Properties["AppIsolated"][0] = (System.Int32)2;
VDir.CommitChanges();
}
余談。AppCreateの引数の型は? §
AppCreateの引数の型も、BooleanなのかIntegerなのか、良く分からないところがあったり……。それも悩ましい……。MSDN Libraryで調べる限りBooleanのように読めるのですが、スキーマを見るとIntegerと書いてあったり。