Skip to content

Add batch filters - #1413

Merged
SimonCropp merged 1 commit into
mainfrom
batch-filters
Sep 17, 2026
Merged

SimonCropp merged 1 commit into
mainfrom
batch-filters

Conversation

@SimonCropp

Copy link
Copy Markdown
Owner

A filter runs once per item, so one that queries the database made a query for every item a response returned. A list of parents, each with children, cost a query per parent and another per child. Found in a downstream API whose authorization filters made a read-access query for each row.

filters.For().AddBatch(projection, filter) adds a filter that decides for many items in one call. It is passed the distinct projections and returns those to include.

Rows are batched across the response, not only within one list. Every resolver that filters (query, connection, navigation, navigation list and connection, single, first, and the Resolve/ResolveList extensions) now goes through Filters.Apply. Per item filters run there as before. Items with a batch filter join the execution's open batch, and the resolver returns a deferred result. GraphQL.NET completes deferred results after the other fields at the same depth, so each batch filter runs once per query depth, whichever rows returned the items. A batch that has started takes no more items, and a resolver's items join a batch together.

Resolvers now return object, since the value may be a deferred result. Nothing is deferred unless a batch filter applies, so existing filters behave as before. Without an execution to share, as for ApplyFilter and ShouldInclude, a batch filter runs over the given items.

Version 35.3.0.

A filter runs once per item, so one that queries the database made a query
for every item a response returned. A list of parents, each with children,
cost a query per parent and another per child. Found in a downstream API
whose authorization filters made a read-access query for each row.

filters.For<T>().AddBatch(projection, filter) adds a filter that decides for
many items in one call. It is passed the distinct projections and returns
those to include.

Rows are batched across the response, not only within one list. Every
resolver that filters (query, connection, navigation, navigation list and
connection, single, first, and the Resolve/ResolveList extensions) now goes
through Filters.Apply. Per item filters run there as before. Items with a
batch filter join the execution's open batch, and the resolver returns a
deferred result. GraphQL.NET completes deferred results after the other
fields at the same depth, so each batch filter runs once per query depth,
whichever rows returned the items. A batch that has started takes no more
items, and a resolver's items join a batch together.

Resolvers now return object, since the value may be a deferred result.
Nothing is deferred unless a batch filter applies, so existing filters
behave as before. Without an execution to share, as for ApplyFilter and
ShouldInclude, a batch filter runs over the given items.

Version 35.3.0.
@SimonCropp SimonCropp added this to the 35.3.0 milestone Sep 17, 2026
@SimonCropp
SimonCropp merged commit ea960f4 into main Sep 17, 2026
4 of 6 checks passed
@SimonCropp
SimonCropp deleted the batch-filters branch September 17, 2026 05:37
@github-actions
github-actions Bot restored the batch-filters branch September 17, 2026 05:38
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 this pull request may close these issues.

1 participant