Bind resolvers

Resolvers are used to resolve the data for the query. They bind the execution of GraphQL operation into your logic.

See also

Tanka GraphQL provides few ways of binding resolvers to your schema.

  • Bind manually using SchemaBuilder
  • Bind using resolver maps by using SchemaBuilder or SchemaTools

Bind manually using SchemaBuilder


        [Fact]
        public async Task Part2_BindResolvers_Manual()
        {
            // Create builder and load sdl
            var builder = new SchemaBuilder()
                .Sdl(@"
                type Query {
                    name: String
                }
                ");

            // Get query type
            builder.GetQuery(out var query);

            // Connections are used to defined fields and resolvers.
            // Connections method can be called multiple times.
            builder.Connections(connections =>
            {
                // Get or add resolver builder for Query.name field
                var nameResolverBuilder = connections
                    .GetOrAddResolver(query, "name");

                // "Run" allows us to define an end of the resolver 
                // chain. You can add "middlewares" using "Use".
                nameResolverBuilder
                    .Run(context =>
                    {
                        // Create result using Test as the value
                        var result = Resolve.As("Test");

                        // Resolvers can be sync or async so
                        // ValueTask result is used to reduce 
                        // allocations
                        return new ValueTask<IResolverResult>(result);
                    });
            });

            // Build schema with the resolver
            var schema = builder.Build();

            // Get resolver for Query.name field
            var nameResolver = schema.GetResolver(schema.Query.Name, "name");

            // Execute the resolver. This is normally handled by the executor.
            var nameValue = await nameResolver(null);
            Assert.Equal("Test", nameValue.Value);
        }

Bind using SchemaTools or SchemaBuilder

This approach uses a map of the types and fields to bind resolvers to fields.

NOTE: Binding is done when the method is called.


        [Fact]
        public async Task Part2_BindResolvers_SchemaBuilder_Maps()
        {
            // Create builder and load sdl
            var builder = new SchemaBuilder()
                .Sdl(@"
                type Query {
                    name: String
                }
                ");

            // Get query type
            builder.GetQuery(out var query);

            // Bind resolvers from ObjectTypeMap
            builder.UseResolversAndSubscribers(
                new ObjectTypeMap
                {
                    {
                        query.Name, new FieldResolversMap
                        {
                            {
                                "name", context =>
                                {
                                    var result = Resolve.As("Test");
                                    return new ValueTask<IResolverResult>(result);
                                }
                            }
                        }
                    }
                });

            // Build schema
            var schema = builder.Build();

            // Get resolver for Query.name field
            var nameResolver = schema.GetResolver(schema.Query.Name, "name");

            // Execute the resolver. This is normally handled by the executor.
            var nameValue = await nameResolver(null);
            Assert.Equal("Test", nameValue.Value);
        }

This is what you would usually do to bind the resolvers and create schema.


        [Fact]
        public async Task Part2_BindResolvers_SchemaTools_Maps()
        {
            // Create builder and load sdl
            var builder = new SchemaBuilder()
                .Sdl(@"
                type Query {
                    name: String
                }
                ");

            // Get query type
            builder.GetQuery(out var query);

            // Build schema by binding resolvers from ObjectTypeMap
            var schema = SchemaTools.MakeExecutableSchema(
                builder,
                new ObjectTypeMap
                {
                    {
                        query.Name, new FieldResolversMap
                        {
                            {
                                "name", context =>
                                {
                                    var result = Resolve.As("Test");
                                    return new ValueTask<IResolverResult>(result);
                                }
                            }
                        }
                    }
                });


            // Get resolver for Query.name field
            var nameResolver = schema.GetResolver(schema.Query.Name, "name");

            // Execute the resolver. This is normally handled by the executor.
            var nameValue = await nameResolver(null);
            Assert.Equal("Test", nameValue.Value);
        }