はじめに
私は GraphQL Schema を記述する .graphql
( .gql
) を分割管理しています。
また、GraphQL Code Generator で TS 向けに型を出力して、型安全生活を送っています。
1# ディレクトリ構造の例
2$ tree . -L 2
3.
4├── codegen.yml
5├── dis
6│ └── schema.graphql # `src/*.graphql`が統合されたファイル
7├── package.json
8├── src
9│ ├── category.graphql
10│ ├── main.graphql
11│ ├── post.graphql
12│ └── tag.graphql
13├── tsconfig.json
14└── yarn.lock
分割方式は有用だと考えているのですが、一点だけ悩みがありました。
分割された .graphql
をどう統合するかです。
そこで、今回は .graphql
をどう統合するかの私的な改善を備忘録しておきます。
tl; dr
GraphQL Code Generator の Schema AST という plugin を使えば、.graphql
を統合できます。
当たり前の当たり前ですが、これに気がつくのに時間がかかりました 💦
1yarn add -D @graphql-codegen/schema-ast
1# 公式例
2schema:
3 - "./src/schema.graphql"
4generates:
5 path/to/file.graphql:
6 plugins:
7 - schema-ast
8 config:
9 includeDirectives: true
なぜ分割管理してるの?
- 単一ファイルで膨れ上がる Schema を管理するのが単純に辛い
- GraphQL Code Generator で特定の
.graphql
を選別して読み込みたい時がある
分割しているために筆者が困っていたこと
.graphql
を分割しているのだから、それを統合してあげる必要があります。
そして、今までこの統合処理を package.json
のスクリプト配下に自前で書いていました。
concat という package で src
配下の *.gql
を dist/schema.gql
に統合出力していました。
1{
2 "scripts": {
3 "build:concat": "mkdir dist && concat -o dist/schema.gql src/*.gql"
4 }
5}
たいした処理でもないので気にする必要はないかと思いましたが、以下の観点で改善したいと考えていました。
*.graphql
を統合するためだけに、concat
という package を管理する必要がある- 特定の
*.graphql
は混ぜたくないと考えると、とたんにコマンドが複雑化してしんどくなる- 私的なモノレポ構成だと Schema を共有管理しているため、A のバックエンドに含めたくない Schema だが、B のバックエンドには必要などのケースがありました
どうしたのか?
そもそも GraphQL Code Generator で .graphql
を統合できないのか?が純粋に浮かびました。
調べると、Schema AST という plugin があるではないですか、同 plugin なら schema を統合できます。
This plugin prints the merged schema as string. If multiple schemas are provided, they will be merged and printed as one schema. Schema AST より
上述のディレクトリ構成とコマンドを鑑みると以下のように変更して解決しました。
ただし、Schema AST で統合できるのは .graphql
の拡張子のみです。
.gql
では統合できなかったので、リネームしました。
1# codegen.yml
2generates:
3 dist/schema.graphql:
4 schema:
5 - src/**/*.graphql
6 plugins:
7 - schema-ast
1// graohql-codegenで`dist/schema.graphql`に出力される
2{
3 "scripts": {
4 "build:generate": "graphql-codegen --config codegen.yml"
5 }
6}
おわりに
今回はこの Schema AST を使って .graphql
を統合した方が楽ですよ話でした、以上、ありゃっした!!
なのですが、なぜこんな単純な解決があるのに、ややこしい方法に至ったか自分で自分が不思議でなりません 🌝