Graphql-laravel: Error: Introspection must provide input type for arguments.

Created on 26 Sep 2018  路  6Comments  路  Source: rebing/graphql-laravel

When introspecting (via GraphQL Voyager, GraphiQL and others). I get the error Error: Introspection must provide input type for arguments..
I have types and queries defined, as well as a few input types for mutations.
My types are otherwise very much as per the docs, I can't see what I've missed?

Example

<?php

namespace App\GraphQL\Type;

use App\Models\Auth\User;
use GraphQL\Type\Definition\Type;
use Rebing\GraphQL\Support\Type as GraphQLType;

class UserType extends GraphQLType
{
    protected $attributes = [
        'name' => 'User',
        'description' => 'A user',
        'model' => User::class,
    ];

    /*
    * Uncomment following line to make the type input object.
    * http://graphql.org/learn/schema/#input-types
    */
    // protected $inputObject = true;

    public function fields()
    {
        return [
            'id' => [
                'type' => Type::nonNull(Type::id()),
                'description' => 'The id of the user'
            ],
            'uuid' => [
                'type' => Type::nonNull(Type::string()),
                'description' => 'The id of the user'
            ],
            'email' => [
                'type' => Type::nonNull(Type::string()),
                'description' => 'The email of user'
            ],
            'first_name' => [
                'type' => Type::string(),
                'description' => 'Users first name'
            ],
            'last_name' => [
                'type' => Type::string(),
                'description' => 'Users last name'
            ],
            'full_name' => [
                'selectable' => false,
                'type' => Type::string(),
                'description' => 'Users full name'
            ]
        ];
    }

    // If you want to resolve the field yourself, you can declare a method
    // with the following format resolve[FIELD_NAME]Field()

    protected function resolveFullNameField($root, $args)
    {
        return "{$root->first_name} {$root->last_name}";
    }
}

Most helpful comment

I think this is the problem: https://gist.github.com/jglover/f31142eb3fabe0cd38c80d706fa434f9#file-queries_pagesquery-php-L56

You are using a ObjectType there which are not InputObjectType, basically if you want to filter the query you can't input a whole User, you need to probably change that to Type::id().

All 6 comments

Okay this seems to be directly related to using the GraphQL::type method. As soon as I use it, I run into the issue. Example of the offending line:

 public function fields()
 {
      return [
           'creator' => ['name' => 'creator', 'type' => GraphQL::type('User')]
      ]
 }

Could you please post all the classes involved and the specific error message?

Sure, let me create a gist

Type and Query files here, much appreciate your help:
https://gist.github.com/jglover/f31142eb3fabe0cd38c80d706fa434f9

Error message is fired on GraphiQL loading up and running introspection for the docs & autosuggest, or running the default introspection query from the GraphQL voyager page. The error is specifically:

Error: Introspection must provide input type for arguments.
    at n (file:///Applications/GraphiQL.app/Contents/Resources/app.asar/dist/bundle.js:28:12899)
    at i (file:///Applications/GraphiQL.app/Contents/Resources/app.asar/dist/bundle.js:32:21915)
    at x (file:///Applications/GraphiQL.app/Contents/Resources/app.asar/dist/bundle.js:32:24361)
    at file:///Applications/GraphiQL.app/Contents/Resources/app.asar/dist/bundle.js:28:15421
    at Array.reduce (native)
    at n (file:///Applications/GraphiQL.app/Contents/Resources/app.asar/dist/bundle.js:28:15385)
    at N (file:///Applications/GraphiQL.app/Contents/Resources/app.asar/dist/bundle.js:32:24308)
    at file:///Applications/GraphiQL.app/Contents/Resources/app.asar/dist/bundle.js:32:24262
    at file:///Applications/GraphiQL.app/Contents/Resources/app.asar/dist/bundle.js:28:15421
    at Array.reduce (native)

I think this is the problem: https://gist.github.com/jglover/f31142eb3fabe0cd38c80d706fa434f9#file-queries_pagesquery-php-L56

You are using a ObjectType there which are not InputObjectType, basically if you want to filter the query you can't input a whole User, you need to probably change that to Type::id().

Thanks @hvdklauw , that makes a lot of sense in retrospect. Though I believe I got that from the docs so that might need fixing. I'll open a PR to fix them if that's the case.
For anyone else who comes across this, the solution was indeed to use an InputObjectType for the args definition in the query, put simply; you are filtering on a objectType arg (id, int, string etc), not an entire object. The resulting class looked something like this:

class PagesQuery extends Query
{
   ...
   public function args()
    {
        return [
            'id' => [
                'name' => 'id',
                'type' => Type::int()
            ],
            ...
            'created_by' => [
                'name' => 'created_by',
                'type' => Type::id()
            ]
        ];
    }

    public function resolve($root, $args, SelectFields $fields, ResolveInfo $info)
    {
        $where = function ($query) use ($args) {
            return collect($args)->map(function ($arg, $key) use ($query) {
                $query->where($key, $arg);
            });
        };

        $page = Page::with(array_keys($fields->getRelations()))
            ->where($where)
            ->select($fields->getSelect())
            ->paginate();

        return $page;
    }
Was this page helpful?
0 / 5 - 0 ratings

Related issues

AdrianCarreno picture AdrianCarreno  路  5Comments

canhkieu picture canhkieu  路  3Comments

drmax24 picture drmax24  路  6Comments

timothyvictor picture timothyvictor  路  3Comments

dongkaipo picture dongkaipo  路  4Comments