Strawberry GraphQL is a popular Python library for building GraphQL APIs. It's widely adopted and integrates smoothly with Django, SQLAlchemy, Pydantic, and other Object Relational Mapping (ORM) systems. In early 2024, a critical vulnerability—CVE-2025-22151—was discovered in Strawberry’s relay integration, affecting versions .182. up to, but not including, .257..
This flaw can cause severe security issues like leaking sensitive information or even unauthorized privilege escalation. In this post, I’ll explain the bug in simple terms, show how it works (code included), and what you should do if your project uses Strawberry.
What’s the Problem?
The bug is a type confusion issue in Strawberry's relay support. In Strawberry, you can connect GraphQL types to backend models (like Django or SQLAlchemy models). Companies often use this for building complex APIs.
If you set up *multiple GraphQL types* for the same backend model (say, FruitType and SpecialFruitType for a FruitModel), and both use the GraphQL relay _node interface_, you might expect calling the global node query to always give the matching GraphQL type for the ID. But before version .257., Strawberry might return the “wrong” type — say, returning a SpecialFruitType when you asked for a FruitType. If the returned type exposes private data, boom: information disclosure.
In certain cases, if a privileged type is exposed, users might even gain access to data, features, or mutations they shouldn’t see.
Let's look at a simplified but dangerous example using Strawberry with Django
import strawberry
from strawberry.django import relay
from .models import FruitModel
# Regular fruit type
@strawberry.django.type(FruitModel)
class FruitType(relay.Node):
id: strawberry.ID
name: str
# Special fruit type - e.g., with a sensitive internal code
@strawberry.django.type(FruitModel)
class SpecialFruitType(relay.Node):
id: strawberry.ID
name: str
secret_code: str # Sensitive field
@strawberry.type
class Query:
node: relay.Node = relay.node_field()
What’s the problem?
Both FruitType and SpecialFruitType map to the same model but have different fields. Querying for the global node, *it’s possible (pre-.257.)* to ask for a FruitType, but get a SpecialFruitType (or vice versa):
query {
node(id: "FruitType:1") {
... on SpecialFruitType {
id
name
secret_code # This might succeed and leak sensitive information!
}
}
}
Even though you queried using a FruitType ID, the resolver can return a SpecialFruitType, exposing that extra secret_code. In complex apps with multiple models and permission settings, the consequences can be severe.
At a technical level
- Strawberry uses a global "node" field to find types by ID across the schema, following the Relay spec.
- When more than one GraphQL type is mapped to a model, Strawberry's internal lookup may not distinguish which type is being requested. It may just fetch and return whichever type matches first, or based on order of registration.
- This mistake means attackers can craft queries that extract fields only present on privileged types.
Finds two or more types for the same model (e.g., via introspection).
3. Crafts a query for the global node ID, specifying the more privileged type in the fragment, hoping Strawberry mistakenly resolves and exposes those sensitive fields.
Proof-of-Concept Query
Suppose user A should only access FruitType, *not* fields exclusive to SpecialFruitType.
With versions < .257., user A can run
query {
node(id: "FruitType:1") {
... on SpecialFruitType {
secret_code # This should NOT be accessible!
}
}
}
If the bug is present, Strawberry returns secret_code even for users who should never see it.
Solution: Update to .257.+
- Patch available: Strawberry release .257.
- Changelog/fix PR: GitHub pull request with the fix
Upgrading Strawberry in your Python project is straightforward
pip install --upgrade 'strawberry-graphql>=.257.'
Avoid mapping multiple GraphQL types to the same ORM model on relay nodes.
2. Restrict GraphQL type exposure: Don’t include privileged/sensitive fields on GraphQL types mapped to relay nodes.
References and More Reading
- Strawberry’s security advisory (GHSA-v7fv-65c5-vjm2)
- GitHub Issue: Type confusion relay nodes
- Relay Node Interface in Strawberry Docs
- GraphQL Relay Specification
Conclusion
CVE-2025-22151 is a serious issue for apps using Strawberry GraphQL with relay integration and multiple types per model. If you’re building APIs with Strawberry and use relays, upgrade to v.257. or later _immediately_.
Want to check your risk? Audit your GraphQL types—look for ORM models mapped to more than one GraphQL type, especially if any expose privileged data. Until you upgrade, limit your GraphQL exposure and don’t rely on GraphQL alone for access control.
Keep your APIs secure—and spread the word!
Timeline
Published on: 01/09/2025 19:15:20 UTC