Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Rails開発者向けGraphQL入門

 Rails開発者向けGraphQL入門

yasudatoshiyuki

February 19, 2020
Tweet

More Decks by yasudatoshiyuki

Other Decks in Programming

Transcript

  1. ©iCARE Co., Ltd All rights reserved 自己紹介
 2 名前:安田俊之 関わってきた技術

    Ruby on Rails, Vue.js, AngularJS PHP: Symfony, FuelPHP, CakePHP Java: Androidアプリ、Spring Perl: CGI DB: PostgreSQL, MySQL, Oracle, PL/SQL その他: Terraform, Ansible, Chef, Nginx, etc.
  2. ©iCARE Co., Ltd All rights reserved PostgreSQL Rails Javascript GraphQLってなに?


    5 GraphQL query { users { name email } } SQL SELECT name, email FROM users 弊社の場合のフロー(ブラウザからDBへ) GraphQL サーバー
  3. ©iCARE Co., Ltd All rights reserved GraphQLってなに?
 6 無理やり、RESTに問い合わせ言語の概念を付与すると https://some.where/users

    の /users や https://some.where/users/1 の /users/1 の部分が問い合わせ言語になると言えるでしょうか。 パッと見て分かる通り、RESTの仕様では、userのどういう属性を取得できるか は、問い合わせ内容からは不明ですし、どの属性が欲しくて、どの属性がいら ないかの選択もできないことがわかるかと思います。
  4. ©iCARE Co., Ltd All rights reserved どんなメリットを得られるのか?
 8 REST https://some.where/users

    GET GraphQL https://some.where/graphql POST query { users { name email } } ※他のデータへの問い合わせもエン ドポイントは同じ/graphql リクエストの形式
  5. ©iCARE Co., Ltd All rights reserved どんなメリットを得られるのか?
 9 問い合わせを受け取る実装 REST

    app/controllers/users_controller.rb class UsersController def index @users = User.some_scope end end GraphQL app/graphql/types/query_type.rb module Types class QueryType < Types::BaseObject field :users, [UserType], null: true def users @users = User.some_scope end end end ※GraphQL用のコントローラはあるが、全ての 問い合わせで共通のコントローラ
  6. ©iCARE Co., Ltd All rights reserved どんなメリットを得られるのか?
 10 レスポンス(もしくはレスポンス可能なもの)を定義する実装 REST

    app/views/users/index.json.jbuilder json.users @usrs do | c | json.name c.name json.email c.email ... end ↑ 該当のリクエスト専用の定義のため再利用不 可 GraphQL app/graphql/types/user_type.rb module Types class UserType < Types::BaseObject field :name, String field :email, String end end ↑ 該当のリクエスト専用の定義ではないので再 利用可能(ActiveRecordの定義同様)
  7. ©iCARE Co., Ltd All rights reserved どんなメリットを得られるのか?
 11 型定義の再利用 query

    { orders { price datetime user { name email } } } 上記のように異なる構造のクエリの場合でも、 jbuilderの定義と異なりCustomerTypeの定義 はそのまま再利用できる
  8. ©iCARE Co., Ltd All rights reserved どんなメリットを得られるのか?
 12 実際のレスポンス REST

    { "users":[ { "name":"山田太郎", "email":"taro@yamada", } ] } GraphQL { "data":{ "users":[ { "name":"山田太郎", "email":"taro@yamada", } ] } }
  9. ©iCARE Co., Ltd All rights reserved どんなメリットを得られるのか?
 13 1回のリクエストで得られるレスポンス REST

    userに紐づくorders(注文)を取得するときは、 userごとに別途リクエストをする必要がある GraphQL GraphQL側の型定義さえあれば、1回のクエリ で入れ子構造のデータを取得することができる query { usrs { name email orders { price datetime } } } ※N+1問題に気をつける必要がある
  10. ©iCARE Co., Ltd All rights reserved どんなメリットを得られるのか?
 14 まとめ 1.

    エンドポイントが一つ(/graphql)になるので、Webサーバーにエンドポイントを どう作るかについて悩む必要がなくなる 2. データ定義を資産として再利用できる(RESTの場合のjbuilderだと再利用で きない) 3. リクエスト側から入れ子構造でデータを問い合わせることができるため、1回 のリクエストで複雑な構造のデータを柔軟に取得することができる。(ので、 サーバー側に、たくさんエンドポイントを用意する必要がなくなる) 4. GraphiQL(ブラウザインターフェース)でスキーマ(どんなフィールドがある か)の確認および動作確認ができる