プロトコル ハンドラーをインストールするには、DLL を Program Files ディレクトリ内の適切な場所にコピーし、レジストリを介してプロトコル ハンドラーを登録する必要があります。 インストール アプリケーションでは、検索ルートとスコープルールを追加して、シェル データ ソースの既定のクロール スコープを定義することもできます。
このトピックは次のように構成されています。
- URL について
- プロトコル ハンドラー インターフェイスの実装
- コンテナーのフィルター ハンドラーの実装
- プロトコル ハンドラーのインストールと登録
- アイテムのインデックスが作成されていることを確認する
- 関連トピック
URL について
Windows Search では、URL を使用して、シェル データ ソースの階層内の項目を一意に識別します。 階層内の最初のノードである URL は 、検索ルートと呼ばれます。Windows Search は検索ルートでインデックス作成を開始し、プロトコル ハンドラーが各 URL の子リンクを列挙することを要求します。
一般的な URL 構造は次のとおりです。
<protocol>:// [{user SID}/] <localhost>/<path>/[<ItemID>]
URL 構文については、次の表で説明します。
| 構文 | Description |
|---|---|
| <議定書> | URL に対して呼び出すプロトコル ハンドラーを識別します。 |
| {user SID} | プロトコル ハンドラーが呼び出されるユーザー セキュリティ コンテキストを識別します。 ユーザー セキュリティ識別子 (SID) が識別されない場合、プロトコル ハンドラーはシステム サービスのセキュリティ コンテキストで呼び出されます。 |
| <パス> | ストアの階層を定義します。各スラッシュ ('/') はフォルダー名間の区切り記号です。 |
| <ItemID> | 子項目 (ファイル名など) を識別する一意の文字列を表します。 |
Windows Search インデクサーは、URL から最終的なスラッシュをトリミングします。 そのため、最終的なスラッシュの存在に依存して、ディレクトリと項目を識別することはできません。 プロトコル ハンドラーは、この URL 構文を処理できる必要があります。 シェル データ ソースを識別するために選択したプロトコル名が、現在のものと競合していないことを確認します。
companyName.schemeという名前付け規則をお勧めします。
シェル データ ソースの作成の詳細については、「 基本的なフォルダー オブジェクト インターフェイスの実装」を参照してください。
プロトコル ハンドラー インターフェイスの実装
プロトコル ハンドラーを作成するには、次の 3 つのインターフェイスを実装する必要があります。
- UrlAccessor オブジェクトを管理するための ISearchProtocol。
- プロパティを公開し、シェル データ ソース内の項目の適切なフィルターを識別する IUrlAccessor。
- IFilter を使用して、独自のファイルをフィルター処理したり、階層的に格納されたファイルを列挙およびフィルター処理したりします。
3 つの必須インターフェイスを除き、他のインターフェイスは省略可能であり、手元のタスクに最適な任意のインターフェイスを自由に実装できます。
ISearchProtocol と ISearchProtocol2
SearchProtocol インターフェイスは、プロトコル ハンドラー UrlAccessor オブジェクトを初期化して管理します。 ISearchProtocol2 インターフェイスは、ISearchProtocol のオプションの拡張であり、ユーザーと項目に関する詳細情報を指定する追加のメソッドが含まれています。
Iurlaccessor、iurlaccessor2、iurlaccessor3、および IUrlAccessor4
IUrlAccessor インターフェイスについては、次の表で説明します。
| インターフェイス | Description |
|---|---|
| IUrlAccessor | 指定された URL の場合、 IUrlAccessor インターフェイスは、URL で公開されている項目のプロパティへのアクセスを提供します。 また、これらのプロパティをプロトコル ハンドラー固有のフィルター (つまり、ファイル名に関連付けられているフィルター以外のフィルター) にバインドすることもできます。 |
| IUrlAccessor2 (省略可能) | IUrlAccessor2 インターフェイスは、アイテムのプロパティとその表示 URL のコード ページを取得し、URL (ドキュメントまたはディレクトリ) 内のアイテムの種類を取得するメソッドで IUrlAccessor を拡張します。 |
| IUrlAccessor3 (省略可能) | IUrlAccessor3 インターフェイスは、ユーザー SID の配列を取得するメソッドで IUrlAccessor2 を拡張し、検索プロトコル ホストがこれらのユーザーを偽装してアイテムのインデックスを作成できるようにします。 |
| IUrlAccessor4 (省略可能) | IUrlAccessor4 インターフェイスは、IUrlAccessor3 インターフェイスの機能を拡張し、項目のコンテンツにインデックスを付けるかどうかを識別するメソッドを使用します。 |
UrlAccessor オブジェクトは、SearchProtocol オブジェクトによってインスタンス化および初期化されます。 IUrlAccessor インターフェイスは、次の表で説明するメソッドを使用して、重要な情報へのアクセスを提供します。
| メソッド | Description |
|---|---|
| IUrlAccessor::GetLastModified | URL が最後に変更された時刻を返します。 今回がこの URL をインデクサーが最後に処理した時刻よりも新しい場合は、フィルター ハンドラー ( IFilter インターフェイスの実装) が呼び出されて、その項目の変更されたデータが抽出されます。 ディレクトリの変更時刻は無視されます。 |
| IUrlAccessor::IsDirectory | URL が子 URL を含むフォルダーを表すかどうかを識別します。 |
| IUrlAccessor::BindToStream | カスタム データ ストア内のファイルのデータを表す IStream インターフェイス にバインドします。 |
| IUrlAccessor::BindToFilter | プロトコル ハンドラー固有の IFilter にバインドします。この IFilter は、項目のプロパティを公開できます。 |
| IUrlAccessor4::ShouldIndexItemContent | アイテムのコンテンツにインデックスを作成するかどうかを識別します。 |
IProtocolHandlerSite
IProtocolHandlerSite インターフェイスは、分離されたプロセスでホストされるフィルター ハンドラーをインスタンス化するために使用されます。 指定された永続クラス識別子 (CLSID)、ドキュメント ストレージ クラス、またはファイル名拡張子に対して、適切なフィルター ハンドラーが取得されます。 ホスト プロセスに IFilter へのバインドを要求する利点は、ホスト プロセスが適切なフィルター ハンドラーを検索するプロセスを管理し、ハンドラーの呼び出しに関連するセキュリティを制御できることです。
コンテナーのフィルター ハンドラーの実装
階層型プロトコル ハンドラーを実装する場合は、子 URL を列挙するコンテナーのフィルター ハンドラーを実装する必要があります。 フィルター ハンドラーは、 IFilter インターフェイスの実装です。 列挙プロセスは、IFilter インターフェイスのIFilter::GetChunk メソッドと IFilter::GetValue メソッドを介したループです。各子 URL は、プロパティの値として公開されます。
IFilter::GetChunk はコンテナーのプロパティを返します。 子 URL を列挙するために、 IFilter::GetChunk は次のいずれかを返します。
-
最後に変更された時刻のないアイテムの URL。 IFilter::GetValue は、子 URL を含む PROPVARIANT を返します。
PKEY_Search_UrlToIndexWithModificationTime:
URL と最後に変更された時刻。 IFilter::GetValue は、子 URL と最終変更時刻のベクターを含む PROPVARIANT を返します。
ISearchProtocol::CreateAccessor メソッドと IUrlAccessor::GetLastModified メソッドを呼び出さずに、アイテムのインデックスを作成する必要があるかどうかをインデクサーですぐに判断できるため、PKEY_Search_UrlToIndexWithModificationTimeを返す方が効率的です。
次のコード例は、 PKEY_Search_UrlToIndexWithModificationTime プロパティを返す方法を示しています。
Important
Copyright (c) Microsoft Corporation。 All rights reserved.
// Parameters are assumed to be valid
HRESULT GetPropVariantForUrlAndTime
(PCWSTR pszUrl, const FILETIME &ftLastModified, PROPVARIANT **ppPropValue)
{
*ppPropValue = NULL;
// Allocate the propvariant pointer.
size_t const cbAlloc = sizeof(**ppPropValue);
*ppPropValue = (PROPVARIANT *)CoTaskMemAlloc(cbAlloc));
HRESULT hr = *ppPropValue ? S_OK : E_OUTOFMEMORY;
if (SUCCEEDED(hr))
{
PropVariantInit(*ppPropValue); // Zero init the value
// Now allocate enough memory for 2 nested PropVariants.
// PKEY_Search_UrlToIndexWithModificationTime is an array of two PROPVARIANTs.
PROPVARIANT *pVector = (PROPVARIANT *)CoTaskMemAlloc(sizeof(*pVector) * 2);
hr = pVector ? S_OK : E_OUTOFMEMORY;
if (SUCCEEDED(hr))
{
// Set the container PROPVARIANT to be a vector of two PROPVARIANTS.
(*ppPropValue)->vt = VT_VARIANT | VT_VECTOR;
(*ppPropValue)->capropvar.cElems = 2;
(*ppPropValue)->capropvar.pElems = pVector;
PWSTR pszUrlAlloc;
hr = SHStrDup(pszUrl, &pszUrlAlloc);
if (SUCCEEDED(hr))
{
// Now fill the array of PROPVARIANTS.
// Put the pointer to the URL into the vector.
(*ppPropValue)->capropvar.pElems[0].vt = VT_LPWSTR;
(*ppPropValue)->capropvar.pElems[0].pwszVal = pszUrlAlloc;
// Put the FILETIME into vector.
(*ppPropValue)->capropvar.pElems[1].vt = VT_FILETIME;
(*ppPropValue)->capropvar.pElems[1].filetime = ftLastModified;
}
else
{
CoTaskMemFree(pVector);
}
}
if (FAILED(hr))
{
CoTaskMemFree(*ppPropValue);
*ppPropValue = NULL;
}
}
return S_OK;
}
注
コンテナー IFilter コンポーネントは、子 URL が変更されていない場合でも、すべての子 URL を常に列挙する必要があります。これは、インデクサーが列挙プロセスを通じて削除を検出するためです。 PKEY_Search_UrlToIndexWithModificationTimeの日付出力でデータが変更されていないことが示されている場合、インデクサーはその URL のデータを更新しません。
プロトコル ハンドラーのインストールと登録
プロトコル ハンドラーをインストールするには、プログラム ファイル ディレクトリ内の適切な場所に DLL をコピーし、DLL を登録する必要があります。 プロトコル ハンドラーは、インストールのために自己登録を実装する必要があります。 インストール アプリケーションでは、検索ルートとスコープ ルールを追加してシェル データ ソースの既定のクロール スコープを定義することもできます。これについては、このトピックの最後にある 「アイテムのインデックス作成の確認 」で説明されています。
プロトコル ハンドラーを登録するためのガイドライン
プロトコル ハンドラーを登録するときは、次のガイドラインに従う必要があります。
- インストーラーでは、EXE または MSI インストーラーを使用する必要があります。
- リリース ノートを指定する必要があります。
- インストールされているアドインごとに、[プログラムの追加と削除] エントリを作成する必要があります。
- インストーラーは、特定のファイルの種類または現在のアドインが認識するストアのすべてのレジストリ設定を引き継ぐ必要があります。
- 以前のアドインが上書きされている場合、インストーラーはユーザーに通知する必要があります。
- 新しいアドインが以前のアドインを上書きした場合は、以前のアドインの機能を復元し、そのファイルの種類の既定のアドインにし直す機能が必要です。
- インストーラーでは、検索ルートを追加してインデクサーの既定のクロール スコープを定義し、クロール スコープ マネージャー (CSM) を使用してスコープ ルールを定義する必要があります。
プロトコル ハンドラーの登録
プロトコル ハンドラー コンポーネントを登録するには、レジストリに 14 個のエントリを作成する必要があります。
- Ver_Ind_ProgID は、プロトコル ハンドラー実装のバージョンに依存しない ProgID です。
- Ver_Dep_ProgID は、プロトコル ハンドラー実装のバージョンに依存する ProgID です。
- CLSID_1 は、プロトコル ハンドラー実装の CLSID です。
プロトコル ハンドラーを登録するには:
バージョンに依存しない ProgID を次のキーと値に登録します。
HKEY_CLASSES_ROOT <Ver_Ind_ProgID> (Default) = <Protocol Handler Class Description>HKEY_CLASSES_ROOT <Ver_Ind_ProgID> CLSID (Default) = {CLSID_1}HKEY_CLASSES_ROOT <Ver_Ind_ProgID> CurVer (Default) = <Ver_Dep_ProgID>バージョンに依存する ProgID を次のキーと値に登録します。
HKEY_CLASSES_ROOT <Ver_Dep_ProgID> (Default) = <Protocol Handler Class Description>HKEY_CLASSES_ROOT <Ver_Dep_ProgID> CLSID (Default) = {CLSID_1}プロトコル ハンドラーの CLSID を次のキーと値に登録します。
HKEY_CLASSES_ROOT {CLSID_1} (Default) = <Protocol Handler Class Description>HKEY_CLASSES_ROOT {CLSID_1} {InprocServer32} (Default) = <DLL Install Path> Threading Model = BothHKEY_CLASSES_ROOT {CLSID_1} <ProgID> (Default) = <Ver_Dep_ProgID>HKEY_CLASSES_ROOT {CLSID_1} <ShellFolder> Attributes = dword:a0180000HKEY_CLASSES_ROOT {CLSID_1} TypeLib (Default) = {LIBID of PH Component}HKEY_CLASSES_ROOT {CLSID_1} VersionIndependentProgID (Default) = <Ver_Ind_ProgID>プロトコル ハンドラーを Windows Search に登録します。 次の例では、 <Protocol Name> はプロトコル自体の名前 (ファイル、mapi など) です。
HKEY_LOCAL_MACHINE SOFTWARE Microsoft Windows Search ProtocolHandlers <Protocol Name> = <Ver_Dep_ProgID>HKEY_CURRENT_USER SOFTWARE Microsoft Windows Search ProtocolHandlers <Protocol Name> = <Ver_Dep_ProgID>Windows Vista より前のバージョン:
HKEY_CURRENT_USER SOFTWARE Microsoft Windows Desktop Search DS Index ProtocolHandlers <Protocol Name> HasRequirements = dword:00000000 HasStartPage = dword:00000000
プロトコル ハンドラーのファイル型ハンドラーの登録
プロトコル ハンドラーのファイルの種類ハンドラー (シェル拡張機能とも呼ばれます) を登録するには、レジストリに 2 つのエントリを作成する必要があります。
-
HKEY_LOCAL_MACHINE SOFTWARE Microsoft Windows CurrentVersion Explorer Desktop NameSpace {CLSID of PH Implementation} (Default) = <Shell Implementation Description> -
HKEY_LOCAL_MACHINE SOFTWARE Microsoft Windows CurrentVersion Explorer Shell Extensions Approved {CLSID of PH Implementation} = <Shell Implementation Description>
アイテムのインデックスが作成されていることを確認する
プロトコル ハンドラーを実装したら、プロトコル ハンドラーがインデックスを作成するシェル項目を指定する必要があります。 カタログ マネージャーを使用してインデックスの再作成を開始できます (詳細については、 カタログ マネージャーの使用を参照してください)。 または、クロール スコープ マネージャー (CSM) を使用して、インデクサーでクロールする URL を示す既定のルールを設定することもできます (詳細については、「 クロール スコープ マネージャーの使用 と スコープ ルールの管理」を参照してください)。 検索ルートを追加することもできます (詳細については、「 検索ルートの管理」を参照してください)。 使用できるもう 1 つのオプションは、 Windows Search コード サンプルの ReIndex サンプルの手順に従う方法です。
ISearchCrawlScopeManager インターフェイスには、クロールや監視を行うコンテナーの検索エンジンに通知するメソッドと、クロールまたは監視時に含めるか除外するコンテナーの下の項目が用意されています。 Windows 7 以降では、ISearchCrawlScopeManager2 は、バージョンを取得する ISearchCrawlScopeManager2::GetVersion メソッドを使用して ISearchCrawlScopeManager を拡張し、CSM の状態が変更されたかどうかをクライアントに通知します。
関連トピック
-
概念的