🤖

GraphQLを用いたWebアプリ開発の俯瞰図

2022/10/11に公開

この記事のモチベーション

先人たちが書いた開発ブログや各ライブラリの"Get Started"などを読めば簡単にGraphQLを使ったアプリを作ることができますし、REST APIとの違いなども理解することができます(大変ありがたい...)。

例えばこのライブラリをインストールして、こんな風にサーバーを立てて、クエリを書いて、フロントからリクエスト送って〜みたいなことが書いてあり、それをそのまま写経すればアプリは作れます。
自分もApolloのDocumentや他の方のブログを読んでGraphQLアプリを個人で作ったりしてました(Node.jsやReactを使ったWebアプリケーション開発)。

しかし、開発し終わったあとに以下のようなことを思いました。

  • なんかやたらライブラリをインストールしているけどなんでそれをインストールしなきゃいけないのか分からない...
  • JS/TS以外の他言語で実装することになったら何もできなさそう...

そこで実装方法という具体的な部分ではなく、GraphQL開発の全体像を理解したいと思い、勉強がてら記事を書いてみました。
間違って理解している部分とかあるかもしれないので指摘していただけるとありがたいです🙏

そもそもGraphQLとは

graphql.orgでGraphQLは以下のように説明されています。

GraphQL is a query language for APIs and a runtime for fulfilling those queries with your existing data.

https://graphql.org/

つまりGraphQLはクエリ言語(及びそのクエリを実行するランタイム) だということです。

これはGraphQLがライブラリでもフレームワークでもないということを逆説的に意味しています。
GraphQLには仕様のみが定められており、その仕様を守った実装であれば何であれGraphQLと呼ぶことができます。
あくまでもGraphQLはクエリ言語であり、仕様さえ守っていれば実装方法は皆様にお任せします、というスタンスです。

もちろん多くの開発者はこの仕様を読んでゼロベースでGraphQLを実装するのではなく、この仕様を実装したライブラリを用いて開発することになります。
実際、様々な言語で様々な実装がなされています。

https://graphql.org/code/

加えて、GraphQLはWebアプリケーション開発以外の場面でも使うことができます。組み込み開発の場面で使われることもあるみたい?です。

以下では、JSによるWebアプリケーション開発を例にして進めて行きたいと思います。

GraphQLを使ったWebアプリケーション開発

GraphQLはAPIで用いられます。なのでREST APIと同様にWebアプリケーション開発では、

リクエストの発行(クライアント側)
→リクエストを受け付ける(サーバー側)
→リクエストの内容に応じたレスポンスを返す(サーバー側)
→レスポンスを受け取る(クライアント側)

という場面でGraphQLを用いることになります。

上記の処理を行うために、GraphQL SchemaGraphQLサーバーGraphQLクライアントを準備する必要があります。

GraphQL Schema

クライアントとサーバー間でデータのやり取りをするためには、どのようなデータが存在しているのか、データがどのように関連しているのか、クライアントはどのようにリクエストをするのか、サーバーはどのデータおよびどの操作を提供するのか、が分かってなくてはいけません。

GraphQLではデータのグラフ構造をサーバー側・クライアント側が理解する必要があるため、グラフ構造を記述するGraphQL Schemaを構築し、サーバー側・クライアント側がそれを参照しなくてはなりません。GraphQL Schemaはスキーマ定義言語(Schema Definition Language: SDL)で記述される必要があります。

Schemaの構築方法について、Schema-firstアプローチCode-firstアプローチがあります。Schema-firstアプローチはスキーマ定義言語でGraphQL Schemaを予め作っておく方法、Code-firstアプローチはサーバー側のコードからGraphQL Schemaを生成する方法です。
これらの違いに関しては様々なところで語られているので例えば以下の記事とか読んでください。

https://www.prisma.io/blog/the-problems-of-schema-first-graphql-development-x1mn4cb0tyl3

代表的なJSライブラリ

  • GraphQL.js
    • みんながいつもnpm install graphqlしてるやつ
    • JSでの参照実装
      • 仕様の実装で基本となるライブラリなので、他のライブラリとともに使う
    • やってくれること
      • Schemaの構築
      • クエリの検証・実行
  • GraphQL Tools
    • Schema-firstアプローチでGraphQL Schemaを作成
  • TypeGraphQL
    • Code-firstアプローチでGraphQL Schemaを生成してくれる
  • Nexus
    • Code-firstアプローチでGraphQL Schemaを生成してくれる

GraphQLサーバー

GraphQLサーバーはサーバーサイド側で動作するプログラムです。GraphQL APIサーバーとも呼ばれるらしく、言ってしまえばREST APIサーバーのGraphQL版みたいな感じです。

HTTPサーバーとしての役割[1]を果たし、クライアントからのリクエストを受け付け、レスポンスを返す、という機能を果たします。

通常のHTTPサーバーと異なるの点として、HTTPサーバーとしての機能に加え、

  • 構築されたSchemaにリクエストが従っているかを検証する
  • 問題なければリゾルバに記述された方法でデータを引っ張ってくる
  • データをグラフ形式でレスポンスとして返す

ということをやってくれます。

また前述のCode-firstアプローチでは、サーバー側でGraphQL Schemaを生成し、それをクライアント側に参照させます。その場合、GraphQLサーバーはHTTPサーバーとしての機能だけじゃなく、GraphQL Schema構築の機能も果たします。

代表的なJSライブラリ

  • Apollo Server
    • Apolloが作っていて、多分一番よく見るやつ
    • "batteries-included"な[2]ライブラリで、とりあえずこれ入れておけば大抵のWebアプリケーションフレームワークとともに使える
    • 内部でapollo-server-expressapollo-server-fastifyapollo-server-microなどをインストールしている感じみたい
      • apollo-server-<integration>は使用しているwebアプリケーションフレームワークに対応したApollo Serverという感じ
      • どれをインストールするべきかは公式Docを参照
  • express-graphql
    • Express上で動作するGraphQL APIサーバー
  • GraphQL Yoga
    • シンプルなGraphQL APIサーバー

GraphQLクライアント

GraphQLクライアントはクライアント側で動作するプログラムです。主な役割はクライアント側からクエリをGraphQLサーバーにリクエストし、そのレスポンスを受け取ることです。

代表的なJSライブラリ

実のところ、特にライブラリを使うことなくクエリを実行することができます。
例えばコマンドライン(curlとか)やJSのfetchメソッドを使えば、リクエストを送りレスポンスを受け取ることができます。

しかしコマンドラインやfetchだと機能が乏しい(例えばcacheが効かない、返り値に型がつかない)ので、便利な機能を提供してくれるGraphQLクライアント専用のライブラリを使うことが多いです。

  • Apollo Client
    • Apolloが作っていて、多分一番よく見るやつ
    • React, Vue, SvelteなどのJS系フロントライブラリや、Web Components、iOS開発などでも用いることができる
  • Relay
    • Meta社が開発してるやつ
    • Reactに特化している
  • graphql-request
    • シンプルで軽量なGraphQLクライアント
    • cacheまではケアしてくれない
脚注
  1. より正確に言うと、GraphQLの仕様では通信プロトコルをHTTPに限定していません ↩︎

  2. 標準でいろんなことができる、的な意味のスラング(https://en.wikipedia.org/wiki/Batteries_Included) ↩︎

GitHubで編集を提案

Discussion