Slide 1

Slide 1 text

TiDB の SQL Parser を使用して CSV ファイルの不備を検知する仕組み 1 Go Connect #5 2025/02/19 (Web) @mwudo / 岸田慎之介

Slide 2

Slide 2 text

2 自己紹介 ●  SO Technologies 株式会社 ●  新卒4年目 ● Go言語でAPI/バッチ処理の開発を主に行いつつ 問い合わせの調査も行っている グループ横断の取り組みで使うアプリの開発にも従事 ●  毎週ボルダリングに通ってる 岸田 慎之介 @mwudo

Slide 3

Slide 3 text

話すこと 3 テストで使用している CSV ファイルの不備に気づくために SQL Parser の使った取り組みについて紹介

Slide 4

Slide 4 text

CSVの不備 4 開発で DB 定義(DDL)に則したダミーデータ を CSV ファイルとしてリポジトリで用意 CSV ファイルを DB へ投入するときのコマンドは LOAD DATA LOCAL INFILE を使用 既存の DB のテーブル定義に対して列の追加・削除などの対応を 行った時に漏れる場合があった

Slide 5

Slide 5 text

SQL Parser の導入 5 正規表現 を使用して検知を試みた ChatGPT などを使えば正規表現を用意することは可能 正規表現自体が複雑になり保守性が低い しかし

Slide 6

Slide 6 text

SQL Parser の導入 6 PingCAP が開発している TiDB で使用されている SQL Parser https://github.com/pingcap/tidb/tree/master/pkg/parser

Slide 7

Slide 7 text

github.com/pingcap/tidb/pkg/parser 7 SQL を抽象構文木(以下 AST)に変換 AST のノードを参照することで SQL の情報を取得することが可能 https://github.com/pingcap/tidb/tree/master/pkg/parser MySQL のほとんどの構文をサポート 数行の実装を追加するだけで、独自の構文をサポート パフォーマンスがよい README によると、

Slide 8

Slide 8 text

実装の一部を紹介 8 AST のノードを取得するためには、以下の interface を実装

Slide 9

Slide 9 text

実装の一部を紹介 9 DDL の情報を取得するために構造体は以下のように定義

Slide 10

Slide 10 text

実装の一部を紹介 TableDef のメソッドに Visitor を実装 10

Slide 11

Slide 11 text

実装の一部を紹介 SQL を引数にして parser.New().ParseSQL を呼び出し Accept を実行すると、AST のノードが取得され def に情報を格納 11

Slide 12

Slide 12 text

実装の一部を紹介 12 型ごとに期待される値かどうかテスト

Slide 13

Slide 13 text

検知する仕組みを取り入れた結果 いくつか不備を見つけた 13 カラム名が間違っていた データのフォーマットが異なっている 列不足のデータも存在 当初の目的は果たせている ● 例:2020-01-01 00:00:0 → 2020-01-01 00:00:00

Slide 14

Slide 14 text

さらなる改善 DDL のカラムの順序と CSV ファイルの列の順序が異なっていると検知できていない LOAD DATA LOCAL INFILE は DDL のカラムの順序のつもりで CSV ファイルを解釈する 14 カラムの順序の検知もテストに加えたい

Slide 15

Slide 15 text

参考記事 ❏ TiDB の SQL Parser を使用して CSV ファイルの不備を検知する仕組み ❏ TiDBのSQLパーサーを使ってみました ❏ pingcap/parser (MySQL互換) で SQL を手軽に解析 ❏ GolangでMySQLのSQL文をパースする(CREATE TABLE文のパース例) 15