graphql-dotnet / conventions

GraphQL Conventions Library for .NET
MIT License
233 stars 63 forks source link

Task unwrapping in ObjectReflector.GetType #187

Closed K-Pavlov closed 5 years ago

K-Pavlov commented 5 years ago

Let's say we have this schema:

private class BugReproQueryTaskSecond
        {
            public Task<Broken> ZName() => Task.FromResult(new Broken()); // Changes the name of the method to 'Broken' and it will work...

            public Task<Connection<Holder>> Holders() =>
                Task.FromResult(new Connection<Holder>
                {
                    Edges = new List<Edge<Holder>>
                            {
                            new Edge<Holder>
                            {
                                Cursor = Cursor.New<Holder>(0),
                                Node = new Holder
                                {
                                }
                            }
                            },
                    PageInfo = new PageInfo
                    {
                        EndCursor = Cursor.New<Holder>(0),
                        HasNextPage = false,
                        HasPreviousPage = false,
                        StartCursor = Cursor.New<Holder>(0)
                    },
                    TotalCount = 1
                });
        }

        private class Holder
        {
            public async Task<IEnumerable<ICommonInterface>> InterfaceConnection() => new[] { new Broken() };
        }

        private interface ICommonInterface
        {
            int Test { get; }
        }

        private class Broken : ICommonInterface
        {
            public int Test => 1;
        }

We have a method in the query that returns a Task and an interface connection to Broken. Because tasks were not unwrapped, two GraphQL types were added for that Broken and depending on the naming of the method (alphabetic sorting in the ObjectReflector.GetFields) the interface was getting either the Task or Broken type; The integer type in Broken is wrapped in a NonNull and depending on which Broken Type is selected for the interface possible types, the NonNull either gets a ResolvedType or doesn't. If it doesn't get a ResolvedType the GraphQL lib throws a "Unexpected type: " exception;

K-Pavlov commented 5 years ago

@tlil I have a fix for this and will make a PR soon

tlil commented 5 years ago

Great, thanks!