This Strawberry GraphQL error occurs when you have selected a field in your GraphQL query that has subfields, but didn’t specify them. To fix this, simply add the fields you want in brackets after the field that’s causing the error. So, instead of query{ foo }
, you’d put query{ foo { bar }}
.
Forgetting subfields in your GraphQL queries is very common, even for developers who have been working with GraphQL for a while. I came across this error myself when working on the full-stack GraphQL example.
Before looking at the solution, let’s look at an example scenario that will cause the error.
Problem: you queried a field that has more fields within it
Let’s say you have defined your Strawberry GraphQL schema on the backend like this:
import strawberry
@strawberry.type
class Message:
name: str
text: str
message = Message(name="Fred", text="Hello World")
@strawberry.type
class Query:
@strawberry.field
async def message() -> Message:
return message
@strawberry.type
class Mutation:
@strawberry.field
async def set_message(text: str) -> Message:
message.text = text
return message
PythonThere’s a Query and a Mutation, both of which operate on a custom type called Message
. There’s also message
, a globally defined instance of Message
which the query and mutation both work with. Normally, this would be fetched from a database, but we’re keeping it simple for the example.
Now say you have the following component in the frontend that’s querying your Strawberry GraphQL backend service:
import { useQuery } from "urql";
const GET_MESSAGE = `
query {
message
}
`;
export default function Message() {
const [{data, fetching}] = useQuery({query: GET_MESSAGE});
if (fetching) {
return (
<h1>Loading...</h1>
);
} else {
return (
<h1>{data?.message.name} says: {data?.message.text}</h1>
);
}
}
JavaScriptHere, we’re using the GET_MESSAGE
query, which is selecting just the message
field defined in your GraphQL Query object above. If you’re new to GraphQL, you might think this means you’d get everything in the Message type object that’s returned.
Unfortunately, you’ll get the following error instead:
Field 'message' of type 'Message!' must have a selection of subfields. Did you mean 'message { ... }'?
GraphQL request:2:3
1 | {
2 | message
| ^
3 | }
Solution: Select the fields you want
If you look back at our Strawberry schema definition, you’ll see that we have two fields defined in the Message
type: name
and text
.
import strawberry
@strawberry.type
class Message:
name: str
text: str
message = Message(name="Fred", text="Hello World")
PythonSince Message
has fields within it, we can’t just query it, we have to modify our query in the frontend component to pick which fields we want like this:
import { useQuery } from "urql";
const GET_MESSAGE = `
query {
message {
name
text
}
}
`;
export default function Message() {
JavaScriptNow, we should see the component behaving correctly:
Conclusion
GraphQL requires you to select which subfields you want when you specify a type that has them. This is a big way that GraphQL differs from standard REST APIs – they give you only the data you want, and in that way, can be much more efficient. So remember to always select subfields from your Strawberry GraphQL types.
John is a professional software engineer who has been solving problems with code for 15+ years. He has experience with full stack web development, container orchestration, mobile development, DevOps, Windows and Linux kernel development, cybersecurity, and reverse engineering. In his spare time, he’s researching the potential business applications of AI.