GraphQL non-nullable fields can lead to cascading null errors.

Let's say this is the result of a GraphQL query:

{
  "data": {
    "user": {
      "name": "user1",
      "email": "user1@example.com",
      "tickets": [{"id": "ticket1"}],
      "project": {
	    "name": "Project1",
	    "description": "Description for project 1",
	    "client": "Client 1"
	  }
    }
  }
}

All the fields are marked as non-null:

type User {
  name: String!
  email: String!
  project: Project!
  tickets: [Ticket!]!
}

type Project {
  name: String!
  description: String!
  client: String!
}

// + Ticket

Let's say the Project.client is considered sensitive information and will be removed for non-admin users.

This is the result for the same query when the client returns an error:

{
  "data": null,
  "errors": ...
}

One field was denied, but the whole User object is now null in the response. This is surprising but logical.

The Project.client is marked as non-null, meaning that this field will always have a value. That means the User.project has to be null.

But User.project is marked as non-null, so it can't be null. Because of that, User will be null.

The solution seems simple: make the Project.client nullable as that is how it behaves. But that's a breaking change: clients don't need to check if that field is nullable or not because it's marked as required. By relaxing this requirement the clients now need to check the field before they use it. And introducing breaking changes is always painful.

While it seems desirable to avoid non-null fields in the schema, I'd still prefer them whenever it makes sense. If some users can get a field but not others then make it nullable. But if a field being null is a result of some backend-side error then mark it as non-nullable.

What I'd definitely advise against is to work around the nullability and keep the clients happy by introducing magic values or returning an empty list. A client of "" or "INVALID" or "ACCESS DENIED" are terrible options.

September 19, 2024

Free PDF guide

Sign up to our newsletter and download the "Git Tips and Tricks" guide.