TiDB Serverless の Chat2Query を試してみる
はじめに
NewSQLとして注目を集めているTiDBについて、今回はそのサーバレスDBaaSであるTiDB Servelessを取り上げます。
TiDB Serverless は無償で利用開始でき従量課金であるという特徴の他に、AIを利用して自然言語からクエリを生成してくれる Chat2Query という機能があるので、これを試してみます。
環境構築
少しレガシーなゲームのデバッグ用環境のDB(MySQL5.7.x)から、データをTiDB Serverlessに突っ込んでChat2Queryを雑に扱う、というような検証を行いました。
まずTiDB Serverlessにデータを投入する必要があります。今回は、IaaS上で動いているMySQLを運用していれば珍しくないであろう、 mysqldump
コマンドで取得されたデータ(DDL込み)を持ってきてS3に配置し、TiDB ServerlessのImportで読み取りました。しかし、残念ながらそうしたデータをImportは読んでくれません。
データを投入するには、Importが読める形式に合わせる必要があります。
データ加工を考えるのは少し面倒だな、と思っていたところ、PingCAPの方からTiDB用のツール群である tiup
に含まれるdumpデータ取得ツール dumpling
Dumpling Overview | PingCAP Docs を使えば問題無いというアドバイスをいただきました。
tiup dumpling
の具体的な利用方法として、以下のようなコマンドを教えて貰っています。
tiup dumpling \
-u "dbuser" \
-p "******"" \
-P 4000 \
-h <host> \
-F 256MiB \
-o "<s3 Bucket>" \
--s3.region "<region>" \
--filetype csv \
--filter "gamedb.*" \
--output-filename-template '{{.DB}}.{{.Table}}.{{.Index}}'
なお、現状の最新の tiup
(v8.1.0)だとTLS必須になっており、レガシーすぎるMySQLだと繋がらないかもしれません。
(今回の試験用の環境は繋がりませんでした…)
その場合、以下のように tiup
のバージョンを指定して再インストールします。
tiup uninstall dumpling --all
tiup install dumpling:v7.5.1
v7.5.1 はTLS必須化前のバージョンということで、今回のケースではこちらを利用します。
Importを使ったデータ投入はTiDBコンソールやドキュメントの指示通りで概ね問題無いので省きます。 今回はS3 bucketに投入用のデータを配置したのでS3 IAM Roleを用意しています。 Role設定時に許可対象として必要な Account ID と External ID は、TiDBコンソールのImport画面で Guide for getting the required Role ARN から取得できます。 Guideという事なのでドキュメントへのリンクかと思っていたら、必要なID情報があるので若干罠かも知れません…
Chat2Queryを使ってみる
データ投入が終わったらいきなりChat2Queryが使えます。 特に事前準備は不要です。 DB規模にもよると思われますが、その場でスキーマを読んだりもしているのか、若干応答までに時間は掛かります。
早速、ゲームの運営をしていたら気になりそうな情報を取得するために、Chat2Queryにクエリを生成してもらいます。
> 一番長くゲームを遊んでいるユーザの名前を教えて?

ユーザ作成日時に着眼した、欲しい情報が取得できそうなクエリが生成されました。しかし実際には、残念ながらそのユーザが現在も遊んでくださっているとは限らないので、 NOW()
との比較よりは何らか別の最終ログイン日時等のデータと比較した方が良いでしょう。 この環境では別DBに t_user_login_bonus
というテーブルがあるので、そこのデータを組み合わせてあげるのが良いのですが、DBをまたいだクエリの処理には対応していませんでした。
TIMESTAMPDIFF関数を叩きまくりそうなのも負荷的にちょっと怖い。
> 全ユーザ数を教えて

何故か変なテーブルからデータを拾ってしまいました。

テーブル指定を付け加えると、それに従って想定通りのクエリを生成してくれました。
> ガチャを回した数の多いユーザの上位10名

これは上手くいきませんでした。 「ガチャを回す」という表現からデータの動きを類推できないのかもしれません。
> 一番フレンド数の多いユーザとそのフレンド数を教えて

十分使えそうなクエリです。
ちなみに、一度生成されたクエリに対して、Chat2Queryで追加修正ができます。

件数など簡単な直しは余裕の模様です。

フレンド数という本来のテーブルが持っていない曖昧な対象を指定しても、意図した通りの修正をしてくれました。
> 特定キャラを保有しているユーザの調査

よくありそうなユーザデータの調査です。 生成されたクエリは正確でツッコミどころはありません。

ただ、残念ながら前段のクエリの結果を受けるようなクエリは作れないようです。

ただし、複数条件を一通り書けばまとめて取るクエリは作ってくれました。
> ログボが一番多いユーザを教えて

「ログボ」とかいう雑な指定で t_user_login_bonus
テーブルを選ぶことができたのは凄い。 何ならゲーム業界未経験だったりしたら、人間でも「ログボって何?」となる気がします。
> 一年以内に開始されたクエストで、一番遊ばれたクエストはどれ?

時間の指定についても解釈してくれます。

クエリの修正でも使えます。(JSTかどうかは若干怪しい)
> 招待報酬の受け取りフラグが0のデータを20に更新したい

更新系クエリも作れます。 このケースでも割と正確なクエリを作ってくれました。
ざっくりレビュー
- TiDBは
tiup dumpling
など周辺ツールも充実しておりデータ投入は行いやすい。- 既存の
mysqldump
のデータから投入しようとすると、DDLを分離する必要があるなどかなり面倒そう…
- 既存の
- Chat2Queryは利用者側がデータ構造を理解していないと間違いに気付けない点はどうしようもなく、手軽ではあるが気軽に使ってしまって大丈夫かは別問題。(ハルシネーションの問題はここにもある)
- 逆にある程度データが分かっていて具体的な指示が出せれば、精度の高いクエリは出てくる。
- いい加減な指定でもある程度は動いてくれるので、見知らぬDBの調査をする時には便利かも(あまり想像したくないシチュエーションですが)
- 既存クエリの直しや拡張などでも使えるので、期間指定などを修正して使いたい時などは楽ができるかも。
- TiDB ServerlessのRequest Unit(RU)はChat2Queryのクエリ生成でも消費される模様。
- ExplainでもRU消費がある。実行時と同等の消費があるケースも見られた。
- TiDBコンソールのDiagnosisで確認できるのでどんなクエリがRU消費が多いのか見てみると良い。
- ExplainでもRU消費がある。実行時と同等の消費があるケースも見られた。
- クラスターを作るとPublicエンドポイントが有効になっているので、テスト目的で無ければ disabled にした方が良い。
- Private接続についてはAWSのPrivate Linkなどの準備をする必要がある。
- GCPなど他クラウドプラットフォーム向けのPrivateLink提供はまだの模様。(2024年6月の検証時点での情報です)
総評
- DBエンジニアなら使いやすい。
- 調査目的でのクエリのベース作りや、簡単なデータ更新クエリの作成などは楽になるかも。 正確なテーブル名を指定しなくても可読性のあるテーブル名であれば類推してくれる。
- 課金に繋がるRU消費が読みにくいのが気になるところ。
- 費用的にはVPCエンドポイントを構える分が必要で、Publicエンドポイントで運用しない限りはFree Tierでも完全に無料で使えるという訳ではないので注意。