これはPGroonga 2.X and 3.X用のドキュメントです。古いPGroongaを使っているならPGroonga 1.xのドキュメントを見てください。
CREATE INDEX USING pgroonga
インデックスメソッドとしてPGroongaを使うためにはCREATE INDEX
にUSING pgroonga
を指定します。このセクションではpgroonga
インデックスメソッドについて説明します。
このセクションではpgroonga
インデックスメソッド関連のCREATE INDEX
の構文だけ説明します。完全なCREATE INDEX
の構文はPostgreSQLのCREATE INDEX
のドキュメントを参照してください。
シングルカラムインデックスを作成する基本的な構文は次の通りです。
CREATE INDEX ${INDEX_NAME}
ON ${TABLE_NAME}
USING pgroonga (${COLUMN});
次のケースのときはこの構文を使えます。
text
型のカラム用の全文検索インデックスを作るときtext
型の配列のカラム用の全文検索インデックスを作るときtext
型以外の型のカラム用の等価条件・比較条件検索用インデックスを作るときtext
型以外の型の配列のカラム用の等価条件・比較条件検索用インデックスを作るときjsonb
型のカラム用のサブセット検索・高度な検索用のインデックスを作るときvarchar
型のカラム用の全文検索インデックスを作るときの基本的な構文は次の通りです。
CREATE INDEX ${INDEX_NAME}
ON ${TABLE_NAME}
USING pgroonga (${COLUMN} pgroonga_varchar_full_text_search_ops_v2);
この場合はpgroonga_varchar_full_text_search_ops_v2
オペレータークラスを指定する必要があります。
2.3.5からINCLUDE
も使えます。
CREATE INDEX
のWITH
オプションを使って次の項目をカスタマイズできます。
プラグイン:Groongaの拡張機能です。プラグインを登録することで追加の機能を使うことができます。追加の機能には追加のトークナイザー・ノーマライザー・トークンフィルターなどがあります。
トークナイザー:キーワードの抽出方法をカスタマイズするモジュールです。
ノーマライザー:text
型とvarchar
型の等価性をカスタマイズするモジュールです。
トークンフィルター:トークナイザーが抽出したキーワードをフィルターするモジュールです。
語彙表の種類:トークンを管理する語彙表の種類です。
クエリー構文:$@~
演算子が使っている構文です。
通常、これらをカスタマイズする必要はありません。なぜなら多くの場合で適切なようにデフォルト値が設定されているからです。これらをカスタマイズする機能は高度なユーザー向けの機能です。
デフォルトではプラグインとトークンフィルターは使われていません。
デフォルトのトークナイザーとノーマライザーと語彙表の種類は次の通りです。
トークナイザー:TokenBigram
:bigramベースのトークナイザーです。このトークナイザーはbigramベースのトークナイズ方法とスペース区切りベースのトークナイズ方法を組み合わせています。非ASCII文字にはbigramベースのトークナイズ方法を使い、ASCII文字にはスペース区切りベースのトークナイズ方法を使います。これはASCII文字だけのクエリーで検索したときのノイズを減らすためです。
ノーマライザー:NormalizerAuto
:対象のエンコーディングに合わせて適切なノーマライズ方法を選びます。たとえば、UTF-8の場合はUnicode NFKCベースのノーマライズ方法を使います。
語彙表の種類:patricia_trie
:前方一致検索のようなリッチな方法でトークンを検索できます。サイズも小さいです。
1.2.0で追加。
プラグインを登録するにはplugins='${プラグイン名1}, ${プラグイン名2}, ..., ${プラグイン名N}'
を指定します。
CREATE INDEX
の最初のオプションとしてplugins
を指定しなければいけないことに注意してください。CREATE INDEX
のオプションは指定された順に処理されます。指定したプラグインに含まれてるトークナイザー・ノーマライザー・トークンフィルターを使うかもしれないので、他のオプションより先にプラグインを登録しておく必要があります。
以下はTokenFilterStem
トークンフィルターを使うためにtoken_filters/stem
プラグインを登録する例です。
CREATE TABLE memos (
id integer,
content text
);
CREATE INDEX pgroonga_content_index
ON memos
USING pgroonga (content)
WITH (plugins='token_filters/stem',
token_filters='TokenFilterStem');
トークンフィルターについてはトークンフィルターのカスタマイズ方法を参照してください。
トークナイザーをカスタマイズするにはtokenizer='${トークナイザー名}'
を指定します。通常、トークナイザーをカスタマイズする必要はありません。
以下はMeCabベースのトークナイザーを使う例です。tokenizer='TokenMecab'
を指定する必要があります。TokenMecab
はMeCabベースのトークナイザーの名前です。
CREATE TABLE memos (
id integer,
content text
);
CREATE INDEX pgroonga_content_index
ON memos
USING pgroonga (content)
WITH (tokenizer='TokenMecab');
tokenizer=''
と指定することでトークナイザーを無効にすることができます。トークナイザーを無効にすると、完全一致検索または前方一致検索のみでカラムの値を検索できます。これにより誤ヒットが少なくなるケースがあります。例えば、タグ検索・名前検索などのときは有用です。
以下はトークナイザーを無効にする例です。
CREATE TABLE memos (
id integer,
tag text
);
CREATE INDEX pgroonga_tag_index
ON memos
USING pgroonga (tag)
WITH (tokenizer='');
tokenizer='TokenDelimit'
はタグ検索で便利です。TokenDelimit
も参照してください。
tokenizer='${TOKENIZER_NAME}(...)'
という構文でトークナイザーのオプションを指定できます。
2.0.6から使えます。
以下は"n"
オプションと3
オプションを指定してTokenNgram
トークナイザーを使う例です。
CREATE TABLE memos (
id integer,
tag text
);
CREATE INDEX pgroonga_tag_index
ON memos
USING pgroonga (tag)
WITH (tokenizer='TokenNgram("n", 3)');
他のトークナイザーについてはトークナイザーを参照してください。
If you plan to perform partial matching searches for keywords in alphabetic languages, it is recommended to configure your tokenizer to TokenNgram
with extra options. The default tokenizer in PGroonga
is TokenBigram
, which means that if you search for the keyword 'pp', for instance, it won't match 'Apple', 'Pineapple', or 'Ripple' in your data. To avoid this issue, it is strongly advised to set up your tokenizer as following TokenNgram
example.
Here is an example to use TokenNgram
based tokenizer. You need to specify tokenizer='TokenNgram'
. See TokenNgram
for more detail.
CREATE TABLE memos (
id integer,
content text
);
CREATE INDEX pgroonga_content_index
ON memos
USING pgroonga (content)
WITH(tokenizer='TokenNgram("unify_alphabet", false, "unify_symbol", false, "unify_digit", false)');
You may also use TokenBigramBigramSplitSymbolAlphaDigit
for partial match instead of TokenNgram
above. (Using TokenNgram(...)
is recommended).
Remarks
We however do not recommend using TokenNgram("unify_...)
. It is advisable to use TokenNgram/TokenBigram
instead, as partial matches in alphabetical languages tend to introduce a lot of noise. TokenNgram("unify_...)
should only be utilized when it is truly necessary.
次のパラメーターを使ってノーマライザーをカスタマイズできます。通常、ノーマライザーをカスタマイズする必要はありません。
normalizers
:以下のどのパラメーターも使われなかったときに使われるデフォルトのノーマライザーです。
normalizer
:normalizers
と同じです。2.3.1から非推奨になりました。
full_text_search_normalizer
:normalizers_mapping
でインデックス対象のノーマライザーが指定されなかったときに使われる全文検索インデックス用のノーマライザーです。
regexp_search_normalizer
: normalizers_mapping
でインデックス対象のノーマライザーが指定されなかったときに使われる正規表現検索インデックス用のノーマライザーです。
prefix_search_normalizer
: normalizers_mapping
でインデックス対象のノーマライザーが指定されなかったときに使われる前方一致検索インデックス用のノーマライザーです。
normalizers_mapping
:指定したインデックス対象用のノーマライザーを指定できます。
normalizers=''
のように空の値を指定するとノーマライザーを無効にすることができます。ノーマライザーを無効にすると元のカラムの値そのものでだけ検索できます。もし、ノーマライザーを使うことで誤ヒットが増える場合は無効にした方がよいでしょう。
ノーマライザーを無効にする方法は次の通りです。
CREATE TABLE memos (
id integer,
tag text
);
CREATE INDEX pgroonga_tag_index
ON memos
USING pgroonga (tag)
WITH (normalizers='');
normalizers='${NORMALIZER_NAME}(...)'
という構文でノーマライザーのオプションを指定できます。
2.0.6から使えます。
以下は"unify_kana"
オプションとtrue
オプションを指定してNormalizerNFKC100
ノーマライザーを使う例です。
CREATE TABLE memos (
id integer,
tag text
);
CREATE INDEX pgroonga_tag_index
ON memos
USING pgroonga (tag)
WITH (normalizers='NormalizerNFKC100("unify_kana", true)');
normalizers='${NORMALIZER_NAME1}(...), ${NORMALISER_NAME2(...), ...'
という構文で複数のノーマライザーを指定できます。
2.3.1から使えます。
以下は"unify_kana"
がtrue
というオプション付きのNormalizerNFKC130
ノーマライザーと"unify_hyphen"
がtrue
というオプション付きのNormalizerNFKC130
ノーマライザーを使う実用的ではない例です。
CREATE TABLE memos (
id integer,
tag text
);
CREATE INDEX pgroonga_tag_index
ON memos
USING pgroonga (tag)
WITH (normalizers='
NormalizerNFKC130("unify_kana", true),
NormalizerNFKC130("unify_hyphen", true)
');
他のノーマライザーについてはノーマライザーを参照してください。
全文検索・正規表現検索・前方一致検索それぞれに別のノーマライザーを使うこともできます。これらの検索用の代表的な演算子クラスは次の通りです。
正規表現検索:pgroonga_text_regexp_ops_v2
次のパラメーターを使うことでそれぞれの検索方法ごとに異なるノーマライザーを使えます。
全文検索:full_text_search_normalizer
正規表現検索:regexp_search_normalizer
前方一致検索:prefix_search_normalizer
これらのパラメーターを使っていない場合はnormalizers
パラメーターの値を使います。
以下は全文検索用のインデックスだけノーマライザーを無効にする例です。
CREATE TABLE memos (
id integer,
title text,
content text,
tag text
);
CREATE INDEX pgroonga_memos_index
ON memos
USING pgroonga (
title pgroonga_text_full_text_search_ops_v2,
content pgroonga_text_regexp_ops_v2,
tag pgroonga_text_term_search_ops_v2
)
WITH (full_text_search_normalizer='',
normalizers='NormalizerAuto');
title
のインデックスは全文検索用です。full_text_search_normalizer
が''
なので、このインデックスはノーマライザーを使いません。normalizer
が'NormalizerAuto'
なので、他のインデックスはNormalizerAuto
を使います。
以下は正規表現検索用のインデックスだけノーマライザーを無効にする例です。
CREATE TABLE memos (
id integer,
title text,
content text,
tag text
);
CREATE INDEX pgroonga_memos_index
ON memos
USING pgroonga (
title pgroonga_text_full_text_search_ops_v2,
content pgroonga_text_regexp_ops_v2,
tag pgroonga_text_term_search_ops_v2
)
WITH (regexp_search_normalizer='',
normalizers='NormalizerAuto');
content
のインデックスは正規表現検索用です。regular_expression_search_normalizer
が''
なので、このインデックスはノーマライザーを使いません。normalizers
が'NormalizerAuto'
なので、他のインデックスはNormalizerAuto
を使います。
以下は前方一致検索用のインデックスだけノーマライザーを無効にする例です。
CREATE TABLE memos (
id integer,
title text,
content text,
tag text
);
CREATE INDEX pgroonga_memos_index
ON memos
USING pgroonga (
title pgroonga_text_full_text_search_ops_v2,
content pgroonga_text_regexp_ops_v2,
tag pgroonga_text_term_search_ops_v2
)
WITH (prefix_search_normalizer='',
normalizers='NormalizerAuto');
tag
のインデックスは単語検索用です。単語検索は前方一致検索も含んでいます。prefix_search_normalizer
が''
なので、このインデックスはノーマライザーを使いません。normalizers
が'NormalizerAuto'
なので、他のインデックスはNormalizerAuto
を使います。
normalizers_mapping='${MAPPING_IN_JSON}'
を使うと指定したインデックス対象用のノーマライザーを指定できます。
2.3.1から使えます。
以下は${MAPPING_IN_JSON}
の構文です。
{
"${index_target_name1}": "${normalizer1}",
"${index_target_name2}": "${normalizer2}",
...
}
以下の例ではtitle
にNormalizerNFKC130("unify_kana", true)
ノーマライザー、content
にNormalizerNFKC130("unify_hyphen", true)
ノーマライザー、それ以外のカラムにNormalizerAuto
を指定しています。
CREATE TABLE memos (
id integer,
title text,
content text,
tag text
);
CREATE INDEX pgroonga_memos_index
ON memos
USING pgroonga (
title pgroonga_text_full_text_search_ops_v2,
content pgroonga_text_regexp_ops_v2,
tag pgroonga_text_term_search_ops_v2
)
WITH (normalizers_mapping='{
"title": "NormalizerNFKC130(\"unify_kana\", true)",
"content": "NormalizerNFKC130(\"unify_hyphen\", true)"
}',
normalizers='NormalizerAuto');
NormalizerTable
の使い方ノーマライザーを指定するテキスト中で${table:PGROONGA_INDEX_NAME}
という構文を使えます。
2.3.1から使えます。
この値はPGROONGA_INDEX_NAME
で指定したPGroongaのインデックスに対応するGroongaのテーブル名に置換されます。これはNormalizerTable
を使うときに便利です。NormalizerTable
はGroongaのテーブル名・カラム名を使うからです。
以下はNormalizerNFKC130
ノーマライザーとNormalizerTable
ノーマライザーを使う例です。
CREATE TABLE normalizations (
target text,
normalized text
);
CREATE INDEX pgrn_normalizations_index ON normalizations
USING pgroonga (target pgroonga_text_term_search_ops_v2,
normalized);
INSERT INTO normalizations VALUES ('o', '0');
INSERT INTO normalizations VALUES ('ss', '55');
CREATE TABLE memos (
id integer,
content text
);
CREATE INDEX pgroonga_memos_index
ON memos
USING pgroonga (content)
WITH (normalizers='
NormalizerNFKC130,
NormalizerTable(
"normalized", "${table:pgrn_normalizations_index}.normalized",
"target", "target"
)
');
INSERT INTO memos VALUES (1, '0123455');
INSERT INTO memos VALUES (2, 'o1234ss');
SELECT * FROM memos WHERE content &@~ 'o123455';
-- id | content
-- ----+---------
-- 1 | 0123455
-- 2 | o1234ss
-- (2 rows)
normalizations
テーブルを変更した後はREINDEX INDEX pgroonga_memos_index
を実行しないといけないことに注意してください。なぜならnormalizations
テーブルが変わるとノーマライズ結果も変わるからです。
pgroonga_highlight_html
と一緒にNormalizerTable
を使う方法このNormalizerTable
と一緒にpgroonga_highlight_html
関数を使うときは、TokenNgram
に"report_source_location", true"
オプションを指定するだけでなく、NormalizerNFKC*
とNormalizerTable
それぞれに"report_source_offset", true"
オプションを指定する必要があります。
詳細はpgroonga_highlight_html
関数を参照してください。
1.2.0で追加。
トークンフィルターを使うにはtoken_filters='${トークンフィルター1}, ${トークンフィルター2}, ..., ${トークンフィルターN}'
を指定します。
Groongaはデフォルトでは1つもトークンフィルターを提供していません。すべてのトークンフィルターはプラグインとして提供しています。トークンフィルターを使う場合はプラグインを登録する必要があります。
以下はtoken_filters/stem
プラグインに含まれているTokenFilterStem
トークンフィルターを使う例です。
CREATE TABLE memos (
id integer,
content text
);
CREATE INDEX pgroonga_content_index
ON memos
USING pgroonga (content)
WITH (plugins='token_filters/stem',
token_filters='TokenFilterStem');
token_filters
より前にplugins
を指定しなければいけないことに注意してください。CREATE INDEX
に指定したオプションは指定した順に処理されます。トークンフィルターを使う前にプラグインを登録しておく必要があります。
他のトークンフィルターについてはトークンフィルターを参照してください。
1.1.6で追加。
テーブルスペースをカスタマイズするにはTABLESPACE ${TABLESPACE_NAME}
を指定してください。もし高速なストレージがある場合は、テーブルスペースを変更してそのストレージにPGroongaのインデックスを置きたくなるかもしれません。
以下はテーブルスペースを変更する例です。
CREATE TABLESPACE fast LOCATION '/data/fast_disk';
CREATE TABLE memos (
id integer,
tag text
);
CREATE INDEX pgroonga_tag_index
ON memos
USING pgroonga (tag)
TABLESPACE fast;
2.0.6で追加。
語彙表の種類をカスタマイズするにはlexicon_type='${LEXICON_TYPE}'
を指定します。
利用可能な語彙表の種類は次の通りです。
通常、これをカスタマイズする必要はありません。なぜなら多くの場合はデフォルト値が適切だからです。
以下はトークンの前方一致検索を無効にするために語彙表の種類をhash_table
にする例です。
CREATE TABLE memos (
id integer,
content text
);
CREATE INDEX pgroonga_content_index
ON memos
USING pgroonga (content)
WITH (lexicon_type='hash_table');
column:...
構文を使う方法2.1.3で追加。
クエリー中でcolumn:...
構文を使うにはquery_allow_column=true
を指定します。
column:...
構文を使うと、他のカラムを使ったり、マッチ以外の演算子も使うことができます。
column:...
構文はシーケンシャルサーチでは動かないことに注意してください。インデックスサーチでしか動きません。
以下は同じインデックス内の他のカラムを使うためにquery_allow_column
を使う例です。
DROP TABLE IF EXISTS memos;
CREATE TABLE memos (
title text,
content text
);
CREATE INDEX pgroonga_memo_texts_index
ON memos
USING pgroonga (title, content)
WITH (query_allow_column=true);
INSERT INTO memos VALUES
('PGroonga = PostgreSQL + Groonga', 'Very fast full text search extension.'),
('PostGIS', 'GIS extension.');
SELECT *
FROM memos
-- contentカラムは'extension'を含んでいて、かつ、
-- titleカラムは'Groonga'を含んでいなければいけない。
WHERE content &@~ 'extension title:@Groonga';
-- title | content
-- ---------------------------------+---------------------------------------
-- PGroonga = PostgreSQL + Groonga | Very fast full text search extension.
-- (1 row)
以下は他の演算を使うためにquery_allow_column
を使う例です。
DROP TABLE IF EXISTS memos;
CREATE TABLE memos (
title text
);
CREATE INDEX pgroonga_title_index
ON memos
USING pgroonga (title)
WITH (query_allow_column=true);
INSERT INTO memos VALUES ('PGroonga');
INSERT INTO memos VALUES ('PGroonga = PostgreSQL + Groonga');
SELECT *
FROM memos
-- titleカラムは'PGroonga'でなければいけない。
-- この演算はインデックスを使わないことに注意すること。
WHERE title &@~ 'title:PGroonga';
-- title
-- ----------
-- PGroonga
-- (1 row)
使える演算はGroongaのクエリー構文を参照してください。
2.3.2で追加。
指定したインデックス対象のインデックスカラムフラグをカスタマイズするにはindex_flags_mappings='${MAPPING_IN_JSON}'
を指定します。
以下は${MAPPING_IN_JSON}
の構文です。
{
"${index_target_name1}": ["${flag1_1}", "${flag1_2}", ..., "${flag1_N}"],
"${index_target_name2}": ["${flag2_1}", "${flag2_2}", ..., "${flag2_N}"],
...
}
以下は利用可能なインデックスカラムのフラグです。それぞれGroongaのフラグに対応しています。
SMALL
: GroongaでのINDEX_SMALL
MEDIUM
: GroongaでのINDEX_MEDIUM
LARGE
: GroongaでのINDEX_LARGE
WITH_WEIGHT
: GroongaでのWITH_WEIGHT
WEIGHT_FLOAT32
: GroongaでのWEIGHT_FLOAT32
["SMALL", "MEDIUM", "LARGE"]
というように競合するフラグを同時に指定することはできません。
通常、これをカスタマイズする必要はありません。なぜなら多くの場合はデフォルト値が適切だからです。
以下は大量データのために大きいインデックスカラムを使う例です。
CREATE TABLE memos (
id integer,
content text
);
CREATE INDEX pgroonga_content_index
ON memos
USING pgroonga (content)
WITH (index_flags_mapping='{
"content": ["LARGE"]
}');