JoshJoe JoshJoe - 3 months ago 14
reST (reStructuredText) Question

How can I use one query to resolve many Rest round trips in graphQL?

I'm trying to resolve a REST query using GraphQL and Apollo.

My rest data looks like this

Pass a fund id to a splits resolver which returns a -> [Splits array] -> each split has a donation_id -> I want to use that ID to get the {donation} object from a separate rest endpoint

Here is my schema

export const schema = [`

schema {
query: RootQuery
}

type RootQuery {
Splits(id: Int!): [Splits]
}

type Splits {
amount_in_cents:Int
donation_id:Int
fund_id:Int
id:Int
memo:String
donation(donation_id: Int): Donation
}

type Donation {
amount_in_cents: Int
bank_name: String
}
`];


And here is my resolver file

import rp from 'request-promise';

const DTBaseURL = 'https://restendpointdomainhere.com/';
const getFromDT = (getQuery) => {
const data = rp( DTBaseURL + getQuery, {
'auth': {
"user": Meteor.settings.endpoint.user,
"pass": Meteor.settings.endpoint.pass,
}
} )
.then( ( res ) => JSON.parse( res ) )
.then((res) =>{
return res;
});
return data;
};



export default resolveFunctions = {
RootQuery: {
Splits( root, args, context ){
let newValue = [];
const getQuery = 'funds/' + args.id + '/splits.json';

const data = getFromDT(getQuery)
.then( ( res ) => {
res.forEach( function ( donationSplit ) {
newValue.push( donationSplit.split );
} );
return newValue;
} );

return data;
},
donation( root, args, context ){
console.log( args );
const getQuery = 'donations/' + args.donation_id + '.json';

const data = getFromDT(getQuery)
.then((res) => {
return res.donation;
});
return data;
}
}
};


Any query I do @ /graphql gets me this error message.

{
"errors": [
{
"message": "Resolve function missing for \"Splits.donation\""
}
]
}


Any help here is appreciated.

Answer

It looks like you're using graphql-tools to create your schema. This error message tells you that your schema cannot be built successfully because the donation field on Splits needs a resolve function. You defined the resolve function, but you put it inside RootQuery instead of Splits where it belongs:

export default resolveFunctions = {
  RootQuery: {
    Splits( root, args, context ){
      let newValue = [];
      const getQuery = 'funds/' + args.id + '/splits.json';

      const data = getFromDT(getQuery)
        .then( ( res ) => {
          res.forEach( function ( donationSplit ) {
            newValue.push( donationSplit.split );
          } );
          return newValue;
        } );

      return data;
    },
  },
  Splits: { // <<---- you forgot this ------
    donation( root, args, context ){
      console.log( args );
      const getQuery = 'donations/' + args.donation_id + '.json';

      const data = getFromDT(getQuery)
        .then((res) => {
          return res.donation;
        });
      return data;
    }
  },
};
Comments