💠

jinja2 ベースの自作テンプレートエンジンで sqlc の対抗を作ってみた

2024/09/01に公開

※ Disclaimer: ツール自体は OSS 公開になっていますが、現段階でメンテする予定はない(基本自分用)ためここで名前やリンクなどは載せないこととします。

普段は sqlc を使っていませんが(CRUDを直接コード生成するため)こちらのツイートで少し興味を持ったためです。https://x.com/voluntas/status/1821912712638820653

jinja2 は Python ベースのテンプレートエンジンです。ansible や最近では dbt で利用されているので割と有名だと思います。

対象は play.sqlc.dev にあるスキーマとクエリをベースにした検証となります。

一段階目としてスキーマとクエリをそれぞれパースします。詳細は割愛。

仕組みとしては github.com/pganalyze/pg_query_go/v5 を利用して Go で SQL を読み込むイメージです。

読み込んだものを一旦 JSON に落とします。(JSONに落としている理由はこちらツールは sql のみならず GraphQL や OpenAPI まで幅広く対応するため中間レイヤー相当となります、本記事対象外)

JSON で見るとこういうイメージです。

ParseToJSON というメソードもあるので pg_query_go で直接JSONに落とすのも可能です。
(自分はカスタマイズしたいので使っておりません)

JSON が用意できましたら jinja2 ベースの自作テンプレートエンジンに渡します。
モデルの生成は一番シンプルでテンプレートは以下となります。

スキーマ

※ ヘッダーの部分とかは別ファイルで用意するイメージです。
生成されるコード(型などは適度にマッピングする感じです)

次はクエリの生成です。
スキーマ

クエリのJSONはこんな感じです。

SQL 部分のコード生成用のテンプレート

生成されるコード

Go のメソードを生成用のテンプレート

生成されるコード

Insert 文

テンプレート

生成されるコード

DELETE や List または Update も似たようなものなのでここでは省略します。

sqlc のコードと比較して実装部分に差分がないことまでは確認できました。

実際試しているのはサンプルにあるコードのみなので sqlc の他の機能に関しては調整は必要になるかと思います。

以上

Discussion