ExpediaGroup / graphql-kotlin

Libraries for running GraphQL in Kotlin
https://opensource.expediagroup.com/graphql-kotlin/
Apache License 2.0
1.74k stars 345 forks source link

Add support for max query depth and complexity #855

Open herder opened 4 years ago

herder commented 4 years ago

Is your feature request related to a problem? Please describe.

Currently I haven't found any way to annotate classes and Query:s to limit the complexity and depth of the queries, exposing the service to malicious and/or badly crafted queries.

Describe the solution you'd like

Being able to add annotation on a query describing max complexity and depth via an annotation, and being able to annotate fields in the data classes with complexity numbers, then instrumenting the execution so that the query is rejected if it exceeds the limits would be a great addition to the framework.

Maybe something like


data class MyClass(val name: String, @GraphQLComplexity(1) val addresses: List<String>)

class MyQuery(id: String): Query {

@MaxQueryDepth(2)
@MaxQueryComplexity(3)
fun getMyClass(id: String): MyClass {
}

}

This is supported if not documented in graphql-java via this pull request: https://github.com/graphql-java/graphql-java/pull/655

Describe alternatives you've considered

It is probably still possible to instrument the execution manually, but integrating it into the framework would be preferable.

smyrick commented 3 years ago

The MaxQueryComplexityInstrumentation and MaxQueryDepthInstrumentation are implemented at instrumentation so you can just add these to your GraphQL object today.

https://www.graphql-java.com/documentation/v16/instrumentation/

Or on graphql-kotlin-spring-server, create an instance of them as a bean: https://opensource.expediagroup.com/graphql-kotlin/docs/server/spring-server/spring-beans/#graphql-configuration

dariuszkuc commented 3 years ago

I believe the ask was for a convenience on how to generically assign complexity value for given fields. You can specify custom FieldComplexityCalculator when creating an instance of MaxQueryComplexityInstrumentation but ideally this info could be automatically generated from the schema definition itself.

Similarly you might want to specify different max depths for different queries.

smyrick commented 3 years ago

I don't think we will be implementing this in our library just due to the increase features and support it would take. As mentioned the instrumentation is available and you can create custom annotations that implement these extra things through hooks.

@dariuszkuc Would you like to keep the issue open though and keep it available for someone else to implement?