Extension:LuceneSearch/ja

この拡張機能は何ができるのか？
Luceneに基づく全文検索. 機能:
 * 分散型の検索/索引作業
 * 訛りのない検索、12の言語のためのstemmers
 * ランキングのためのリンク解析
 * 名前空間が接頭辞のクエリー

ソフトウェアは2つの機能に分割されます. 最初はlsearchデーモン、すべての検索作業と索引作業を行います. もう一つはMediaWiki拡張機能で、デーモンのためのMediaWiki専用のインターフェイスです.

MediaWiki拡張機能をインストールする
LocalSettings.phpに設置して下さい. wgLuceneHostはホストの配列になります.

検索(名前空間)接頭辞を使う
検索は標準的な名前空間もしくはローカライズした名前空間を接頭辞として持ちます. 例えば、次の文字列を検索ボックスに入力して下さい: help:images "images"の単語の存在に関して"Help"名前空間を検索します. allという特別な接頭辞もあります. これは検索エンジンにすべてを検索するよう支持します(デフォルトでは"main"名前空間のみが検索されます).

名前空間とコロンの間にスペースは許可されないことに注意して下さい.

複数の名前空間を検索する場合、例えばhelp,project:imagesのようにカンマで名前を区切って下さい.

名前空間の接頭辞をカスタマイズする
異なる名前空間を結びつけるカスタムの接頭辞を指定するためには、 MediaWiki:Searchaliasesを編集して下さい. サンプルのエントリは次の通りです:

wp|Project all_talk|Talk,User_talk,Image_talk,MediaWiki_talk,Template_talk,Help_talk,Category_talk

So, 構文は次の通りです: "alias|&lt;list of namespaces&gt;" per line. MediaWiki:searchallを編集して一行ごとにローカライズした名前を追加することでallキーワードをローカライズして下さい.

LSearchデーモンをインストールする
要件: Linux、Java 5、Apache Ant 1.6、Rsync (分散アーキテクチャのため) Windowsユーザーのための注: バージョン2.0からLSearchデーモン はWindowsプラットフォームをサポートしません(ハードとソフトファイルリンクを使うため). C#で書かれた古いデーモンを利用できます. インストール方法のインストラクションは次の記事です: Installing lucene search.

システムのサイズによって、典型的なインストール作業のシナリオがいくつかあります.

単独のホストのセットアップ
多くの場合単独のホストは索引作業と検索作業の両方を取り扱うことができるようになります. 検索作業はメモリーが不足になりことがよくあり、メモリーにバッファアップされるインデックスを少なくとも半分持つことがグッドプラクティスです. インデックスが利用できるメモリーよりも2x以上である場合、重大なパフォーマンスの劣化を経験することになるので、分散検索を考慮すべきです.

一般的に、検索インデックスは対応するxmlデータベースダンプよりも約3-5倍小さいです.

分散アーキテクチャの簡単なメンテナンスのために、設定は2角部分に分割されます: グローバルとローカルです. 単独のホストのインストレーションではそれらの両方をセットアップする必要があります:

ローカルの設定:
残りのプロパティに関してはデフォルトの値のままにできます.
 * 1) lsearchデーモンのコピーを入手し、例えば/usr/local/search/ls2/に展開して下さい SVNからダウンロードした場合、 mwdumper.jarも必要で、例えば/usr/local/search/ls2/libに設置します
 * 2) インデックスが保存されるディレクトリを作って下さい. 例えば/usr/local/search/indexesです.
 * 3) lsearch.confファイルを編集して下さい:
 * 4) * MWConfig.global - ここにグローバル設定ファイルのURLを設置する(下記を参照)、例えばfile:///etc/lsearch-global.conf
 * 5) * MWConfig.lib - ここのローカルパスをlibディレクトリに設置して下さい、例えば/usr/local/search/ls2/libです
 * 6) * Indexes.path - インデックスを保存するデーモンが必要であるベースのパス、例えば/usr/local/search/indexes
 * 7) * Localization.url - MediaWikiメッセージファイルへのURL、例えばfile:///var/www/html/wiki/phase3/languages/messages
 * 8) * Logging.logconfig - log4js設定ファイルへのローカルパス、 例えばe.g. /etc/lsearch.log4j (the lsearch SVN has a sample log4j file you can use called lsearch.log4j-example)

グローバル設定はデーモンにデータベース、とネットワークのセットアップを伝えます.

グローバルな設定

 * lsearch-global.confファイルを編集して下さい:
 * Databaseのセクション: いくつかのデータベースを追加します(MediaWikiのデータベース名は$wgDBnameです).

[Database] wikilucene : (single) (language,en) (warmup,0) wikidev : (single) (language,sr) wikilucene : (nssplit,3) (nspart1,[0]) (nspart2,[4,5,12,13]), (nspart3,[]) wikilucene : (language,en) (warmup,10) wikidb : (single) (language,en) (warmup,10)


 * where: wikidb : (single) (language,en)はwikidbが単独の(非分散の)インデックスであることと英語をデフォルトの言語として使うので、英語のstemmingを使うことを宣言します. 加えて、プロパティ(warmup,100)'も追加できるので、これはアップデートされたバージョンが取得されたときインデックスをウォームアップするためにサーチャーにバックグラウンドで100のクエリーを適用するように支持します. これによってパフォーマンスにおけるスムーズな移行が可能になりインデックスは常によくキャッシュされバッファされることを保証します.
 * 重要: 引数にスペースがないことを確認して下さい(例えば(warmup,10))この条件はインデックスを構築するときに検索、スナップショットを作成もしくはインデックスフォルダを作ることが失敗してしまうことにつながります.


 * Search-group セクション: 検索作業とwikidbの索引作業に関してホストを宣言する

[Search-Group] localhost : wikidb
 * 1) 検索グループ
 * 2) Index parts of a split index are always taken from the node's group
 * 3) host : db1.part db2.part
 * 4) 複数のホストは複数のDBSを検索できる(N-Nマッピング)
 * 1) oblak : wikilucene wikidev+
 * Replace oblak with your localhost name.
 * 重要: localhostではなく、環境変数$HOSTNAMEにあるようなホスト名を正確に使って下さい.


 * Indexのセクション: (上記と同じ)
 * オプションとして、カスタムの名前空間をNamespace-Prefixセクションに追加して下さい

その他のプロパティに関してはデフォルトの値のままにできます.

次に、antを起動してLuceneSearch.jarをビルドする、もしくはバイナリリリース(現在著者からのみ入手可能)が手に入る場合、./lsearchdでデーモンを起動させるだけです. javaをpathに設定する必要があることに注意して下さい.

インデックスを構築する
インデックスを最新に保つ最もシンプルな方法は定期的にリビルドすることです. cronjobに加えるか、インデックスをリビルドして一定の時間が経過したらsleepするスクリプトを作ることができます.

インデックスをビルドするため、データベースのXMLダンプが必要になります(dumpBackup.phpを使って下さい). XMLダンプを作成するためにAdminSettings.phpをセットアップする必要があります. それからインデックスをリビルドするために、Importerヘルパーツールを使って下さい. コードサンプルです: (ダンプファイルパスを調整したい場合など..) php maintenance/dumpBackup.php --current --quiet > wikidb.xml && java -cp LuceneSearch.jar org.wikimedia.lsearch.importer.Importer -s wikidb.xml wikidb

ImporterはXMLダンプをインポートしてインデックスのスナップショット(-sオプション)を作ります. インデックスのスナップショットはlsearchデーモンによってピックアップされ(インデックスのスナップショットを周期的にチェックします) インデックスのワーキングコピーは更新されます. lsearchデーモンのためのインデックスは標準的な位置に保存されます. /usr/local/search/indexesがrootのインデックスパスの場合、indexes/snapshotはスナップショットを含み、indexes/searchは現在のインデックスのワーキングコピーを含み、以前のワーキングコピーとインデックスの更新をインデックス化/更新など..

それでお終いです. MWの拡張機能を正しくセットアップしたいのであれば、検索とインデックスを更新できるようになります.

トラブルシューティング
複数のコンポーネントが関係しているため、getting LuceneSearchを起動させることと実行することが難しいことがあり得ます. ちょっとしたノートです:


 * curlをPHP本体に導入している場合、結果を返すスクリプトのためにそれらは順序よく動作しなければなりません. さもなければ検索が失敗したと通知されます.
 * データベース(上記の説明では"wikidb")はインデックスが保存されるwikiのMySQL(もしくはその他)にマッチしなければなりません.
 * 実際に検索失敗の通知が表示されたら、lsearchdの出力を確認して下さい. デフォルトのlog4j構成でデーモンを始めたとしたら、これはデーモンを始めたコンソールで見つかります. エラーメッセージを得たら、Javaの例外(ArrayIndexOutOfBoundsException, NullPointerException)も含めて、不一致や間違いに関してすべての構成設定を注意深く徹底的に調べて下さい.
 * lsearchdの出力に間違いが見つからなかったら、How to debug/jaで説明されているようにMediaWikiのログをonに切り替えて下さい.
 * 内部では、LuceneSearch拡張機能はHTTPリクエストを通してLuceneデーモンにクエリーを行います. You'll be able to see the URL requested by looking in the MediaWiki log output. Luceneサイドが動作していることをテストするために、このURLをウェブブラウザに入力して訪問してみて下さい. 検索結果のテキストリストが手に入るのであれば、それは動いています. 層ではない場合、これによって何が間違っているのかがわかります.

インクリメンタルなアップデート
定期的なインデックスのリビルドがデータベースに過負荷を与えていると思うのであれば、インクリメンタルアップデーターを使うことができます. そのためには追加の作業が必要です: php maintenance/dumpBackup.php --current --quiet > wikidb.xml && java -cp LuceneSearch.jar org.wikimedia.lsearch.ranks.RankBuilder wikidb.xml wikidb
 * 1) Install OAI extension for MediaWiki. この拡張機能は最新の記事を取得するインクリメンタルアップデーターを有効にします.
 * 2) 例えばlsearchdbのような新しいMySQLのデータベースを作り、それがUTF-8のデータベースであることを確認して下さい. それは記事のランキングデータを保存するために必要です. このデータはインポートするたびにインポーターによって通常再計算されます.
 * 3) ローカル構成(lsearch.conf)のStorageセクションをセットアップして下さい. MySQL DBに対してユーザーと管理者のパスワードを入力して下さい. 管理者のパスワードはテーブルの作成などに必要です.
 * 4) 記事のランクデータをリビルドし、週もしくは月に一回のcronジョブを設定して下さい(記事のランクは大抵非常に遅く変わります):
 * 1) 初期のバージョンのインデックスを作って下さい - 以前のセクションで説明されたインポーターを使ってこの作業を行うことができます

最後に、グローバルコンフィグ(lsearch-global.conf),において、インクリメンタルアップデーターに対してOAIをセットアップし、dbname : hostのマッピングをセットアップし, ローカル設定でOAI.username/passwordが存在するのであればそれにユーザー名/パスワードを入力して下さい. 次のコマンドでインクリメンタルアップデーターを始めて下さい: java -cp LuceneSearch.jar org.wikimedia.lsearch.oai.IncrementalUpdater -n -d -s 600 -dt start_time wikidb パラメータは以下の通りです:
 * -n - 記事が首尾良く追加されるindexerからの通知を待つ
 * -d - デーモン化、すなわち、無限ループでアップデートを実行する
 * -s 600 - after one round of updates sleep 10 minutes (600s)
 * -dt timestamp - デフォルトのタイムスタンプ (e.g. 2007-06-17T15:00:00Z) - これは初期のインデックスビルドのタイムスタンプです. インクリメンタルアップデーターを始める最初のときにこのパラメータを渡す必要があるので、so it knows from what time to start the updates. 後でインクリメンタルアップデーターは最後の成功したアップデートのタイムスタンプをindexes/status/wikidbに保存します.

(2)、(3)と(4)への代わりはランキングを使わないことです. --no-ranksパラメータをインクリメンタルアップデーターに渡すことでこれを行うことができ、そうすればMySQLデータベースからランクを取得しようとしません. wikiが小さくて数百ページしかないのであれば、おそらくランキングは必要ないでしょう. しかし数十万のページを持つもしくは計画しているのであれば、ランキングデータから確かな恩恵がもたらされます.

これまでのところインデックスをインクリメンタルなアップデートすることのみをなんとかしました. 周期的にインデックスのスナップショット(サーチャーによって取得されます)を作るようにインデクサー(indexer)に指示するために、これをcronジョブに追加して下さい: curl http://indexerhost:8321/makeSnapshots

Indexerはhttpインターフェイスのコマンドを持ちます. その他のコマンドはgetStatus、flushAll、などです.

分散アーキテクチャ
共通のdistributionは多くのsearcher/one indexerアプローチです. グローバル構成ファイル(lsearch-global.conf)をっざっと見ると、検索をdistributeする方法は明らかなです. さらにhost : dbname マッピングを追加しそれらのホストでlsearchdを起動させる必要があるだけです. しかしながら、サーチャーはインデックスを取得し更新できるようになることが必要です. ですので:
 * 1) indexerのホスト上でrsyncd.confをセットアップしrsyncデーモンをスタートさせます(SVNにサンプルの構成ファイルがあります)
 * 2) indexerホスト上のrsyncのパスをグローバル構成のIndex-Pathセクションに追加して下さい.

すべて(searchersとindexer)を再起動するとそれらはお互いを認知するので、searcherは割り当てられたインデックスの更新を定期的にチェックします. indexerのホストでImporterを実行する必要がありますが、どのホストでもIncrementalUpdaterを実行できます. なぜならグローバル構成ファイルからindexerがどこにあるのかわかるからです.

インデックスを分割する
インデックスが大きすぎて、メモリーに収まらない場合、より小さな部分に分割したいと思うことがあります. これを行う方法はたくさんあります. 最もシンプルな方法はmainsplitを行うことです. これはインデックスを2の部分に分割します. 一つはmain名前空間にあるすべての記事を含み、もう一つは残りの記事すべてです. nssplitも行うことができます. これはどの名前空間の組み合わせによってもインデックスを分割します. 最後に、ランダムのドキュメントをNインデックスの部分の一つに割り当てるsplit アーキテクチャがあります. パフォーマンスの観点から名前空間でインデックスを分割することがベストで、可能であるならmainsplitです. ほとんどのユーザーがmain名前空間のみを検索することを前提とするならこれがベストです.

インデックスを複数のホストに分割する場合、使い方はロードバランスになります. 例えばすべての検索で求められるインデックス部分を持つ異なるホストの組み合わせが検索されます. MediaWiki Lucene Search拡張機能はこれを気にする必要はありません. いくつかの部分のインデックスを持つホストにリクエストをするだけです.

パッケージのlsearch-global.confにこれらのインデックスアーキテクチャの使い方の例があります.

パフォーマンスのチューニング
lucene indexerのデフォルトの値は最小のメモリー使用量とセグメントの最小数を促進します. しかしながら、indexingはこのため非常に遅くなることがあります. デフォルトは10のバッファされたドキュメントと2のマージファクターです. これらの値を増やしたいことがあります. 例えば500のバッファされた度球面ｔと20のマージファクターです. グローバル構成でこれを行うことができます. 例えばwikidb : (single,true,20,500)です. バッファされたドキュメントのかすの増加によってすぐにヒープを平らげてしまうことに注意して下さい. 異なる値を試してみてメモリーのプロファイルに対して何がベストなのかを見ることがベストです.

複数のCPUホストでサーチャーを実行する場合、ローカルコンフィグファイルでSearcherPool.sizeを調整したい場合があります. プールサイズはインデックスごとのIndexSearchersの数に対応します. 少なくともCPUの数もしくはよりベターなCPU+1の数に設定する必要があります. これによってCPUが単独のRandomAccessFileインスタンスを通してアクセスすることでお互いにロッキングすることを防止します.

関連項目

 * Setting up OAI