2024.10.01
自社の社内情報を未来の“ゴミ”にしないための備え 「情報量が多すぎる」時代がもたらす課題とは?
リンクをコピー
記事をブックマーク
山本祥太氏:『gqlgencを作成した』というタイトルで発表していきたいと思います。よろしくお願いします。僕の名前は山本祥太と言います。ふだんは株式会社Appify TechnologiesでGAE(Google App Engine) Goを使ったサーバーサイドの開発や、React、TypeScript、ApolloでWebフロントの開発を行っています。Twitter、GitHubのIDはこちらなので、もしよかったらフォローをよろしくお願いします。
今回の目次はこんな感じになっています。gqlgencというGoのGraphQLクライアントライブラリ生成ツールを作ったという話をベースに、GraphQLとGoの組み合わせについて興味をもってもらおうという構成になっています。
はじめにGraphQLの説明をざっくりして、gqlgencがなぜ必要でどう良いのかを説明したあとに、gqlgencそのものを使ってみるということで今回の発表を締めたいと思います。
まず、GraphQLの説明から入っていきたいと思います。GraphQLはFacebookが開発元のAPIクエリ言語であり、ランタイムです。表現力が非常に高いのが特徴で、複雑なデータ構造をスキーマ上で表現することが可能です。
その型をそのままクライアント側も取得でき、それによってクライアント側もサーバー側も多くの恩恵を受けられるのですが、よく言われる恩恵の1つが「オーバーフェッチングを避けられる」です。
従来のものだと、クライアントがAPIを叩く時に不要なデータが入って来ても、リクエストとレスポンスが1対1の対応をしているので、そのまま受け取らなければいけなかったのですが、GraphQLはクエリで定義するので、不要なデータをクエリで定義しなければオーバーフェッチングを避けられます。
次にGraphQLはどのくらい流行っているのかを見たかったので、今回は世界の検索トレンド5年分のグラフを用意しました。gRPCが赤色で、GraphQLが青色で表現されています。これを見るとGraphQLのほうが若干人気があるのかなと思います。
日本だとそこまで差はなくて、ほとんど同じくらいのトレンドに見えます。これは日本の5年間のグラフです。ただ、記事やコミュニティのサイズなどもいろいろと見てみると、gRPCのコミュニティは日本だと特に大きく、GraphQLはあまりないので、まだまだGraphQLはこれからの技術なのかなと感じます。
ただ、さまざまな企業がAPIとして採用していて、GitHubだったりshopifyだったりがGraphQLのAPIを公開しています。それ以外にも多くの事例があるのですが、ここでは紹介しきれないので、見たい方は採用事例がわかるgraphql.org/usersをぜひ見に行ってください。
次に、なぜ必要になったのかをお話しします。弊社では「Appify」というサービスを開発しています。過去にもほかにいろいろなサービスを開発をしていたのですが、その頃はprotobuf(Protocol Buffers)をベースに開発していました。protobufからサーバーのコードとクライアントのコードを生成して、クライアントのコードはe2eのクライアントとして使用していました。
Appifyを作るとなった時に、GraphQLにしようとなりましたが、protobufで開発していた頃と同じ開発フローを踏みたいという要望があり、サーバーとクライアントのコードをGraphQLから生成できれば同じようなことができるんじゃないかということで、それを目指していました。
GraphQLの場合はスキーマとクエリが分かれているので、それぞれ役割が違います。スキーマからはサーバーのコードを作る必要があって、クライアントはスキーマを元にクエリが書かれるので、スキーマとクエリからクライアントのコードを生成する必要があります。
サーバーのコードを生成するツールとしてgqlgenはすでに存在していて、スキーマを書いてgqlgenコマンドを叩くとサーバーのコードが生成されます。ただ、クライアントのコードを生成するものは存在しなくて、gqlgenはあくまでもサーバーのコードのみを生成してくれるものなので、クライアントコードには対応していませんでした。
なので、僕はここの間を埋めるためにgqlgencというツールを作って、弊社の開発フローを保とうと思いました。これがあると、スキーマクエリドリブンで開発が行えるようになります。
具体的には、スキーマを編集してgqlgenコマンドを叩くと、サーバーのコードが生成されます。そのあとサーバーに独自のロジックをどんどん追加して開発ができます。
ただ、例えばスキーマの変更が入ったり、新しいクエリを追加したりする時は、まずクエリを編集する必要があります。そのあとに、それに該当するクライアントStructやクライアントそのもののコードに変更を加えて、それを使って処理を書いていきます。
クエリ編集とクライアントの中間の部分をgqlgencに任せて、スキーマの変更、もしくは新しいクエリの追加であればクエリを変更してgqlgencコマンドを叩くことで、そのクライアントに該当するStructの型が変更されたり、クライアントそのものが変更されて生成されたりするので、あとはそれを使うだけです。
ここからは、GraphQL Clientの作成について話していきたいと思います。GraphQLを作成するにあたって、最低限何がそろっているとよいのか、6つの条件を挙げました。これはあくまでも最低限で、ほかにもGraphQLのAPIクライアントとして必要なものはあるのですが、今回は6つ挙げました。
それぞれを細かく見ていきます。まずは、GraphQL Schema Parserです。これはGraphQLスキーマを静的解析して、サーバー側で定義されているスキーマファイルを読み取って、そこからASTのツリーを作成するというものです。
次にIntorospection to Client Schemaです。Intorospectionという言葉があまり耳馴染みがない方も多いと思うのですが、これはGraphQLが用意している特殊なクエリで、GraphQLのサーバーに投げるとスキーマの定義の情報がJSON形式で取得できます。
このJSONからスキーマのASTツリーを作成することが可能になります。これがあると、スキーマファイルが手元になかったとしてもエンドポイントさえわかっていればスキーマ情報を取得できます。
次にGraphQL Query Parserです。これはクライアント側が書いているGraphQLのクエリを静的解析してASTのツリーを作るというものです。
4つ目が、GraphQL Query Response Model Ganeratorです。これはスキーマとクエリのASTからGraphQLの型を生成するものです。これまで用意してきたASTのツリーを使って、Goの型などを生成します。
次にGraphQL Client Generatorです。これはGraphQL Query Response Model Ganeratorで生成した型を使ってリクエストを投げて、返ってきた結果をレスポンスにマッピングできるクライアントを生成するというものです。
最後にGraphQL JSON Parserです。これはGraphQL特有のJSONをパースして、生成された型にマッピングするのですが、これはクライアントの中で使われるものなのですが、GraphQL特有の定義に対応していて、生成された型に対してマッピングができるJSON Parserを用意する必要があります。
次に、従来のGo GraphQL Clientが先ほどの6つのうちのどれに対応しているかを見ていこうと思います。
これは一番下のGraphQL JSON Parserのみに対応しています。なので、スキーマ情報を取ってきたり、Intorospectionを叩いたりはできません。単純にクエリのストリングを受けて、自分たちの手元で用意したレスポンスを受ける型のStructを用意して、それにデータをアサインしてくれるというかたちだったので、今回自分たちのユースケースには合わないと判断して採用はしませんでした。
次は、それぞれ6つの条件に当てはまるライブラリが存在しないのかを見ていこうと思います。まずはGraphQL Schema Parserです。これはgqlgenの作者が作っているgqlparserが存在するので、これを利用することにしました。
次にIntorospection to Client Schemaですが、これに関しては実装しているものが一切見つからなかったので、自作することにしました。次のGraphQL Query Parserですが、これはGraphQL Schema Parserと同じgqlparserが利用できるので、これを利用します。
GraphQL Query Response Model Ganeratorは、gqlgenがスキーマ情報からモデルのみを生成するものを作っているので、それを利用します。リクエスト、レスポンスの型に関しては生成するものがなかったので、それに関しては自作する必要があります。
次にGraphQL Client Generatorです。リクエスト、レスポンスを生成するものがない時点で、これも生成するものがないので作る必要があります。最後にGraphQL JSON Parserですが、これは先ほど紹介したクライアントのうちの1つ目のParserを参考に実装することにしました。
作成が必要なものは、Intorospection to Client SchemaとGraphQL Query Response Model GaneratorとGraphQL Client Generatorの3つで、そのうえでgqlparserやほかの実装を参考にしてgqlgencは作成されています。
(次回へつづく)
2024.10.29
5〜10万円の低単価案件の受注をやめたら労働生産性が劇的に向上 相見積もり案件には提案書を出さないことで見えた“意外な効果”
2024.10.24
パワポ資料の「手戻り」が多すぎる問題の解消法 資料作成のプロが語る、修正の無限ループから抜け出す4つのコツ
2024.10.28
スキル重視の採用を続けた結果、早期離職が増え社員が1人に… 下半期の退職者ゼロを達成した「関係の質」向上の取り組み
2024.10.22
気づかぬうちに評価を下げる「ダメな口癖」3選 デキる人はやっている、上司の指摘に対する上手な返し方
2024.10.24
リスクを取らない人が多い日本は、むしろ稼ぐチャンス? 日本のGDP4位転落の今、個人に必要なマインドとは
2024.10.23
「初任給40万円時代」が、比較的早いうちにやってくる? これから淘汰される会社・生き残る会社の分かれ目
2024.10.23
「どうしてもあなたから買いたい」と言われる営業になるには 『無敗営業』著者が教える、納得感を高める商談の進め方
2024.10.28
“力を抜くこと”がリーダーにとって重要な理由 「人間の達人」タモリさんから学んだ自然体の大切さ
2024.10.29
「テスラの何がすごいのか」がわからない学生たち 起業率2年連続日本一の大学で「Appleのフレームワーク」を教えるわけ
2024.10.30
職場にいる「困った部下」への対処法 上司・部下間で生まれる“常識のズレ”を解消するには