Model(ActiveRecord)からGraphQL::ObjectTypesを自動生成する仕組みを考えるメモ

最近個人的にWebアプリ作ってます。 フロントはReactJS+Redux サーバサイドはRails それぞれ独立していて、GraphQLを用いて通信しています。

GraphQLのRuby実装として一番スターの多いgraphql-rubyを使っています。

GraphQL周りはまだ発展途上なのでいろいろと不便。 Typesを手動で定義するのが面倒なのでこれについて考えてみる。

Modelに対応するObjectの構成要素について

ActiveRecord内の要素で、今回着目するつもりなのは以下の通り - ActiveRecord::Attributes - ActiveRecord::Relation - ActiveRecord::Enum

ActiveRecordは GraphQL::ObjectTypeと対応させるとして, ActiveRecord::Relationの場合は has_oneの場合:GraphQL::ObjectType has_manyの場合:GraphQL::ListType(GraphQL::ObjectType) でよさそう。 ActiveRecord::EnumはそのままGraphQL::EnumTypeで問題ないはず。

ActiveRecord::AttributesはGraphQL::ScalarTypeになるのだけれど、 GraphQLの標準として定められているScalarTypeは

  • Int
  • Float
  • String
  • Boolean
  • ID

5つだけ。

- ActiveModel::Type::BigInteger
- ActiveModel::Type::Binary
- ActiveModel::Type::Boolean
- ActiveModel::Type::Decimal
- ActiveModel::Type::DecimalWithoutScale
- ActiveModel::Type::Float
- ActiveModel::Type::Integer
- ActiveModel::Type::String
- ActiveModel::Type::Text
- ActiveModel::Type::UnsignedInteger
- ActiveModel::Type::Value

Rails側はこんな感じ

対応できないGraphQL::ScalarTypeを新たに定義するのでもいいけど ユーザ独自で定義したActiveModel::Typeにも対応させることを考えると、 ActiveModel::Typeレベルから対応関係を結んだほうがよさそう。