Solr9のkuromojiでUniDic2.1.2を使う
概要
Solr9.1のkuromojiでUniDic2.1.2を使えるようにします。
UniDicは国立国語研究所によって開発された、形態素解析器MeCab用の解析用辞書です。
形態素解析用辞書にはIPA(IPADic)やNAIST辞書、NEologd辞書などがありますが、IPA辞書は2007年で、NAIST辞書は2011年で、NEologd辞書は2020年で更新が停止しています。UniDicは2022年9月にバージョン3.1.1がリリースされており、2022年現在でも更新が続いている数少ない辞書です。
kuromojiは最新のUniDic3.1.1にはまだ正式対応していないようでしたので、ここではUniDic2.1.2を使用することにします。
(UniDic3.1.1も無理やりビルドすることはできますが、正式対応していないのと辞書サイズが約422MBと大きいので実用的ではないと思われます)
内容的にはこちらのエントリそのままですが、Lucene9からビルドシステムがApache AntからGradleに変更になったことで先人の知恵がそのまま適用できなかったりしたので、覚書ということでこの記事を書きました。
環境
- Ubuntu 22.04
- openjdk 11
- Solr 9.1.0
- Lucene 9.3.0
手順
Java11のインストール
Java11をインストールします。Ubuntuの場合、apt
でインストールすることができます。
sudo apt install openjdk-11-jdk
Luceneのダウンロード
LuceneのGitHubリポジトリから9.3.0をクローンします。
リポジトリのサイズが非常に大きいので、シャロークローンすることをおすすめします。
git clone https://github.com/apache/lucene.git --branch releases/lucene/9.3.0 --depth 1
コードの変更
Luceneのいくつかのコードを変更します。変更箇所はこちらのエントリとほとんど同じです。
パッチファイルをGitHub Gistに用意したので、これを各ファイルに適用します。
curl -O https://gist.githubusercontent.com/fjnkt98/b97a30b23d90a257aaba23efe54861bd/raw/c52efb8b364b40a7336616c69fda5c4076504b5d/DictionaryBuilder.java.patch
curl -O https://gist.githubusercontent.com/fjnkt98/9d298769314bc0875a7809fa08bcf250/raw/d2c9a9ecfecc0b948973c8762458ccf3487ae626/TokenInfoDictionaryBuilder.java.patch
curl -O https://gist.githubusercontent.com/fjnkt98/3e7655081b8141116bd39fd5a4b95e6a/raw/fbfad21fb165d1457affd8f411d06109da1ec95c/UnknownDictionaryBuilder.java.patch
curl -O https://gist.githubusercontent.com/fjnkt98/c6e9cbf47ef062f0ae1ca21380ecbe24/raw/05b1e593d8bf763858448f82829848855033e9a6/kuromoji.gradle.patch
cd lucene
git apply ../TokenInfoDictionaryBuilder.java.patch
git apply ../DictionaryBuilder.java.patch
git apply ../kuromoji.gradle.patch
git apply ../UnknownDictionaryBuilder.java.patch
辞書のビルド
辞書をビルドします。compileUnidic
を実行しないとipadicの辞書ができてしまうのでcompileUnidicタスクを単体で実行してから全体ビルドします(Gradleの仕様がよくわかってない)
./gradlew assemble compileUnidic
./gradlew assemble
ビルドが完了すると、lucene/analysis/kuromoji/build/libs
以下に辞書のアーカイブファイルが生成されます。何も設定を変更していなければ、lucene-analysis-kuromoji-9.3.0-SNAPSHOT.jar
という名前でファイルが作成されます。
ファイルサイズが17MBになっていればOKです。
Dockerfile
辞書のビルドを行うDockerfileを以下に示します。Dockerの実行環境があれば、辞書ファイルを持つDockerイメージが作成できます。
FROM openjdk:11.0.16-slim-buster
RUN apt-get update \
&& apt-get install -y git curl \
&& rm -rf /var/lib/apt/lists/*
RUN git clone https://github.com/apache/lucene.git --branch releases/lucene/9.3.0 --depth 1
RUN curl -O https://gist.githubusercontent.com/fjnkt98/b97a30b23d90a257aaba23efe54861bd/raw/c52efb8b364b40a7336616c69fda5c4076504b5d/DictionaryBuilder.java.patch \
&& curl -O https://gist.githubusercontent.com/fjnkt98/9d298769314bc0875a7809fa08bcf250/raw/d2c9a9ecfecc0b948973c8762458ccf3487ae626/TokenInfoDictionaryBuilder.java.patch \
&& curl -O https://gist.githubusercontent.com/fjnkt98/3e7655081b8141116bd39fd5a4b95e6a/raw/fbfad21fb165d1457affd8f411d06109da1ec95c/UnknownDictionaryBuilder.java.patch \
&& curl -O https://gist.githubusercontent.com/fjnkt98/c6e9cbf47ef062f0ae1ca21380ecbe24/raw/05b1e593d8bf763858448f82829848855033e9a6/kuromoji.gradle.patch
RUN cd /lucene \
&& git apply ../TokenInfoDictionaryBuilder.java.patch \
&& git apply ../DictionaryBuilder.java.patch \
&& git apply ../kuromoji.gradle.patch \
&& git apply ../UnknownDictionaryBuilder.java.patch
RUN cd /lucene \
&& ./gradlew clean
# compileUnidic単体でビルド 何かこれやらないとipadicの辞書が出来上がるのでこの手順を挟む
RUN cd /lucene \
&& ./gradlew assemble compileUnidic
RUN cd /lucene \
&& ./gradlew assemble
RUN cp /lucene/lucene/analysis/kuromoji/build/libs/lucene-analysis-kuromoji-9.3.0-SNAPSHOT.jar /
コンテナを起動して、docker cp
でホストにコピーすれば辞書が手に入ります。
docker run --rm -it lucene9.3.0-unidic2.1.2:latest bash
Solrで使用する
作成した辞書をSolrに配置して、動作確認をしてみます。
作成した辞書をSolrに適用するには、まずデフォルトでインストールされているkuromoji辞書を無効化します。デフォルトではlucene-analysis-kuromoji-9.3.0.jar
という辞書があるので、これを削除するか、lucene-analysis-kuromoji-9.3.0.jar.org
のようにリネームするかします。拡張子が.jar
でなくなればなんでもよいです。
そして、生成した辞書オブジェクトをこのディレクトリに配置します。
/opt/solr/server/solr-webapp/webapp/WEB-INF/lib
以下に、生成した辞書アーカイブを配置します。
DockerでSolrを実行する場合、以下のようなDockerfileを作成すると簡単に辞書入りSolrが作成できます。
FROM solr:9.1.0
COPY ./lucene-analysis-kuromoji-9.3.0-unidic-2.1.2.jar /opt/solr/server/solr-webapp/webapp/WEB-INF/lib/lucene-analysis-kuromoji-9.3.0.jar
USER solr
上記のDockerfileと同じディレクトリにlucene-analysis-kuromoji-9.3.0-unidic-2.1.2.jar
を配置し、Solrイメージをビルドします。
イメージタグは好きなものを付けてください。
docker build -t solr-unidic .
作成したSolrイメージを起動します。
docker run -p 8983:8983 --rm solr-unidic:latest solr-precreate example
起動後にコアが作成されるので、テキスト解析をリクエストしてみましょう。
$ curl -sS 'http://localhost:8983/solr/example/analysis/field?analysis.fieldtype=text_ja' --get --data-urlencode 'analysis.fieldvalue=自動車と自転車の違いはなんでしょう?' | jq '.analysis.field_types.text_ja.index[13][].text'
"自動"
"車"
"自転"
"車"
"違い"
"なん"
「自動車」が「自動」「車」に分割されれば成功です。
Discussion