Graphql-js: [Feat] Chain operations (mutations/queries) values

Created on 28 Feb 2017  路  13Comments  路  Source: graphql/graphql-js

This is a feature request

The objective is it would be great to be able to send 2 operations or more, and to use the result of the 潞1 one into the 2潞 one, like say i would like to query the id of some field and use it to set a foreign key in the second operation(mutation).

Something along the lines:

mutation a {
  theProduct: getProduct(code: 1001) {
    id
  }

  createOrder(orderNumber: 1010, productId: theProduct.id) {
    id
    productId
  }
}

Is it possible? or what's the recommended way to do so?

PD: I realize the getProduct mutation has no side effects, it is essentially a query in this scenario, but maybe in another scenario we could create the product and immediately associate it's id to an order.

Most helpful comment

+1

All 13 comments

This is something I am wondering about also - is it possible to use the result of a first mutation and be able to reference it in a second mutation, without requiring multiple round trips?

As far as i know it's not possible, that's why i posted as a feature request.

Something like this is already used at Facebook I think. I'm sure that there was a talk which mention something similar with connected queries.. can anybody bring link to this talk?

+1

This idea seems great, but I was wandering about those following examples :

mutation a {
  theProducts: getProducts(codes: [1001]) {
     id
  }
  # now theProducts is an array  [ { "id" : "product-foo-1001" } ]
  # Would the following  be correct ?
  createOrder(orderNumber: 1010, productId: theProducts[0].id) {  
    id
    productId
  }
}
mutation a {
  theProduct : store(id:"store-123456") {
    product(code:1001) {
      id
  聽 }
  }
  # does the following seem correct ?
  createOrder(orderNumber:1010, productId : theProduct.product.id) {
    id
    productId
  }  
}

mutation a {
  theStores : stores(ids: [ "store-123456" ] ) {  # return an array of store with one entry
    products(codes:[1001]) {   # return an array of product with one entry
      id
    }
  }

  createOrder(orderNumber:1010, productId : theStore[0].products[0].id) { 
    id
    productId
  }  
}

# What if I write :
theProduct : stores(ids : [ "store-123456", "store-456789" ]) { # 2 entries of store
  products(codes:[1001]) {
    id
  }
}

My examples are not very meaningfull as thoses graphql api's seem to be not well designed. But the point is : as far as the queries "theProducts:" in those examples are all valid in term of graphql query, how to deal with the following "theProduct" parameter ? Specially when arrays are involved (writing theProduct[0].product[0] is obviously not a good idea) ?

I have seen some APIs support a "batch" operation where rather than some new GraphQL syntax, two separate GraphQL requests are included in the batch where some variables in the second request are fulfilled by part of the response of the first request. We use this sort of thing at Facebook for some rare cases like this.

Alternatively, it could be better if your createOrder mutation anticipated this access pattern and allowed for input arguments which captured this more complex behavior.

I hope that helped to understand how some others have addressed this use case

I have seen some APIs support a "batch" operation where rather than some new GraphQL syntax, two separate GraphQL requests are included in the batch where some variables in the second request are fulfilled by part of the response of the first request. We use this sort of thing at Facebook for some rare cases like this.

I was looking for this but had no luck on my search. I could only find examples for nested queries and never for two separate GraphQL requests. Could anyone provide an example on how this could be achieved?

@carneiror Most of the batch stuff I've seen is from Apollo. I believe the server supports batching out of the box and you can send multiple using their batch link: https://www.apollographql.com/docs/link/links/batch-http.html

why is this issue closed ? I have the same question and haven't found an answer anywhere.

Batching is only 1/3 of the problem, the feature requested is to be able to use the result of one operation in another one in same request, which I now realize would require the operations of the query be executed in a serial manner, in a defined order.

Maybe I'm asking too much? I think not even rest can do that without hardcoding the functionality in the API middleware, at the end is just a nice to have.

Makes sense, @luchillo17. Thanks for the explanation. I'm still pretty new to graphql. do you know what the "best practice" is for kicking off a second request as soon as the first response is returned? I have a createPost mutation, where I'd like to enter some data into a post table, and then a createTag mutation where I'd like to enter some data into a tag table. then once both requests are returned, I want to use post Id and tag Id's in a createPostTag mutation in a separate table. Thanks in advance!

Why is this closed?

I guess expecting the framework to handle serial tasks, and be able to use the result of one into the next is too much, not even rest can do that without hardcoding it in the middleware, and you can hardcode that in GraphQL as well if needed.

Adding support for this would require to modify the GraphQL spec, like adding syntax specific to scheduling queries or mutations, how do we define parallel vs serial requests? how do we define which query or mutation needs access to the previous query or mutation result? how do we handle error cases when such dependencies exist between queries? basically, GraphQL spec doesn't have an answer for all those questions, and as long as it doesn't this feature likely will not be implemented.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

hekike picture hekike  路  4Comments

matthewgertner picture matthewgertner  路  4Comments

swist picture swist  路  4Comments

pranshuchittora picture pranshuchittora  路  3Comments

henry74 picture henry74  路  4Comments