Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

In mutations include only arguments which have a value set in variables #362

Closed
beepsoft opened this issue Apr 21, 2022 · 0 comments · Fixed by #363
Closed

In mutations include only arguments which have a value set in variables #362

beepsoft opened this issue Apr 21, 2022 · 0 comments · Fixed by #363

Comments

@beepsoft
Copy link
Collaborator

In a Hasura generated schema I have this mutation:

# update data of the table: "task"
updateTasks(
  # append existing jsonb value of filtered columns with new jsonb value
  _append: task_append_input

  # delete the field or element with specified path (for JSON arrays, negative integers count from the end)
  _delete_at_path: task_delete_at_path_input

  # delete the array element with specified index (negative integers count from
  # the end). throws an error if top level container is not an array
  _delete_elem: task_delete_elem_input

  # delete key/value pair or string element. key/value pairs are matched based on their key value
  _delete_key: task_delete_key_input

  # increments the numeric columns with given value of the filtered values
  _inc: task_inc_input

  # prepend existing jsonb value of filtered columns with new jsonb value
  _prepend: task_prepend_input

  # sets the columns of the filtered rows to the given values
  _set: task_set_input

  # filter the rows which have to be updated
  where: task_bool_exp!
): task_mutation_response

For this, the following function is generated by mst-gql:

mutateUpdateTasks(variables: { append?: TaskAppendInput, deleteAtPath?: TaskDeleteAtPathInput, deleteElem?: TaskDeleteElemInput, deleteKey?: TaskDeleteKeyInput, inc?: TaskIncInput, prepend?: TaskPrependInput, set?: TaskSetInput, where: TaskBoolExp }, resultSelector: string | ((qb: TaskMutationResponseModelSelector) => TaskMutationResponseModelSelector) = taskMutationResponseModelPrimitives.toString(), optimisticUpdate?: () => void) {
  return self.mutate<{ updateTasks: TaskMutationResponseModelType}>(`mutation updateTasks($append: task_append_input, $deleteAtPath: task_delete_at_path_input, $deleteElem: task_delete_elem_input, $deleteKey: task_delete_key_input, $inc: task_inc_input, $prepend: task_prepend_input, $set: task_set_input, $where: task_bool_exp!) { updateTasks(_append: $append, _delete_at_path: $deleteAtPath, _delete_elem: $deleteElem, _delete_key: $deleteKey, _inc: $inc, _prepend: $prepend, _set: $set, where: $where) {
    ${typeof resultSelector === "function" ? resultSelector(new TaskMutationResponseModelSelector()).toString() : resultSelector}
  } }`, variables, optimisticUpdate)
},

Note that every argument from the graphql schema is listed in the generated mutation updateTasks(...) as arguments.

When I try to use this function like this (I only want to set a specific value):

store.mutateUpdateTasks({
    where: {
        id: {
            _eq: 1
        }
    },
    set: {
        tag: "foo"
    }
},
selectFromTaskMutationResponse().affected_rows.toString())

I get this error:

{
  "response": {
    "errors": [
      {
        "extensions": {
          "path": "$.selectionSet.updateTasks.args._inc",
          "code": "validation-failed"
        },
        "message": "expected an object for type \"task_inc_input\", but found null"
      }
    ],
    "status": 200
  },
  "request": {
    "query": "mutation updateTasks($append: task_append_input, $deleteAtPath: task_delete_at_path_input, $deleteElem: task_delete_elem_input, $deleteKey: task_delete_key_input, $inc: task_inc_input, $prepend: task_prepend_input, $set: task_set_input, $where: task_bool_exp!) { updateTasks(_append: $append, _delete_at_path: $deleteAtPath, _delete_elem: $deleteElem, _delete_key: $deleteKey, _inc: $inc, _prepend: $prepend, _set: $set, where: $where) {\n        __typename\naffected_rows\n\n      } }",
    "variables": {
      "where": {
        "id": {
          "_eq": 1
        }
      },
      "set": {
        "tag": "foo"
      }
    }
  }
}

The problem is that while _inc (of type task_inc_input) is defined as optional _inc: $inc somehow Hasura expects to have value for it in variables because it is mentioned among the updateTasks() parameters. In case of queries I didn't see this happen, only in mutations. Maybe mutation arguments have a different semantics than query arguments?

Anyways, I think it would be feasible to only generate arguments, which are set in variables. This needs runtime evaluation of the variables and based on that should be the graphql mutation string generated.

A similar mechanism is also implemented in #361, so I could fix this mutation issue as well.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant