Given the following apollo server graphql schema I wanted to break these down into separate modules so I don't want the author query under the root Query schema.. and want it separated. So i added another layer called authorQueries before adding it to the Root Query
type Author { id: Int, firstName: String, lastName: String } type authorQueries { author(firstName: String, lastName: String): Author } type Query { authorQueries: authorQueries } schema { query: Query }
I tried the following.. you can see that authorQueries was added as another layer before the author function is specified.
Query: { authorQueries :{ author (root, args) { return {} } } }
When querying in Graphiql, I also added that extra layer..
{ authorQueries { author(firstName: "Stephen") { id } } }
I get the following error.
"message": "Resolve function for \"Query.authorQueries\" returned undefined",
When setting up a field whose value is a custom type, we have to define a function that tells GraphQL how to get that custom type. In our case, we want to tell GraphQL how to get the posts if we have the author. We do that by defining a new root property inside resolvers.
A resolver is a function that's responsible for populating the data for a single field in your schema. It can populate that data in any way you define, such as by fetching data from a back-end database or a third-party API.
Hence, we can create two separate schemas, the Admin and Public schemas, and expose them under endpoints /graphql/admin and /graphql respectively.
To create a "nested" resolver, simply define the resolver on the return type of the parent field. In this case, your authorQueries
field returns the type authorQueries
, so you can put your resolver there:
{ Query: { authorQueries: () => ({}) }, authorQueries: { author(root, args) { return "Hello, world!"; } } }
So in the technical sense, there is no such thing as a nested resolver - every object type has a flat list of fields, and those fields have return types. The nesting of the GraphQL query is what makes the result nested.
Apollo Official related docs (Great example inside):
https://www.apollographql.com/docs/apollo-server/data/resolvers/#resolver-chains
/* code from: https://www.apollographql.com/docs/apollo-server/data/resolvers/#resolver-chains */ const { ApolloServer, gql } = require('apollo-server'); const libraries = [ { branch: 'downtown' }, { branch: 'riverside' }, ]; // The branch field of a book indicates which library has it in stock const books = [ { title: 'The Awakening', author: 'Kate Chopin', branch: 'riverside' }, { title: 'City of Glass', author: 'Paul Auster', branch: 'downtown' }, ]; // Schema definition const typeDefs = gql` # A library has a branch and books type Library { branch: String! books: [Book!] } # A book has a title and author type Book { title: String! author: Author! } # An author has a name type Author { name: String! } # Queries can fetch a list of libraries type Query { libraries: [Library] } `; // Resolver map const resolvers = { Query: { libraries() { // Return our hardcoded array of libraries return libraries; } }, Library: { books(parent) { // Filter the hardcoded array of books to only include // books that are located at the correct branch return books.filter(book => book.branch === parent.branch); } }, Book: { // The parent resolver (Library.books) returns an object with the // author's name in the "author" field. Return a JSON object containing // the name, because this field expects an object. author(parent) { return { name: parent.author }; } } // Because Book.author returns an object with a "name" field, // Apollo Server's default resolver for Author.name will work. // We don't need to define one. }; // Pass schema definition and resolvers to the // ApolloServer constructor const server = new ApolloServer({ typeDefs, resolvers }); // Launch the server server.listen().then(({ url }) => { console.log(`🚀 Server ready at ${url}`); });
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With