5858import org .springframework .core .ResolvableType ;
5959import org .springframework .core .annotation .AnnotatedElementUtils ;
6060import org .springframework .core .convert .ConversionService ;
61+ import org .springframework .data .domain .ScrollPosition ;
6162import org .springframework .format .FormatterRegistrar ;
6263import org .springframework .format .support .DefaultFormattingConversionService ;
6364import org .springframework .format .support .FormattingConversionService ;
8283import org .springframework .validation .DataBinder ;
8384
8485/**
85- * {@link RuntimeWiringConfigurer} that detects {@link SchemaMapping @SchemaMapping}
86- * annotated handler methods in {@link Controller @Controller} classes and
87- * registers them as {@link DataFetcher}s.
86+ * {@link RuntimeWiringConfigurer} that finds {@link SchemaMapping @SchemaMapping}
87+ * annotated handler methods in {@link Controller @Controller} classes declared in
88+ * Spring configuration, and registers them as {@link DataFetcher}s.
8889 *
8990 * <p>In addition to initializing a {@link RuntimeWiring.Builder}, this class, also
9091 * provides an option to {@link #configure(GraphQLCodeRegistry.Builder) configure}
9192 * data fetchers on a {@link GraphQLCodeRegistry.Builder}.
9293 *
94+ * <p>This class detects the following strategies in Spring configuration,
95+ * expecting to find a single, unique bean of that type:
96+ * <ul>
97+ * <li>{@link CursorStrategy} -- if Spring Data is present, and the strategy
98+ * supports {@code ScrollPosition}, then {@link ScrollSubrangeMethodArgumentResolver}
99+ * is configured for use. If not, then {@link SubrangeMethodArgumentResolver}
100+ * is added instead.
101+ * <li>{@link SortStrategy} -- if present, then {@link SortMethodArgumentResolver}
102+ * is configured for use.
103+ * </ul>
104+ *
105+ *
106+ *
93107 * @author Rossen Stoyanchev
94108 * @author Brian Clozel
95109 * @since 1.0.0
@@ -125,9 +139,6 @@ public class AnnotatedControllerConfigurer implements ApplicationContextAware, I
125139
126140 private final FormattingConversionService conversionService = new DefaultFormattingConversionService ();
127141
128- @ Nullable
129- private CursorStrategy <?> cursorStrategy ;
130-
131142 private final List <HandlerMethodArgumentResolver > customArgumentResolvers = new ArrayList <>(8 );
132143
133144 @ Nullable
@@ -156,21 +167,6 @@ public void addFormatterRegistrar(FormatterRegistrar registrar) {
156167 registrar .registerFormatters (this .conversionService );
157168 }
158169
159- /**
160- * Configure a {@link CursorStrategy} to handle pagination requests, which
161- * results in one of the following:
162- * <ul>
163- * <li>If Spring Data is present, and the strategy supports {@code ScrollPosition},
164- * then {@link ScrollSubrangeMethodArgumentResolver} is configured as a method
165- * argument resolver.
166- * <li>Otherwise {@link SubrangeMethodArgumentResolver} is added.
167- * </ul>
168- * @since 1.2
169- */
170- public void setCursorStrategy (@ Nullable CursorStrategy <?> cursorStrategy ) {
171- this .cursorStrategy = cursorStrategy ;
172- }
173-
174170 /**
175171 * Add a {@link HandlerMethodArgumentResolver} for custom controller method
176172 * arguments. Such custom resolvers are ordered after built-in resolvers
@@ -270,18 +266,8 @@ private HandlerMethodArgumentResolverComposite initArgumentResolvers() {
270266 // Type based
271267 resolvers .addResolver (new DataFetchingEnvironmentMethodArgumentResolver ());
272268 resolvers .addResolver (new DataLoaderMethodArgumentResolver ());
273- if (this .cursorStrategy != null ) {
274- resolvers .addResolver (createSubrangeMethodArgumentResolver (this .cursorStrategy ));
275- }
276- if (springDataPresent ) {
277- try {
278- resolvers .addResolver (
279- new SortMethodArgumentResolver (obtainApplicationContext ().getBean (SortStrategy .class )));
280- }
281- catch (NoSuchBeanDefinitionException ex ) {
282- // ignore
283- }
284- }
269+ addSubrangeMethodArgumentResolver (resolvers );
270+ addSortMethodArgumentResolver (resolvers );
285271 if (springSecurityPresent ) {
286272 ApplicationContext context = obtainApplicationContext ();
287273 resolvers .addResolver (new PrincipalMethodArgumentResolver ());
@@ -299,15 +285,34 @@ private HandlerMethodArgumentResolverComposite initArgumentResolvers() {
299285 return resolvers ;
300286 }
301287
302- @ SuppressWarnings ("unchecked" )
303- private static HandlerMethodArgumentResolver createSubrangeMethodArgumentResolver (CursorStrategy <?> strategy ) {
288+ @ SuppressWarnings ({"unchecked" , "CastCanBeRemovedNarrowingVariableType" })
289+ private void addSubrangeMethodArgumentResolver (HandlerMethodArgumentResolverComposite resolvers ) {
290+ try {
291+ CursorStrategy <?> strategy = obtainApplicationContext ().getBean (CursorStrategy .class );
292+ if (springDataPresent ) {
293+ if (strategy .supports (ScrollPosition .class )) {
294+ CursorStrategy <ScrollPosition > strategyToUse = (CursorStrategy <ScrollPosition >) strategy ;
295+ resolvers .addResolver (new ScrollSubrangeMethodArgumentResolver (strategyToUse ));
296+ return ;
297+ }
298+ }
299+ resolvers .addResolver (new SubrangeMethodArgumentResolver <>(strategy ));
300+ }
301+ catch (NoSuchBeanDefinitionException ex ) {
302+ // ignore
303+ }
304+ }
305+
306+ private void addSortMethodArgumentResolver (HandlerMethodArgumentResolverComposite resolvers ) {
304307 if (springDataPresent ) {
305- if (strategy .supports (org .springframework .data .domain .ScrollPosition .class )) {
306- return new ScrollSubrangeMethodArgumentResolver (
307- (CursorStrategy <org .springframework .data .domain .ScrollPosition >) strategy );
308+ try {
309+ SortStrategy strategy = obtainApplicationContext ().getBean (SortStrategy .class );
310+ resolvers .addResolver (new SortMethodArgumentResolver (strategy ));
311+ }
312+ catch (NoSuchBeanDefinitionException ex ) {
313+ // ignore
308314 }
309315 }
310- return new SubrangeMethodArgumentResolver <>(strategy );
311316 }
312317
313318 protected final ApplicationContext obtainApplicationContext () {
0 commit comments