[groonga-dev,02677] Re: ベクターカラム適用DBをダンプファイルから正常に復元する方法

Back to archive index

Naoya Murakami visio****@gmail*****
2014年 8月 22日 (金) 01:23:19 JST


村上です。

2014年8月21日 19:55 Kimura A <a.kim****@live*****>:

>
>
> Windows版Mroongaでベクターカラムを使ったDBを作成し、いったんMySQLDumpしてからインポートした場合に、ベクターカラムによる検索が機能しなくなってしまい困っています。
> 以下、「mroongaでベクターカラムを使ってタグ検索を実現するには」の例に従って再現手順を書いてみます。
> http://qiita.com/groonga/items/f41cd8cfbe7bd158d5da
>
> 記事との違いは、以下の3点です。
> ◯テーブル名は小文字に統一:以前Windows環境で何かトラブルが起きたことがあったので。
> ◯「ENGINE=mroonga」を加筆:InnoDBになってしまうため。
>
> ◯インデックス用テーブルtagsに「1_」を前置:MySQLDumpファイルからのインポート時に、tags(1_tags)がbugsより先に生成されるようにするため。
>

> まずtestデータベース内に、1_tagsおよびbugsテーブルを作成します。
>
> use test;
>
> CREATE TABLE 1_tags (
>   name VARCHAR(64) PRIMARY KEY
> ) DEFAULT CHARSET=utf8
>   COLLATE=utf8_bin
>   ENGINE=mroonga
>   COMMENT='default_tokenizer "TokenDelimit"';
>
> CREATE TABLE bugs (
>   id INT PRIMARY KEY AUTO_INCREMENT,
>   tags TEXT COMMENT 'flags "COLUMN_VECTOR", type "1_tags"',
>   FULLTEXT INDEX(tags)
> ) DEFAULT CHARSET=utf8
>   ENGINE=mroonga;
>

記事とはFULLTEXT INDEXの作り方が異なっています。
(ちなみにこのQiitaの記事は以前誤っており編集されております。)

記事では、
FULLTEXT INDEX bugs_tags_index(tags) COMMENT 'table "Tags"'
となっているのに対し、

上記では、
  FULLTEXT INDEX(tags)
となっています。

コメントがない方法では、ベクターカラムに対して通常の全文インデックス
と同じ方法でインデックスが作成されてしまいます。

この方法では、データ追加時以外では文字列のデータを取得できない
ため(Groongaではベクター型で保存されている)、オフラインでの
インデックス構築ができません。

以下のスレッドで須藤さんに教えてもらいました。

http://sourceforge.jp/projects/groonga/lists/archive/dev/2013-September/001778.html

mysqldumpのダンプファイルでは、
ALTER TABLE bugs DISABLE KEYS;
INSERT ...
ALTER TABLE bugs ENABLE KEYS;
となっています。

ALTER TABLE bugs DISABLE KEYSで全文インデックス用の
インデックスカラムが削除されます。
ALTER TABLE bugs ENABLE KEYSで全文インデックス用の
インデックスカラムが作成されますが、ベクター型なので値を取得
できず、インデックスの中身は空のままです。

一応、ENABLEの状態でINSERTすれば、インデックスが作られるとは
思いますが、この使用方法はサポートされていないようです(上記スレッド
参照)。

Qiitaの記事のインデックスの作成方法だと、bugsのFULLTEXT
インデックスにより、Groonga的にはインデックスカラムは1_tagsの
方に作成されて、bugsテーブルのtagsカラムを対象にします。
(たぶんわけがわからないと思います)

この方法ならbugsテーブルでDISABLEをしても1_tagsカラムの
インデックスカラムが削除されません。
なので、この状態でINSERTしてもインデックスが作成されます。

◯上掲のような経緯でタグ検索が不可能になったDBを復旧させる方法
>

Qiitaの記事の方法のように、テーブル参照型のインデックスを
張ればいい思います。こうすれば、そのままダンプファイルを
リストアすることができました。

このほかのsyntaxエラー等は環境による何かだと思いますが
よくわかりません。
私の場合、メールにあったものそのままコピペで通りました。
(インデックスは作成されませんが。)

---
ところで、テーブル参照型のインデックスをALTER TABLE でDROP
した場合、Groonga側のインデックスカラムがたどって削除されない
挙動を見つけました。

削除されていないのでもっかいつくろうとするとmysqldが死にます。

たぶん<テーブル名>-<インデックス名>の規則の語彙表削除の
処理しか入っていないんじゃないかなぁと思います。

https://github.com/mroonga/mroonga/blob/master/ha_mroonga.cpp#L13364-L13372

おそらく、インデックス対象のカラム名をとってきて、そのカラム名に張
られているGroongaのインデックスをgrn_column_indexで探してきて、
削除する処理を追加する感じですかね。

<再現例>

CREATE TABLE indexes (
  memo varchar(64) NOT NULL,
  PRIMARY KEY (memo)
)ENGINE=mroonga DEFAULT CHARSET=utf8

CREATE TABLE diaries (
  id int(11) NOT NULL AUTO_INCREMENT,
  title text,
  PRIMARY KEY (id),
  FULLTEXT INDEX title(title) COMMENT 'table "indexes"'
) ENGINE=mroonga DEFAULT CHARSET=utf8;

ALTER TABLE diaries DROP INDEX title;
ALTER TABLE diaries ADD FULLTEXT INDEX title(title) COMMENT 'table
"indexes"'

以上です。



groonga-dev メーリングリストの案内
Back to archive index