Skip to content

Commit f65b83f

Browse files
committed
Optimize performance of method validation
Perform the check for whether validation for a HandlerMethod is needed earlier and only once rather than in the constructor of DataFetcherHandlerMethod. Make the validation helper passed to DataFetcherHandlerMethod stateful, so that validation groups are also determined once on startup. See gh-571
1 parent 4c1e7c5 commit f65b83f

File tree

5 files changed

+208
-234
lines changed

5 files changed

+208
-234
lines changed

spring-graphql/src/main/java/org/springframework/graphql/data/method/annotation/support/AnnotatedControllerConfigurer.java

Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2022 the original author or authors.
2+
* Copyright 2002-2023 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -125,7 +125,7 @@ public class AnnotatedControllerConfigurer
125125
private HandlerMethodArgumentResolverComposite argumentResolvers;
126126

127127
@Nullable
128-
private HandlerMethodValidationHelper validationHelper;
128+
private ValidationHelper validationHelper;
129129

130130

131131
/**
@@ -176,8 +176,7 @@ public void afterPropertiesSet() {
176176
this.argumentResolvers = initArgumentResolvers();
177177

178178
if (beanValidationPresent) {
179-
this.validationHelper =
180-
HandlerMethodValidationHelper.createIfValidatorAvailable(obtainApplicationContext());
179+
this.validationHelper = ValidationHelper.createIfValidatorPresent(obtainApplicationContext());
181180
}
182181
}
183182

@@ -228,7 +227,8 @@ public void configure(RuntimeWiring.Builder runtimeWiringBuilder) {
228227
findHandlerMethods().forEach((info) -> {
229228
DataFetcher<?> dataFetcher;
230229
if (!info.isBatchMapping()) {
231-
dataFetcher = new SchemaMappingDataFetcher(info, this.argumentResolvers, this.validationHelper, this.executor);
230+
dataFetcher = new SchemaMappingDataFetcher(
231+
info, this.argumentResolvers, this.validationHelper, this.executor);
232232
}
233233
else {
234234
String dataLoaderKey = registerBatchLoader(info);
@@ -492,7 +492,7 @@ static class SchemaMappingDataFetcher implements DataFetcher<Object> {
492492
private final HandlerMethodArgumentResolverComposite argumentResolvers;
493493

494494
@Nullable
495-
private final HandlerMethodValidationHelper validatorHelper;
495+
private final Consumer<Object[]> methodValidationHelper;
496496

497497
@Nullable
498498
private final Executor executor;
@@ -501,12 +501,12 @@ static class SchemaMappingDataFetcher implements DataFetcher<Object> {
501501

502502
SchemaMappingDataFetcher(
503503
MappingInfo info, HandlerMethodArgumentResolverComposite resolvers,
504-
@Nullable HandlerMethodValidationHelper validatorHelper,
505-
@Nullable Executor executor) {
504+
@Nullable ValidationHelper validationHelper, @Nullable Executor executor) {
506505

507506
this.info = info;
508507
this.argumentResolvers = resolvers;
509-
this.validatorHelper = validatorHelper;
508+
this.methodValidationHelper = (validationHelper != null ?
509+
validationHelper.getValidationHelperFor(info.getHandlerMethod()) : null);
510510
this.executor = executor;
511511
this.subscription = this.info.getCoordinates().getTypeName().equalsIgnoreCase("Subscription");
512512
}
@@ -524,7 +524,8 @@ public HandlerMethod getHandlerMethod() {
524524
public Object get(DataFetchingEnvironment environment) throws Exception {
525525

526526
DataFetcherHandlerMethod handlerMethod = new DataFetcherHandlerMethod(
527-
getHandlerMethod(), this.argumentResolvers, this.validatorHelper, this.executor, this.subscription);
527+
getHandlerMethod(), this.argumentResolvers, this.methodValidationHelper,
528+
this.executor, this.subscription);
528529

529530
return handlerMethod.invoke(environment);
530531
}

spring-graphql/src/main/java/org/springframework/graphql/data/method/annotation/support/DataFetcherHandlerMethod.java

Lines changed: 9 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2022 the original author or authors.
2+
* Copyright 2002-2023 the original author or authors.
33
*
44
* Licensed under the Apache License, Version 2.0 (the "License");
55
* you may not use this file except in compliance with the License.
@@ -17,6 +17,7 @@
1717

1818
import java.util.Arrays;
1919
import java.util.concurrent.Executor;
20+
import java.util.function.Consumer;
2021

2122
import graphql.schema.DataFetchingEnvironment;
2223
import org.reactivestreams.Publisher;
@@ -49,8 +50,7 @@ public class DataFetcherHandlerMethod extends InvocableHandlerMethodSupport {
4950

5051
private final HandlerMethodArgumentResolverComposite resolvers;
5152

52-
@Nullable
53-
private final HandlerMethodValidationHelper validator;
53+
private final Consumer<Object[]> validationHelper;
5454

5555
private final ParameterNameDiscoverer parameterNameDiscoverer = new DefaultParameterNameDiscoverer();
5656

@@ -61,17 +61,17 @@ public class DataFetcherHandlerMethod extends InvocableHandlerMethodSupport {
6161
* Constructor with a parent handler method.
6262
* @param handlerMethod the handler method
6363
* @param resolvers the argument resolvers
64-
* @param validator the input validator
64+
* @param validationHelper to apply bean validation with
6565
* @param subscription whether the field being fetched is of subscription type
6666
*/
67-
public DataFetcherHandlerMethod(HandlerMethod handlerMethod,
68-
HandlerMethodArgumentResolverComposite resolvers, @Nullable HandlerMethodValidationHelper validator,
69-
@Nullable Executor executor, boolean subscription) {
67+
public DataFetcherHandlerMethod(
68+
HandlerMethod handlerMethod, HandlerMethodArgumentResolverComposite resolvers,
69+
@Nullable Consumer<Object[]> validationHelper, @Nullable Executor executor, boolean subscription) {
7070

7171
super(handlerMethod, executor);
7272
Assert.isTrue(!resolvers.getResolvers().isEmpty(), "No argument resolvers");
7373
this.resolvers = resolvers;
74-
this.validator = (validator != null && validator.requiresValidation(handlerMethod) ? validator : null);
74+
this.validationHelper = (validationHelper != null ? validationHelper : args -> {});
7575
this.subscription = subscription;
7676
}
7777

@@ -83,15 +83,6 @@ public HandlerMethodArgumentResolverComposite getResolvers() {
8383
return this.resolvers;
8484
}
8585

86-
/**
87-
* Return the configured input validator.
88-
* @deprecated as of 1.1 without a replacement
89-
*/
90-
@Deprecated
91-
@Nullable
92-
public HandlerMethodValidationHelper getValidator() {
93-
return this.validator;
94-
}
9586

9687

9788
/**
@@ -188,9 +179,7 @@ private Object[] getMethodArgumentValues(
188179

189180
@Nullable
190181
private Object validateAndInvoke(Object[] args, DataFetchingEnvironment environment) {
191-
if (this.validator != null) {
192-
this.validator.validate(this, args);
193-
}
182+
this.validationHelper.accept(args);
194183
return doInvoke(environment.getGraphQlContext(), args);
195184
}
196185

spring-graphql/src/main/java/org/springframework/graphql/data/method/annotation/support/HandlerMethodValidationHelper.java

Lines changed: 0 additions & 146 deletions
This file was deleted.

0 commit comments

Comments
 (0)