https://kotlinlang.org logo
#graphql-kotlin
Title
# graphql-kotlin
b

Brian Dilley

03/25/2021, 8:49 PM
hey guys, how do you handle a one to many situation. ie:
Copy code
data class Movie(
    val id: Long,
    val token: String
)

data class User(
    val id: Long,
    val name: String
) {

    fun movies(userIds: List<Long>): List<Movie> {
        return LongRange(0, 2)
            .map { Movie(it, "movie-$it") }
            .toList()
    }
}

@Component
class UserQueries : Query {

    fun users(): List<User> {
        return LongRange(0, 5)
            .map { User(it, "user-$it") }
            .toList()
    }
}
In a database situation it would be really bad to query users along with their movies because it would issue a single query per user to get their movies. Is there a way to avoid the multiple queries and instead get a list of the user ids and make a single query for all of their movies?
s

Shane Myrick

03/25/2021, 8:57 PM
Yes, this is call this
n+1
problem in graphql. There are many different solutions. First off is that you can have your movie service handle batch requests and you don’t send the request until you have resolved all the users. Of course you could also implement caching in the downstream services. But if you wanted GraphQL caching, you can use the Data Loader pattern: https://expediagroup.github.io/graphql-kotlin/docs/server/data-loaders
b

Brian Dilley

03/25/2021, 9:00 PM
this seems like it’s mainly just caching
vs. collecting all of the user ids and passing them to a single function for me to query with
i see the BatchLoader interface, but how will it know which movies to associate with which users?
d

Dariusz Kuc

03/25/2021, 9:30 PM
data loader pattern delays "loader" execution AFTER all fields (at a given level) are processed (but not resolved) -> so when the loader kicks off it will have ids from all fields and when it returns then result will be used to construct the appropriate response for the corresponding fields
👍 1
b

Brian Dilley

03/25/2021, 9:32 PM
thanks
2 Views