'How can I reduce the number of database queries for a one to many association in Strawberry GraphQL and FastAPI?

I'm developing a python GraphQL API server using FastAPI and Strawberry, and I'm implementing this feature: I have two entities, User and Order, which have a one to many association (a User can have many Orders, an Order can only have one User), and I want to get a list of users, each with the list of their orders.

If I were to implement this with a simple REST endpoint, I could make a first query to get the users and then a second query to fetch the orders, sorting out, in the python code, which user each order belongs to based on the foreign key value.

Using Strawberry GraphQL though, it seems I cannot avoid making a query for each user, given that, even using the data loader pattern I would still need to know the order ids beforehand, and this is making the response time much slower.

Is there a solution to this problem? Is my approach completely wrong?



Solution 1:[1]

The data loader function itself can do the grouping.

async def load_orders_by_user(keys: list[int]) -> Iterable[list[Order]]:
    orders = # select * from order where user_id in keys
    groups = {key: [] for key in keys}  # dict maintains order
    for order in orders:
        groups[order.user_id].append(order)
    return groups.values()

Variants on that idea:

  • the loader could also load the users at the same time
  • the loader could group order ids only and use a different data loader for orders

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 A. Coady