脈絡はありません inoway

ハードルは低いほど飛びやすいをモットーに駆け出したエンジニアです

はじめてのGraphQLを読んだ&実務でちょっと書いた

実務でGraphQL関連のコードを触ることになったので、友人に「はじめてのGraphQL」を借りて先週読み終わった。

www.oreilly.co.jp

(普通に買えばよかったけど、作業会をした時にたまたま持っていて今読んでないからということでお借りした)

原著の英語版が2018年9月発行なので情報は少し古いかもしれない。ただ、GraphQLの元となっているグラフ理論(ここは特に面白かった)、Schema、Query、Mutation、Subscriptionなど基礎概念の説明、ReactにおけるApollo Clientの使い方といった内容が網羅的にまとまっているので頭の中にインデックスを作るための本として適しているのではないかと思う。

「GraphQLとは何か」などここでまとめ直すといいかもしれないが、そのような内容の記事は公式ドキュメント含め質の高いものがネット上にたくさん存在しているので今回はやらないことにする。これ以上概念的な理解に時間を割くよりもコードを書く中でキャッチアップしていく方が効率的だと思う。

正確性や網羅性は気にせず、印象に残っていることを以下にまとめる。

RESTとGraphQLの比較

以下の記事に非常に分かりやすくまとまっていた。(はじめてのGraphQL読後)

kinsta.com

大きく3点、特徴を取り上げたい。

  • RESTのエンドポイントは複数なのに対して、GraphQLのエンドポイントは一つであること

RESTの問題点の一つとして、リクエスト時に不要なデータまで取得してしまうことが挙げられる。逆に欲しい情報がそのエンドポイントだけでは取れず、複数回のリクエストを送らないといけなくなることもある。

その点、GraphQLではクライアント側で欲しいデータだけを問い合わせるようなクエリを書けるため、このような「オーバーフェッチ、アンダーフェッチ」の問題を避けることができる。

ただ、エンドポイントごとに分けて処理を書くことができないが故に、コード量が増えるにつれてGraphQLのクエリは徐々に複雑になっていくデメリットもある。

  • 型付けができること

昨今のWebフロントエンドにおいては可読性や安全性などの観点で型付けができるTypeScriptが採用されることが多くなっているが、GraphQLも同様に型付けを採用している。TypeScriptとの相性が非常に良いため、セットで使用されているプロジェクトが多く見受けられる。

今はMutation周りを少し触った程度なので、型付けの恩恵を実感できていないが、型付けできるからこそそのままドキュメントとしても活用できるような可読性の高いSchemaが定義できるのだと思う。また、データを問い合わせた際に、どのような型のデータが返ってくるか分からない場合、型判定や型変換の処理を書かなければならないため冗長になる。(そういった処理を書かないとバグの原因になる)

ふだんRubyばかり書いているので(といっても1年弱)、この型付けのメリットを正しく説明できているかちょっと怪しい。間違っているポイントがあればそれはそれで勉強になるのでマサカリをお待ちすることにする。

  • フロントエンド側で柔軟にクエリを書ける

開発マネージャーからおすすめされたtexta.fmの4話の後半5分でこの特徴について語られている。

バックエンドとフロントエンドの開発担当を分けているプロジェクトの場合、RESTであれば両者がどのようなデータが必要かエンドポイントごとにすり合わせをしながら実装していく必要がある一方で、GraphQLならフロントエンド側で柔軟にクエリを書き換えることができるため、バックエンド側に逐一用意してもらう必要がなくなるとのことだ。

開発(リリース)スピードがビジネス上の重要なファクタとなるWeb業界においては、このGraphQLの柔軟性がとても重宝されているようだ。ただ、小規模アプリにはRESTのシンプルなインターフェースで十分ということに注意した方がよさそう。規模が大きくなり、バックエンドとフロントエンドの開発プロセスが分離され始めたフェーズにおいてGraphQLを積極採用すると良いのだと思う。

MutationのRSpecを書いてみた感想

ここは経験が浅いので合ってるか分からないが、書き方はrequest_specに似ているものの、テストダブル(スタブやモック)が使いづらいなと感じた。これは今回実装したテストが、更新対象のModel内でbefore_createコールバックを使用していたことに起因しているかもしれないが、オブジェクトとして渡せる引数がcurrent_userのみ(contextを使用)なことも原因なように思う。

また、エラーハンドリングも慣れなくて難しかった。普段書いてるerrors.addのようにRails内だけで完結しない。例えばインスタンスsave時の条件分岐で以下のようなGraphQL::ExecutionErrorというGraphQL特有のエラーを返す必要があった。

raise GraphQL::ExecutionError.new("Something went wrong", extensions: { "code" => "BROKEN" })

graphql-ruby/execution_errors.md at master · rmosolgo/graphql-ruby · GitHubより

この段落に書いたことは印象論の域を出ないので、これからGraphQLと仲良くなる中でここで感じた印象が正しかったのかどうか検証していきたい。

これからやりたいこと

とにかく実務でGraphQL周りのコードをたくさん書きたい。そのために個人開発やチュートリアルなどでgraphql-rubyの書き方に慣れていこうと思う。フロントエンドの先輩いわくgraphql-rubyは公式ドキュメントが親切らしいので、これもちゃんと読んでいきたい。

https://graphql-ruby.org

もちろんGraphQL本体の公式ドキュメントも読み進める。英語リーディングの題材にもできてよさそう。

https://graphql.org/

あとは以下を500円お支払いして進めている。処理内容の解説はほとんどなく、サンプルコード通りに書いてくださいという感じなので、こんな感じで書くんだなあという感覚が掴めればそれでOKかなと思う。

【GraphQL 開発超入門】React × GraphQL × Rails でアプリケーションを作る

一応はGraphQLについてまとめられたので、ここらで終わりにする。新しい技術を学ぶのはなんだかワクワクしますね。

参照

‎texta.fm: 4. Not Just ORM on Apple Podcasts

GraphQLとRESTの比較─知っておきたい両者の違い