Nicolas Bouvrette
Nicolas Bouvrette

Reputation: 4767

Is there a way with Hasura to do a mutation based on the result of a query, within the same GraphQL call (Hasura transaction)?

I tried to search for an example but, I presume it's not doable. I am looking to hopefully be proven wrong or to find an official confirmation that it's not doable.

Before using Hasura, I was doing transactional SQL queries that ensured that data was kept consistent.

For example, I would like to create a password reset token if a user requests it, only if the user can be found using an email address. Right now, I have to do 2 queries:

In that case, it's not too bad, but now if I want to consume that token, I have to do 3 queries:

Obviously, if something goes wrong and the token is not deleted, this could be an issue - so I would be curious to see if there would be ways to merge these queries/mutations into transactions.

Upvotes: 1

Views: 1632

Answers (3)

Nicolas Bouvrette
Nicolas Bouvrette

Reputation: 4767

After some research here is what I found:

For the first example:

  • Try to find a user with the specified email address
  • Insert and assign the token to this user id

There are no solutions for this today and as answered by @damel, there is an ongoing RFC to support nested mutations: https://github.com/hasura/graphql-engine/issues/1573#issuecomment-1338057350

Hopefully, this feature will be out soon, but in the meantime, for most cases, it's not such a big deal to have multiple queries as it is possible to catch errors on the first query.

For the second example:

  • Find the valid token
  • Change the password to the user associated with that token
  • Delete the token

When sending multiple mutations in the same query, Hasura treats them as a transaction as announced in 2020.

Of course, it would be nice to do this in the same query (similar to the first example) but since there is a transaction on the mutation, for this case it's still not a problem.

I am sure there are probably cases where this can become a problem but I am not exposed to them right now. Nevertheless, it would be great if the RFC makes it to production, giving more options to Hasura users.

Upvotes: 0

damel
damel

Reputation: 11

Sounds like supporting nested updates would solve this problem for you with the least amount of effort. We are working on a rfc for the feature and hope to start development soon. Please follow this Github issue on our community for future updates. https://github.com/hasura/graphql-engine/issues/1573

This comment outlines the current scope of the proposed feature. The rfc will provide a more complete explanation. https://github.com/hasura/graphql-engine/issues/1573#issuecomment-1338057350

Upvotes: 1

Friedrich
Friedrich

Reputation: 2290

You can apply changes to rows that you filter by certain criteria. Here is a sample mutation:

mutation PasswordUpdate($id: uuid!, $token: String!, $new_password: String!) {
  update_user(
    where: {id: {_eq: $id}, token: {_eq: $token}}
    _set: {token: null, password: $new_password}
  ) {
    affected_rows
  }
}

That query deletes the token and sets a password for all users (hopefully just one) that have the token assigned.

Upvotes: 0

Related Questions