BloGroonga

2021-10-04

PostgreSQL用高速日本語全文検索モジュールPGroonga(ぴーじーるんが) 2.3.2リリース

PostgreSQLで高速日本語全文検索をできるようにするPGroongaの2.3.2をリリースしました!

新規ユーザーの方は、PGroonga 2.0.2のリリースアナウンスのPGroongaについても参照してください。

このリリースでは、リリースされたばかりのPostgreSQL14をサポートしています!

ハイライト

PGroonga 2.3.2の主な変更点は以下の通りです。

  • PostgreSQL14 をサポートしました。

  • パラレルスキャンをサポートしました。

  • 宣言型パーティショニングに対するパラレルスキャンをサポートしました。

  • [CREATE INDEX USING PGroonga] インデックス対象毎にインデックスフラグをカスタマイズできる、index_flags_mapping オプションを追加しました。

  • [CREATE INDEX USING PGroonga] normalizers_mapping オプションの中で ${table:INDEX_NAME} 構文をサポートしました。

  • [Ubuntu] Ubuntu 21.04 をサポートしました。

  • [pgroonga_highlight_html 関数] 語彙表を作り直したときに、語彙表が更新されないことがある問題を修正しました。

おしらせ

セッション

2021年11月12日(金)にPostgreSQL Conference Japan 2021PGroongaを使って全文検索結果をより良くする方法というセッションがあります。

このチュートリアルセッションは、PGroongaを既に使っている人向けに、PGroongaを使って検索結果を改善する方法を紹介する予定です。

まとめ

PostgreSQLで高速に日本語全文検索をしたいという方はPGroongaを使ってガンガン検索してください!

2021-09-29

Groonga 11.0.7リリース

Groonga 11.0.7をリリースしました!

それぞれの環境毎のインストール方法: インストール

変更内容

主な変更点は以下の通りです。

改良

  • load "[int, int,…]" のような文字列を [int, int,…] のような整数のベクターにキャストするようにしました。

    例えば、以下のように、"[1, -2]" のようなベクターを文字列としてロードしたとしても、 [1, -2] のように整数のベクターとして扱います。

      table_create Data TABLE_NO_KEY
      column_create Data numbers COLUMN_VECTOR Int16
      table_create Numbers TABLE_PAT_KEY Int16
      column_create Numbers data_numbers COLUMN_INDEX Data numbers
    
      load --table Data
      [
      {"numbers": "[1, -2]"},
      {"numbers": "[-3, 4]"}
      ]
    
      dump   --dump_plugins no   --dump_schema no
      load --table Data
      [
      ["_id","numbers"],
      [1,[1,-2]],
      [2,[-3,4]]
      ]
    
      column_create Numbers data_numbers COLUMN_INDEX Data numbers
      select Data --filter 'numbers @ -2'
      [[0,0.0,0.0],[[[1],[["_id","UInt32"],["numbers","Int16"]],[1,[1,-2]]]]]
    

    この機能は以下の型をサポートします。

    • Int8
    • UInt8
    • Int16
    • UInt16
    • Int32
    • UInt32
    • Int64
    • UInt64
  • load 文字列として表現されたJSON配列を文字列のベクターとしてロードできるようにしました。

    例えば、以下のように "["hello", "world"]" のような文字列として表現されたJSON配列をロードした場合、 ["hello", "world"] のように2つの要素を持つベクターとして扱います。

      table_create Data TABLE_NO_KEY
      [[0,0.0,0.0],true]
      column_create Data strings COLUMN_VECTOR ShortText
      [[0,0.0,0.0],true]
      table_create Terms TABLE_PAT_KEY ShortText   --normalizer NormalizerNFKC130   --default_tokenizer TokenNgram
      [[0,0.0,0.0],true]
      column_create Terms data_strings COLUMN_INDEX Data strings
      [[0,0.0,0.0],true]
      load --table Data
      [
      {"strings": "[\"Hello\", \"World\"]"},
      {"strings": "[\"Good-bye\", \"World\"]"}
      ]
      [[0,0.0,0.0],2]
      dump   --dump_plugins no   --dump_schema no
      load --table Data
      [
      ["_id","strings"],
      [1,["Hello","World"]],
      [2,["Good-bye","World"]]
      ]
    
      column_create Terms data_strings COLUMN_INDEX Data strings
      select Data --filter 'strings @ "bye"'
      [
        [
          0,
          0.0,
          0.0
        ],
        [
          [
            [
              1
            ],
            [
              [
                "_id",
                "UInt32"
              ],
              [
                "strings",
                "ShortText"
              ]
            ],
            [
              2,
              [
                "Good-bye",
                "World"
              ]
            ]
          ]
        ]
      ]
    

    以前のバージョンでは、 "["hello", "world"]" のような文字列として表現されたJSON配列をロードした場合は、 ["["hello", "world"]"] のような一つの要素を持つベクターとして扱っていました。

  • [Documentation] 以下の項目についてのドキュメントを追加しました。

    • column_create WEIGHT_FLOAT32 フラグについてのドキュメントを追加しました。
    • NormalizerNFKC121 NormalizerNFKC121 についてのドキュメントを追加しました。
    • NormalizerNFKC130 NormalizerNFKC130 についてのドキュメントを追加しました。
    • NormalizerTable NormalizerTable についてのドキュメントを追加しました。
  • Groongaが要求する Apache Arrow のバージョンを 3.0.0 に更新しました。

修正

  • テーブル作成時に無効なオプションを持つトークナイザーを指定するとメモリーリークする問題を修正しました。

  • Hashテーブルに新しいエントリーを追加できなくなることがある問題を修正しました。

    このバグは、Groonga 11.0.6 でのみ発生し、頻繁にデータを追加、削除すると発生することがあります。 もし、このバグが発生した場合は、以下の手順を実行することで、この問題を解決できます。

    1. Groongaを11.0.6から11.0.7以降にアップグレードします。
    2. 元のテーブルと同じスキーマを持つ新しいテーブルを作ります。
    3. 元のテーブルから新しいテーブルにデータをコピーします。
  • [Windows] メモリー不足によって、新しくファイルのオープンに失敗した時にリソースリークする問題を修正しました。

既知の問題

  • 現在Groongaには、ベクターカラムに対してデータを大量に追加、削除、更新した際にデータが破損することがある問題があります。

  • [ブラウザーベースの管理ツール] 現在Groongaには、レコード一覧の管理モードのチェックボックスにチェックを入れても、非管理モードに入力された検索クエリーが送信されるという問題があります。

  • *<*> は、filter条件の右辺に query() を使う時のみ有効です。もし、以下のように指定した場合、 *<*>&& として機能します。

    • 'content @ "Groonga" *< content @ "Mroonga"'
  • GRN_II_CURSOR_SET_MIN_ENABLE が原因でマッチするはずのレコードを返さないことがあります。

さいごに

詳細については、以下のお知らせも参照してください。

お知らせ 11.0.7リリース

それでは、Groongaでガンガン検索してください!

2021-08-29

Groonga 11.0.6リリース

Groonga 11.0.6をリリースしました!

それぞれの環境毎のインストール方法: インストール

重要なお知らせ

Groonga 11.0.6 には、Hashテーブルに新しいエントリーを追加できなくなることがある問題があります。

この問題は、Groonga 11.0.7で修正しました。この問題は、Groonga 11.0.6でのみ発生します。 したがって、Groonga 11.0.6をお使いの方は、Groonga 11.0.7以降を使うことを強くおすすめします。

変更内容

主な変更点は以下の通りです。

改良

  • クラッシュ時に自動でリカバリーする機能を追加しました。(実験的な機能です。)

    この機能は実験的な機能です。現状、この機能はまだ安定していません。

    この機能によって、Groongaがクラッシュした時、Groongaはクラッシュした後、 最初のデータベースオープン時に自動的にデータベースをリカバリーします。 ただ、全てのクラッシュケースで自動的にデータベースをリカバリーできるわけではありません。 クラッシュのタイミングによっては、手動でデータベースのリカバリーが必要になります。

  • cache_limit cache_limit 0 を実行したときにキャッシュを削除するようにしました。

    Groongaは内部的なテーブルにクエリーキャッシュを保存しています。 このテーブルは、ハッシュテーブルなので、トータルのキーサイズは最大で4GiBです。 そのため、もし多くの巨大なクエリーを実行した場合、トータルのキーサイズの最大値4GiBを超え、Groongaがクエリーをキャッシュできない可能性があります。 このようなケースで、 cache_limit 0 を実行することで、クエリーキャッシュ用のテーブルをクリアーし、 Groongaがクエリーキャッシュを保存できるようにします。

修正

  • 同時期に複数のスレッドで同じオブジェクトをオープンした時に、Groongaがロックを解除しない問題を修正しました。

  • query_parallel_or query() と結果が異なることがある問題を修正しました。

    例えば、 query("tags || tags2", "beginner man") とした場合は、以下のレコードはマッチしますが、 query_parallel_or("tags || tags2", "beginner man") とした場合は、今までは、以下のレコードはマッチしませんでした。

    {"_key": "Bob",   "comment": "Hey!",       "tags": ["expert", "man"], "tags2": ["beginner"]}
    

    今回の変更によって、 query_parallel_or("tags || tags2", "beginner man") を使った場合であっても、 上記のレコードがマッチするようになりました。

既知の問題

  • 現在Groongaには、ベクターカラムに対してデータを大量に追加、削除、更新した際にデータが破損することがある問題があります。

  • [ブラウザーベースの管理ツール] 現在Groongaには、レコード一覧の管理モードのチェックボックスにチェックを入れても、非管理モードに入力された検索クエリーが送信されるという問題があります。

  • *<*> は、filter条件の右辺に query() を使う時のみ有効です。もし、以下のように指定した場合、 *<*>&& として機能します。

    • 'content @ "Groonga" *< content @ "Mroonga"'
  • GRN_II_CURSOR_SET_MIN_ENABLE が原因でマッチするはずのレコードを返さないことがあります。

さいごに

詳細については、以下のお知らせも参照してください。

お知らせ 11.0.6リリース

それでは、Groongaでガンガン検索してください!

2021-07-29

Groonga 11.0.5リリース

Groonga 11.0.5をリリースしました!

それぞれの環境毎のインストール方法: インストール

変更内容

主な変更点は以下の通りです。

改良

  • Normalizers ノーマライザーを複数指定できるようになりました。

    テーブル作成時に --normalizers オプションを使うことで、複数のノーマライザーを指定できます。 互換性のため、既存の --normalizer を使っても複数のノーマライザーを指定できます。

    Groonga 11.0.4 でノーマライザーをカスタマイズするための NormalizerTable を追加しました。 この NormalizerTable と既存のノーマライザーを組み合わせることでより柔軟な制御ができます。

    例えば、この機能は、以下のようなケースで有用です。

    • 電話番号を検索することを考えます。ただし、データはOCRで手書きのデータを取り込みます。 OCRは数字と文字列をご認識することがあります。(例えば、 5とS など)

    具体的には以下の通りです。

      table_create Normalizations TABLE_PAT_KEY ShortText
      column_create Normalizations normalized COLUMN_SCALAR ShortText
      load --table Normalizations
      [
      {"_key": "s", "normalized": "5"}
      ]
    
      table_create Tels TABLE_NO_KEY
      column_create Tels tel COLUMN_SCALAR ShortText
    
      table_create TelsIndex TABLE_PAT_KEY ShortText \
        --normalizers 'NormalizerNFKC130("unify_hyphen_and_prolonged_sound_mark", true), \
                       NormalizerTable("column", "Normalizations.normalized")' \
        --default_tokenizer 'TokenNgram("loose_symbol", true, "loose_blank", true)'
      column_create TelsIndex tel_index COLUMN_INDEX|WITH_SECTION Tels tel
    
      load --table Tels
      [
      {"tel": "03-4S-1234"}
      {"tel": "03-45-9876"}
      ]
    
      select --table Tels \
        --filter 'tel @ "03-45-1234"'
      [
        [
          0,
          1625227424.560146,
          0.0001730918884277344
        ],
        [
          [
            [
              1
            ],
            [
              [
                "_id",
                "UInt32"
              ],
              [
                "tel",
                "ShortText"
              ]
            ],
            [
              1,
              "03-4S-1234"
            ]
          ]
        ]
      ]
    

    既存のノーマライザーでは、このようなケースには対応できませんでしたが、このリリースから既存のノーマライザーと NormalizerTable を組み合わせることで、このようなケースにも対応できます。

  • query_parallel_orquery シーケンシャルサーチのしきい値をカスタマイズできるようにしました。

    以下のオプションを使うことで、シーケンシャルサーチを使うかどうかのしきい値をクエリーごとにカスタマイズできます。

    • {"max_n_enough_filtered_records": xx}

      max_n_enough_filtered_records は、レコード数を指定します。 query または、 query_parallel_or で、この値以下までレコードが絞り込めそうな場合、シーケンシャルサーチを使います。

    • {"enough_filtered_ratio": x.x}

      enough_filtered_ratio は、全体に占める割合を指定します。 query または、 query_parallel_or で、この割合以下までレコードが絞り込めそうな場合、シーケンシャルサーチを使います。 例えば、 {"enough_filtered_ratio": 0.5} とした場合、 query または query_parallel_or で全体の半分まで 絞り込めそうな場合はシーケンシャルサーチを使います。

    具体的には以下の通りです。

      table_create Products TABLE_NO_KEY
      column_create Products name COLUMN_SCALAR ShortText
    
      table_create Terms TABLE_PAT_KEY ShortText --normalizer NormalizerAuto
      column_create Terms products_name COLUMN_INDEX Products name
    
      load --table Products
      [
      ["name"],
      ["Groonga"],
      ["Mroonga"],
      ["Rroonga"],
      ["PGroonga"],
      ["Ruby"],
      ["PostgreSQL"]
      ]
    
      select \
        --table Products \
        --filter 'query("name", "r name:Ruby", {"enough_filtered_ratio": 0.5})'
    
      table_create Products TABLE_NO_KEY
      column_create Products name COLUMN_SCALAR ShortText
    
      table_create Terms TABLE_PAT_KEY ShortText --normalizer NormalizerAuto
      column_create Terms products_name COLUMN_INDEX Products name
    
      load --table Products
      [
      ["name"],
      ["Groonga"],
      ["Mroonga"],
      ["Rroonga"],
      ["PGroonga"],
      ["Ruby"],
      ["PostgreSQL"]
      ]
    
      select \
        --table Products \
        --filter 'query("name", "r name:Ruby", {"max_n_enough_filtered_records": 10})'
    
  • betweenin_values シーケンシャルサーチのしきい値をカスタマイズできるようにしました。

    betweenin_values は、検索対象のレコードが十分に絞り込まれている時に、シーケンシャルサーチに切り替える機能があります。

    今までも、以下のように環境変数でこのしきい値はカスタマイズできました。

    • GRN_IN_VALUES_TOO_MANY_INDEX_MATCH_RATIO
    • GRN_BETWEEN_TOO_MANY_INDEX_MATCH_RATIO

    in_values():

      # Don't use auto sequential search
      GRN_IN_VALUES_TOO_MANY_INDEX_MATCH_RATIO=-1
      # Set threshold to 0.02
      GRN_IN_VALUES_TOO_MANY_INDEX_MATCH_RATIO=0.02
    

    between():

      # Don't use auto sequential search
      GRN_BETWEEN_TOO_MANY_INDEX_MATCH_RATIO=-1
      # Set threshold to 0.02
      GRN_BETWEEN_TOO_MANY_INDEX_MATCH_RATIO=0.02
    

    環境変数によるカスタマイズは、すべてのクエリーに対して適用されますが、この機能は、クエリーごとにしきい値を指定できます。

    具体的には以下の通りです。 {"too_many_index_match_ratio": x.xx} オプションでしきい値を指定できます。 このオプションの値の型は double 型です。

      table_create Memos TABLE_HASH_KEY ShortText
      column_create Memos timestamp COLUMN_SCALAR Time
    
      table_create Times TABLE_PAT_KEY Time
      column_create Times memos_timestamp COLUMN_INDEX Memos timestamp
    
      load --table Memos
      [
      {"_key": "001", "timestamp": "2014-11-10 07:25:23"},
      {"_key": "002", "timestamp": "2014-11-10 07:25:24"},
      {"_key": "003", "timestamp": "2014-11-10 07:25:25"},
      {"_key": "004", "timestamp": "2014-11-10 07:25:26"},
      {"_key": "005", "timestamp": "2014-11-10 07:25:27"},
      {"_key": "006", "timestamp": "2014-11-10 07:25:28"},
      {"_key": "007", "timestamp": "2014-11-10 07:25:29"},
      {"_key": "008", "timestamp": "2014-11-10 07:25:30"},
      {"_key": "009", "timestamp": "2014-11-10 07:25:31"},
      {"_key": "010", "timestamp": "2014-11-10 07:25:32"},
      {"_key": "011", "timestamp": "2014-11-10 07:25:33"},
      {"_key": "012", "timestamp": "2014-11-10 07:25:34"},
      {"_key": "013", "timestamp": "2014-11-10 07:25:35"},
      {"_key": "014", "timestamp": "2014-11-10 07:25:36"},
      {"_key": "015", "timestamp": "2014-11-10 07:25:37"},
      {"_key": "016", "timestamp": "2014-11-10 07:25:38"},
      {"_key": "017", "timestamp": "2014-11-10 07:25:39"},
      {"_key": "018", "timestamp": "2014-11-10 07:25:40"},
      {"_key": "019", "timestamp": "2014-11-10 07:25:41"},
      {"_key": "020", "timestamp": "2014-11-10 07:25:42"},
      {"_key": "021", "timestamp": "2014-11-10 07:25:43"},
      {"_key": "022", "timestamp": "2014-11-10 07:25:44"},
      {"_key": "023", "timestamp": "2014-11-10 07:25:45"},
      {"_key": "024", "timestamp": "2014-11-10 07:25:46"},
      {"_key": "025", "timestamp": "2014-11-10 07:25:47"},
      {"_key": "026", "timestamp": "2014-11-10 07:25:48"},
      {"_key": "027", "timestamp": "2014-11-10 07:25:49"},
      {"_key": "028", "timestamp": "2014-11-10 07:25:50"},
      {"_key": "029", "timestamp": "2014-11-10 07:25:51"},
      {"_key": "030", "timestamp": "2014-11-10 07:25:52"},
      {"_key": "031", "timestamp": "2014-11-10 07:25:53"},
      {"_key": "032", "timestamp": "2014-11-10 07:25:54"},
      {"_key": "033", "timestamp": "2014-11-10 07:25:55"},
      {"_key": "034", "timestamp": "2014-11-10 07:25:56"},
      {"_key": "035", "timestamp": "2014-11-10 07:25:57"},
      {"_key": "036", "timestamp": "2014-11-10 07:25:58"},
      {"_key": "037", "timestamp": "2014-11-10 07:25:59"},
      {"_key": "038", "timestamp": "2014-11-10 07:26:00"},
      {"_key": "039", "timestamp": "2014-11-10 07:26:01"},
      {"_key": "040", "timestamp": "2014-11-10 07:26:02"},
      {"_key": "041", "timestamp": "2014-11-10 07:26:03"},
      {"_key": "042", "timestamp": "2014-11-10 07:26:04"},
      {"_key": "043", "timestamp": "2014-11-10 07:26:05"},
      {"_key": "044", "timestamp": "2014-11-10 07:26:06"},
      {"_key": "045", "timestamp": "2014-11-10 07:26:07"},
      {"_key": "046", "timestamp": "2014-11-10 07:26:08"},
      {"_key": "047", "timestamp": "2014-11-10 07:26:09"},
      {"_key": "048", "timestamp": "2014-11-10 07:26:10"},
      {"_key": "049", "timestamp": "2014-11-10 07:26:11"},
      {"_key": "050", "timestamp": "2014-11-10 07:26:12"}
      ]
    
      select Memos \
        --filter '_key == "003" && \
                  between(timestamp, \
                          "2014-11-10 07:25:24", \
                          "include", \
                          "2014-11-10 07:27:26", \
                          "exclude", \
                          {"too_many_index_match_ratio": 0.03})'
    
      table_create Tags TABLE_HASH_KEY ShortText
    
      table_create Memos TABLE_HASH_KEY ShortText
      column_create Memos tag COLUMN_SCALAR Tags
    
      load --table Memos
      [
      {"_key": "Rroonga is fast!", "tag": "Rroonga"},
      {"_key": "Groonga is fast!", "tag": "Groonga"},
      {"_key": "Mroonga is fast!", "tag": "Mroonga"},
      {"_key": "Groonga sticker!", "tag": "Groonga"},
      {"_key": "Groonga is good!", "tag": "Groonga"}
      ]
    
      column_create Tags memos_tag COLUMN_INDEX Memos tag
    
      select \
        Memos \
        --filter '_id >= 3 && \
                  in_values(tag, \
                           "Groonga", \
                           {"too_many_index_match_ratio": 0.7})' \
        --output_columns _id,_score,_key,tag
    
  • between GRN_EXPR_OPTIMIZE=yes をサポートしました。

    between() で、条件式の評価順序の最適化をサポートしました。

  • query_parallel_orquery match_columnsvector で指定できるようにしました。

    以下のように、 queryquery_parallel_ormatch_columnsvector を使えます。

    table_create Users TABLE_NO_KEY
    column_create Users name COLUMN_SCALAR ShortText
    column_create Users memo COLUMN_SCALAR ShortText
    column_create Users tag COLUMN_SCALAR ShortText
    
    table_create Terms TABLE_PAT_KEY ShortText \
      --default_tokenizer TokenNgram \
      --normalizer NormalizerNFKC130
    column_create Terms name COLUMN_INDEX|WITH_POSITION Users name
    column_create Terms memo COLUMN_INDEX|WITH_POSITION Users memo
    column_create Terms tag COLUMN_INDEX|WITH_POSITION Users tag
    
    load --table Users
    [
    {"name": "Alice", "memo": "Groonga user", "tag": "Groonga"},
    {"name": "Bob",   "memo": "Rroonga user", "tag": "Rroonga"}
    ]
    
    select Users \
      --output_columns _score,name \
      --filter 'query(["name * 100", "memo", "tag * 10"], \
                      "Alice OR Groonga")'
    
  • select 前方一致検索でセクションと重みをサポートしました。

    前方一致検索でマルチカラムインデックスと、スコアーの調整ができます。

      table_create Memos TABLE_NO_KEY
      column_create Memos title COLUMN_SCALAR ShortText
      column_create Memos tags COLUMN_VECTOR ShortText
    
      table_create Terms TABLE_PAT_KEY ShortText
      column_create Terms index COLUMN_INDEX|WITH_SECTION Memos title,tags
    
      load --table Memos
      [
      {"title": "Groonga", "tags": ["Groonga"]},
      {"title": "Rroonga", "tags": ["Groonga", "Rroonga", "Ruby"]},
      {"title": "Mroonga", "tags": ["Groonga", "Mroonga", "MySQL"]}
      ]
    
      select Memos \
        --match_columns "Terms.index.title * 2" \
        --query 'G*' \
        --output_columns title,tags,_score
      [
        [
          0,
          0.0,
          0.0
        ],
        [
          [
            [
              1
            ],
            [
              [
                "title",
                "ShortText"
              ],
              [
                "tags",
                "ShortText"
              ],
              [
                "_score",
                "Int32"
              ]
            ],
            [
              "Groonga",
              [
                "Groonga"
              ],
              2
            ]
          ]
        ]
      ]
    
  • grndb grndb recover で使用したオブジェクトを即時閉じるようにしました。

    これにより、メモリ消費を抑制できます。おそらくパフォーマンスは低下していますが、許容可能な低下です。 grndb check はまだ、使用したオブジェクトを即時閉じないので注意してください。

  • query_parallel_orquery 以下のように、 match_columnsscorer_tf_idf を指定できるようにしました。

      table_create Tags TABLE_HASH_KEY ShortText
    
      table_create Users TABLE_HASH_KEY ShortText
      column_create Users tags COLUMN_VECTOR Tags
    
      load --table Users
      [
      {"_key": "Alice",
       "tags": ["beginner", "active"]},
      {"_key": "Bob",
       "tags": ["expert", "passive"]},
      {"_key": "Chris",
       "tags": ["beginner", "passive"]}
      ]
    
      column_create Tags users COLUMN_INDEX Users tags
    
      select Users \
        --output_columns _key,_score \
        --sort_keys _id \
        --command_version 3 \
        --filter 'query_parallel_or("scorer_tf_idf(tags)", \
                                    "beginner active")'
      {
        "header": {
          "return_code": 0,
          "start_time": 0.0,
          "elapsed_time": 0.0
        },
        "body": {
          "n_hits": 1,
          "columns": [
            {
              "name": "_key",
              "type": "ShortText"
            },
            {
              "name": "_score",
              "type": "Float"
            }
          ],
          "records": [
            [
              "Alice",
              2.098612308502197
            ]
          ]
        }
      }
    
  • query_expand 展開後の語の重みを操作できるようにしました。

    展開後の語に対して、重みを指定できます。 スコアーを増やしたい場合は、 > を使います。スコアーを減らしたい場合は、 < を指定します。 数字でスコアーの量を指定できます。負の数も指定できます。

    table_create TermExpansions TABLE_NO_KEY
    column_create TermExpansions term COLUMN_SCALAR ShortText
    column_create TermExpansions expansions COLUMN_VECTOR ShortText
    
    load --table TermExpansions
    [
    {"term": "Rroonga", "expansions": ["Rroonga", "Ruby Groonga"]}
    ]
    
    query_expand TermExpansions "Groonga <-0.2Rroonga Mroonga" \
      --term_column term \
      --expanded_term_column expansions
    [[0,0.0,0.0],"Groonga <-0.2((Rroonga) OR (Ruby Groonga)) Mroonga"]
    
  • [httpd] バンドルしているnginxのバージョンを1.21.1に更新しました。

  • バンドルしているApache Arrowを5.0.0に更新しました。

  • Ubuntu Ubuntu 20.10 (Groovy Gorilla)サポートをやめました。

    • 2021年7月22日でEOLとなったためです。

修正

  • query_parallel_orquery query_options とその他のオプションを指定すると、その他のオプションが無視される問題を修正しました。

    例えば、以下のケースでは、 "default_operator": "OR" オプションは無視されていました。

    plugin_register token_filters/stop_word
    
    table_create Memos TABLE_NO_KEY
    column_create Memos content COLUMN_SCALAR ShortText
    
    table_create Terms TABLE_PAT_KEY ShortText \
      --default_tokenizer TokenBigram \
      --normalizer NormalizerAuto \
      --token_filters TokenFilterStopWord
    column_create Terms memos_content COLUMN_INDEX|WITH_POSITION Memos content
    column_create Terms is_stop_word COLUMN_SCALAR Bool
      
    load --table Terms
    [
    {"_key": "and", "is_stop_word": true}
    ]
      
    load --table Memos
    [
    {"content": "Hello"},
    {"content": "Hello and Good-bye"},
    {"content": "and"},
    {"content": "Good-bye"}
    ]
      
    select Memos \
      --filter 'query_parallel_or( \
                  "content", \
                  "Hello and", \
                  {"default_operator": "OR", \
                   "options": {"TokenFilterStopWord.enable": false}})' \
      --match_escalation_threshold -1 \
      --sort_keys -_score
    [
      [
        0,
        0.0,
        0.0
      ],
      [
        [
          [
            1
          ],
          [
            [
              "_id",
              "UInt32"
            ],
            [
              "content",
              "ShortText"
            ]
          ],
          [
            2,
            "Hello and Good-bye"
          ]
        ]
      ]
    ]
    

既知の問題

  • 現在Groongaには、ベクターカラムに対してデータを大量に追加、削除、更新した際にデータが破損することがある問題があります。

  • [ブラウザーベースの管理ツール] 現在Groongaには、レコード一覧の管理モードのチェックボックスにチェックを入れても、非管理モードに入力された検索クエリーが送信されるという問題があります。

  • *<*> は、filter条件の右辺に query() を使う時のみ有効です。もし、以下のように指定した場合、 *<*>&& として機能します。

    • 'content @ "Groonga" *< content @ "Mroonga"'
  • 多くのデータを削除し、同じデータを再度loadすることを繰り返すと、Groongaがヒットすべきレコードを返さないことがあります。

さいごに

詳細については、以下のお知らせも参照してください。

お知らせ 11.0.5リリース

それでは、Groongaでガンガン検索してください!

2021-06-29

Groonga 11.0.4リリース

Groonga 11.0.4をリリースしました!

それぞれの環境毎のインストール方法: インストール

変更内容

主な変更点は以下の通りです。

改良

  • [Normalizer] カスタマイズされたノーマライザーを使えるようになりました。

  • 新しいコマンド object_warm を追加しました。

    このコマンドは、GroongaのDBをOSのページキャッシュに乗せます。 OS起動後、Groongaを一度も起動していない場合、GroongaのDBはOSのページキャッシュ上に存在しません。 そのため、Groongaに対する最初の操作は遅くなります。

    予めこのコマンドを実行した場合、Groongaへの最初の操作は速くなります。 Linuxでは、 cat *.db > dev/null で同等のことができますが、Windowsでは、いままで同様のことはできませんでした。

    このコマンドを使うことで、LinuxでもWindowsでもGroongaのDBをOSのページキャッシュへ乗せることができます。 また、テーブル、カラム、インデックス単位でも同様のことができます。 したがって、よく使うテーブルやカラム、インデックスのみをOSのページキャッシュに乗せることができます。

  • select --filter 内で特定のレコードのスコアーを調整できるようにしました。

    *~ という演算子を使うことで、特定のレコードのスコアーを調整できます。 *~&&|| と同じ論理演算子です。したがって、 &&|| と同じように使えます。 *~ のデフォルトの重みは -1 です。

    したがって、例えば、 'content @ "Groonga" *~ content @ "Mroonga"' は以下の操作を意味します。

    1. 'content @ "Groonga"content @ "MySQL" にマッチしたレコードを抽出します。
    2. 以下のようにスコアーを追加します。
    a. 'content @ "Groonga"' のスコアーを計算します。
    b. 'content @ "Mroonga"' のスコアーを計算します。
    c. bのスコアーを -1 倍します。
    d. このレコードのスコアーは a + b です。したがって、 aのスコアー 1 で bのスコアーが1 の場合、
       このレコードのスコアーは 1 + (1 * -1) = 0 です。
    

    また、 *~${score_quantity} とすることで、スコアーの量を指定できます。

    具体的には、 以下の条件( 'content @ "Groonga" *~2.5 content @ "MySQL"' ) にマッチしたレコードのスコアーを調整します。

      table_create Memos TABLE_NO_KEY
      column_create Memos content COLUMN_SCALAR ShortText
    
      table_create Terms TABLE_PAT_KEY ShortText \
        --default_tokenizer TokenBigram \
        --normalizer NormalizerAuto
      column_create Terms index COLUMN_INDEX|WITH_POSITION Memos content
    
      load --table Memos
      [
      {"content": "Groonga is a full text search engine."},
      {"content": "Rroonga is the Ruby bindings of Groonga."},
      {"content": "Mroonga is a MySQL storage engine based of Groonga."}
      ]
    
      select Memos \
        --command_version 3 \
        --filter 'content @ "Groonga" *~2.5 content @ "Mroonga"' \
        --output_columns 'content, _score' \
        --sort_keys -_score,_id
      {
        "header": {
          "return_code": 0,
          "start_time": 1624605205.641078,
          "elapsed_time": 0.002965450286865234
        },
        "body": {
          "n_hits": 3,
          "columns": [
            {
              "name": "content",
              "type": "ShortText"
            },
            {
              "name": "_score",
              "type": "Float"
            }
          ],
          "records": [
            [
              "Groonga is a full text search engine.",
              1.0
            ],
            [
              "Rroonga is the Ruby bindings of Groonga.",
              1.0
            ],
            [
              "Mroonga is a MySQL storage engine based of Groonga.",
              -1.5
            ]
          ]
        }
      }
    

    adjuster を使っても同様のことができます。 adjuster を使う場合、アプリケーション上で、 --filter 条件と --adjuster 条件を作る必要がありますが、この改良で、 --filter 条件のみを作成すればよくなりました。

    以下のように、 query() を使って、filter条件を記述することもできます。

    • --filter 'content @ "Groonga" *~2.5 content @ "Mroonga"'
  • select 重み付き && をサポートしました。

    *<*> を使うことで、重み付きの && を使えます。 *< のデフォルトの重みは 0.5です。 *> のデフォルトの重みは 2.0 です。

    *<${score_quantity}*>${score_quantity} とすることで、スコアーの量を指定できます。 また、 *<${score_quantity} と指定した場合は、 ${score_quantity} の正負の符号が反転します。

    例えば、 'content @ "Groonga" *<2.5 query("content", "MySQL")' は以下の操作を意味します。

    1. 'content @ "Groonga"content @ "MySQL" にマッチしたレコードを抽出します。
    2. 以下のようにスコアーを追加します。
    a. 'content @ "Groonga"' のスコアーを計算します。
    b. 'query("content", "MySQL") のスコアーを計算します。
    c. bのスコアーは、 *< によって -2.5倍されます。
    d. このレコードのスコアーは a + b です。したがって、 aのスコアー 1 で bのスコアーが1 の場合、
       このレコードのスコアーは 1 + (1 * -2.5) = −1.5 です。
    

    具体的には、 以下の条件( 'content @ "Groonga" *~2.5 query("content", "MySQL")' ) にマッチしたレコードのスコアーを調整します。

      table_create Memos TABLE_NO_KEY
      column_create Memos content COLUMN_SCALAR ShortText
    
      table_create Terms TABLE_PAT_KEY ShortText \
        --default_tokenizer TokenBigram \
        --normalizer NormalizerAuto
      column_create Terms index COLUMN_INDEX|WITH_POSITION Memos content
    
      load --table Memos
      [
      {"content": "Groonga is a full text search engine."},
      {"content": "Rroonga is the Ruby bindings of Groonga."},
      {"content": "Mroonga is a MySQL storage engine based of Groonga."}
      ]
    
      select Memos \
        --command_version 3 \
        --filter 'content @ "Groonga" *<2.5 query("content", "Mroonga")' \
        --output_columns 'content, _score' \
        --sort_keys -_score,_id
      {
        "header": {
          "return_code": 0,
          "start_time": 1624605205.641078,
          "elapsed_time": 0.002965450286865234
        },
        "body": {
          "n_hits": 3,
          "columns": [
            {
              "name": "content",
              "type": "ShortText"
            },
            {
              "name": "_score",
              "type": "Float"
            }
          ],
          "records": [
            [
              "Groonga is a full text search engine.",
              1.0
            ],
            [
              "Rroonga is the Ruby bindings of Groonga.",
              1.0
            ],
            [
              "Mroonga is a MySQL storage engine based of Groonga.",
              -1.5
            ]
          ]
        }
      }
    
  • Log 標準出力、標準エラー出力への出力をサポートしました。

    プロセスログクエリーログ が標準出力と標準エラー出力への出力をサポートしました。

    • --log-path ---query-log-path - と指定した場合、Groongaはログを標準出力に出力します。
    • --log-path +--query-log-path + と指定した場合、Groongaはログを標準エラー出力に出力します。

    プロセスログ は、Groongaの動作全てに関することのログです。 クエリーログ は、クエリー処理に関することだけのログです。

    この機能はDocker上でGroongaを実行する際に有用です。 Dockerは標準で標準出力と標準エラー出力を記録する機能を持っています。したがって、Groongaのログを取得するために、 Dockerの環境にログインする必要がなくなります。

  • [ドキュメント] string_substring に不足している内容を追加しました。

既知の問題

  • 現在Groongaには、ベクターカラムに対してデータを大量に追加、削除、更新した際にデータが破損することがある問題があります。

  • [ブラウザーベースの管理ツール] 現在Groongaには、レコード一覧の管理モードのチェックボックスにチェックを入れても、 非管理モードに入力された検索クエリーが送信されるという問題があります。

  • *<*> は、filter条件の右辺に query() を使う時のみ有効です。もし、以下のように指定した場合、 *<*>&& として機能します。

    • 'content @ "Groonga" *< content @ "Mroonga"'

さいごに

詳細については、以下のお知らせも参照してください。

お知らせ 11.0.4リリース

それでは、Groongaでガンガン検索してください!