diff options
author | Bob Van Landuyt <bob@vanlanduyt.co> | 2018-05-23 10:55:14 +0300 |
---|---|---|
committer | Bob Van Landuyt <bob@vanlanduyt.co> | 2018-06-06 11:58:54 +0300 |
commit | 9b65d4bb417fb4939289eab94487c894f0a62db6 (patch) | |
tree | 1f97b9a1bd0d722a3c3ff4e89ec13bdb7a3aec00 /doc/development | |
parent | c443133e779c4c508b9c6429dd4ba623d64f03f1 (diff) |
Initial setup GraphQL using graphql-ruby 1.8
- All definitions have been replaced by classes:
http://graphql-ruby.org/schema/class_based_api.html
- Authorization & Presentation have been refactored to work in the
class based system
- Loaders have been replaced by resolvers
- Times are now coersed as ISO 8601
Diffstat (limited to 'doc/development')
-rw-r--r-- | doc/development/api_graphql_styleguide.md | 49 |
1 files changed, 32 insertions, 17 deletions
diff --git a/doc/development/api_graphql_styleguide.md b/doc/development/api_graphql_styleguide.md index 4d73efa3f71..f74e4f0bd7e 100644 --- a/doc/development/api_graphql_styleguide.md +++ b/doc/development/api_graphql_styleguide.md @@ -2,8 +2,8 @@ ## Authentication -Authentication happens through the `GrapqlController`, right now this -uses the same authentication as the rails application. So the session +Authentication happens through the `GraphqlController`, right now this +uses the same authentication as the Rails application. So the session can be shared. It is also possible to add a `private_token` to the querystring, or @@ -11,27 +11,25 @@ add a `HTTP_PRIVATE_TOKEN` header. ### Authorization -Fields can be authorized using the same abilities used in the rails +Fields can be authorized using the same abilities used in the Rails app. This can be done using the `authorize` helper: ```ruby -Types::QueryType = GraphQL::ObjectType.define do - name 'Query' +module Types + class QueryType < BaseObject + graphql_name 'Query' - field :project, Types::ProjectType do - argument :full_path, !types.ID do - description 'The full path of the project, e.g., "gitlab-org/gitlab-ce"' + field :project, Types::ProjectType, null: true, resolver: Resolvers::ProjectResolver do + authorize :read_project end - - authorize :read_project - - resolve Loaders::FullPathLoader[:project] end -end ``` The object found by the resolve call is used for authorization. +This works for authorizing a single record, for authorizing +collections, we should only load what the currently authenticated user +is allowed to view. Preferably we use our existing finders for that. ## Types @@ -43,7 +41,7 @@ the definition as minimal as possible. Instead, consider moving any logic into a presenter: ```ruby -Types::MergeRequestType = GraphQL::ObjectType.define do +class Types::MergeRequestType < BaseObject present_using MergeRequestPresenter name 'MergeRequest' @@ -56,11 +54,28 @@ a new presenter specifically for GraphQL. The presenter is initialized using the object resolved by a field, and the context. +## Resolvers + +To find objects to display in a field, we can add resolvers to +`app/graphql/resolvers`. + +Arguments can be defined within the resolver, those arguments will be +made available to the fields using the resolver. + +We already have a `FullPathLoader` that can be included in other +resolvers to quickly find Projects and Namespaces which will have a +lot of dependant objects. + +To limit the amount of queries performed, we can use `BatchLoader`. + ## Testing _full stack_ tests for a graphql query or mutation live in -`spec/requests/graphql`. +`spec/requests/api/graphql`. When adding a query, the `a working graphql query` shared example can -be used to test the query, it expects a valid `query` to be available -in the spec. +be used to test if the query renders valid results. + +Using the `GraphqlHelpers#all_graphql_fields_for`-helper, a query +including all available fields can be constructed. This makes it easy +to add a test rendering all possible fields for a query. |