rebing / graphql-laravel

Laravel wrapper for Facebook's GraphQL
MIT License
2.13k stars 266 forks source link

How to return a type in resolve from another type #430

Closed jumperdenfer closed 5 years ago

jumperdenfer commented 5 years ago

Hello everyone, I need a little help, i want to resolve a fields by getting resource from another Type ( like an tree of data ) i have 2 Types and 2 Queries my first type :


namespace APP\GraphQL\Type;

use App\Model\AuditModel;
use App\Model\CategorieModel;
use GraphQL\Type\Definition\Type;
use Rebing\GraphQL\Support\Type as GraphQLType;
use GraphQL\GraphQL;

class AuditType extends GraphQlType{
    protected $attributes = [
        'name' => 'audit',
        'description' => 'Affichage d\'un audit',
        'model' => AuditModel::class
    ];
    public function fields(){
       return [
           'id' => [
               'type' => Type::nonNull(Type::string()),
               'description' => 'Id de l\'audit'
           ],
           'id_entreprise' => [
               'type' => Type::int(),
               'description' => 'Id de l\'entreprise liée à cette audit',
           ],
           'libelle' =>[
               'type' => Type::string(),
               'description' => 'libelle de l\'audit'
           ],
           'presentation' =>[
               'type' => Type::string(),
               'description' => 'Présentation de l\'audit'
           ],
           'date_creation' =>[
               'type' => Type::string(),
               'description' => 'Date de création de l\'audit'
           ],
           'total_points' =>[
               'type' => Type::float(),
               'description' => 'Score maximum de l\'audit'
           ],
           'categorie' =>[
               'type' => Type::listOf(GraphQL::type('CategorieType')),
               'description' => 'Liste des catégorie de l\'audit',
               'resolve' => function($root){
                   return (new CategorieQuery)->args($root->id);
               }
           ]
       ];
   }
}

My second type :

<?php
namespace App\GraphQL\Type;
use App\Model\AuditModel;
use GraphQL\Type\Definition\Type;
use Rebing\GraphQL\Support\Type as GraphQLType;

class CategorieType extends GraphQlType{
    protected $attributes = [
        'name' => 'categorie',
        'description' => 'Affichage d\'une categorie',
        'model' => CategorieModel::class
    ];
    public function fields(){
        return[
            'id' => [
                'type' =>Type::string(),
                'description'=>'id de la catégorie'
            ]
        ];
    }
}

My querie For AuditType :

<?php
namespace App\GraphQL\Query;

use App\Model\AuditModel;
use Rebing\GraphQL\Support\Facades\GraphQL;
use GraphQL\Type\Definition\ResolveInfo;
use GraphQL\Type\Definition\Type;
use Rebing\GraphQL\Support\Query;

class AuditQuery extends Query
{
    protected $attributes = [
        'name' => 'Audit Query'
    ];

    public function type(): Type
    {
        return Type::listOf(GraphQL::type('AuditType'));
    }

    public function args(): array
    {
        return [
            'id' => ['name' => 'id', 'type' => Type::int()]
        ];
    }

    public function resolve($root, $args, $context, ResolveInfo $resolveInfo)
    {
        if (isset($args['id'])) {
            return AuditModel::where('id' , $args['id'])->get();
        }
        return AuditModel::all();
    }
}

And for CategorieType

namespace App\GraphQL\Query;

use App\Model\AuditModel;
use Rebing\GraphQL\Support\Facades\GraphQL;
use GraphQL\Type\Definition\ResolveInfo;
use GraphQL\Type\Definition\Type;
use Rebing\GraphQL\Support\Query;

class CategorieQuery extends Query
{
    protected $attributes = [
        'name' => 'Categorie Query'
    ];

    public function type(): Type
    {
        return Type::listOf(GraphQL::type('CategorieType'));
    }

    public function args(): array
    {
        return [
            'id' => ['name' => 'id', 'type' => Type::int()]
        ];
    }

    public function resolve($root, $args, $context, ResolveInfo $resolveInfo)
    {
        if (isset($args['id'])) {
            return CategorieModel::where('id' , $args['id'])->get();
        }
        return CategorieModel::all();
    }
}

my Config file :

<?php

use example\Type\ExampleType;
use example\Query\ExampleQuery;
use example\Mutation\ExampleMutation;
use example\Type\ExampleRelationType;
use App\GraphQL\Type\AuditType;
use App\GraphQL\Type\CategorieType;
use App\GraphQL\Query\AuditQuery;
use App\GraphQL\Query\CategorieQuery;
return [

    // The prefix for routes
    'prefix' => 'graphql',

    // The routes to make GraphQL request. Either a string that will apply
    // to both query and mutation or an array containing the key 'query' and/or
    // 'mutation' with the according Route
    //
    // Example:
    //
    // Same route for both query and mutation
    //
    // 'routes' => 'path/to/query/{graphql_schema?}',
    //
    // or define each route
    //
    // 'routes' => [
    //     'query' => 'query/{graphql_schema?}',
    //     'mutation' => 'mutation/{graphql_schema?}',
    // ]
    //
    'routes' => '{graphql_schema?}',

    // The controller to use in GraphQL request. Either a string that will apply
    // to both query and mutation or an array containing the key 'query' and/or
    // 'mutation' with the according Controller and method
    //
    // Example:
    //
    // 'controllers' => [
    //     'query' => '\Rebing\GraphQL\GraphQLController@query',
    //     'mutation' => '\Rebing\GraphQL\GraphQLController@mutation'
    // ]
    //
    'controllers' => \Rebing\GraphQL\GraphQLController::class.'@query',

    // Any middleware for the graphql route group
    'middleware' => ['middleware' => 'auth'],

    // Additional route group attributes
    //
    // Example:
    //
    // 'route_group_attributes' => ['guard' => 'api']
    //
    'route_group_attributes' => [],

    // The name of the default schema used when no argument is provided
    // to GraphQL::schema() or when the route is used without the graphql_schema
    // parameter.
    'default_schema' => 'default',

    // The schemas for query and/or mutation. It expects an array of schemas to provide
    // both the 'query' fields and the 'mutation' fields.
    //
    // You can also provide a middleware that will only apply to the given schema
    //
    // Example:
    //
    //  'schema' => 'default',
    //
    //  'schemas' => [
    //      'default' => [
    //          'query' => [
    //              'users' => 'App\GraphQL\Query\UsersQuery'
    //          ],
    //          'mutation' => [
    //
    //          ]
    //      ],
    //      'user' => [
    //          'query' => [
    //              'profile' => 'App\GraphQL\Query\ProfileQuery'
    //          ],
    //          'mutation' => [
    //
    //          ],
    //          'middleware' => ['auth'],
    //      ],
    //      'user/me' => [
    //          'query' => [
    //              'profile' => 'App\GraphQL\Query\MyProfileQuery'
    //          ],
    //          'mutation' => [
    //
    //          ],
    //          'middleware' => ['auth'],
    //      ],
    //  ]
    //
    'schemas' => [
        'default' => [
            'query' => [
                // 'example_query' => 'AuditQuery::class',
                'Audit' => AuditQuery::class
            ],
            'mutation' => [
                // 'example_mutation'  => ExampleMutation::class,
            ],
            'middleware' => [],
            'method'     => ['get', 'post'],
        ],
    ],

    // The types available in the application. You can then access it from the
    // facade like this: GraphQL::type('user')
    //
    // Example:
    //
    // 'types' => [
    //     'user' => 'App\GraphQL\Type\UserType'
    // ]
    //
    'types' => [
         'AuditType' => AuditType::class,
         'CategorieType' => CategorieType::class
        // 'relation_example'  => ExampleRelationType::class,
    ],

    // This callable will be passed the Error object for each errors GraphQL catch.
    // The method should return an array representing the error.
    // Typically:
    // [
    //     'message' => '',
    //     'locations' => []
    // ]
    'error_formatter' => ['\Rebing\GraphQL\GraphQL', 'formatError'],

    /*
     * Custom Error Handling
     *
     * Expected handler signature is: function (array $errors, callable $formatter): array
     *
     * The default handler will pass exceptions to laravel Error Handling mechanism
     */
    'errors_handler' => ['\Rebing\GraphQL\GraphQL', 'handleErrors'],

    // You can set the key, which will be used to retrieve the dynamic variables
    'params_key'    => 'variables',

    /*
     * Options to limit the query complexity and depth. See the doc
     * @ https://github.com/webonyx/graphql-php#security
     * for details. Disabled by default.
     */
    'security' => [
        'query_max_complexity'  => null,
        'query_max_depth'       => null,
        'disable_introspection' => false,
    ],

    /*
     * You can define your own pagination type.
     * Reference \Rebing\GraphQL\Support\PaginationType::class
     */
    'pagination_type' => \Rebing\GraphQL\Support\PaginationType::class,

    /*
     * Config for GraphiQL (see (https://github.com/graphql/graphiql).
     */
    'graphiql' => [
        'prefix'     => '/graphiql/{graphql_schema?}',
        'controller' => \Rebing\GraphQL\GraphQLController::class.'@graphiql',
        'middleware' => [],
        'view'       => 'graphql::graphiql',
        'display'    => env('ENABLE_GRAPHIQL', true),
    ],

    /*
     * Overrides the default field resolver
     * See http://webonyx.github.io/graphql-php/data-fetching/#default-field-resolver
     *
     * Example:
     *
     * ```php
     * 'defaultFieldResolver' => function ($root, $args, $context, $info) {
     * },
     * ```
     * or
     * ```php
     * 'defaultFieldResolver' => [SomeKlass::class, 'someMethod'],
     * ```
     */
    'defaultFieldResolver' => null,

    /*
     * Any headers that will be added to the response returned by the default controller
     */
    'headers' => [],

    /*
     * Any JSON encoding options when returning a response from the default controller
     * See http://php.net/manual/function.json-encode.php for the full list of options
     */
    'json_encoding_options' => 0,
];

actually i get the error Call to undefined method GraphQL\GraphQL::type()

mfn commented 5 years ago

Call to undefined method GraphQL\GraphQL::type()

In your very first class class AuditType you have:

use GraphQL\GraphQL;

That's supposed to reference the Facade (you got it right in class AuditQuery):

use use Rebing\GraphQL\Support\Facades\GraphQL;

Does that solve it?

jumperdenfer commented 5 years ago

@mfn Yeah ! thx, that solved one of my problems :p