Skip to content

Commit 3b4210f

Browse files
committed
Cannot amend properties in RequestMappingHandlerMapping (e.g. useSuffixPatternMatch) using a bean post processor as ApplicationContextAwareProcessor always fires first initialising RequestMappingHandlerMapping
Issue: SPR-9371
1 parent 79b86a7 commit 3b4210f

File tree

1 file changed

+35
-39
lines changed

1 file changed

+35
-39
lines changed

org.springframework.web.servlet/src/main/java/org/springframework/web/servlet/handler/AbstractHandlerMethodMapping.java

Lines changed: 35 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/*
2-
* Copyright 2002-2011 the original author or authors.
2+
* Copyright 2002-2012 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.
@@ -25,12 +25,11 @@
2525
import java.util.List;
2626
import java.util.Map;
2727
import java.util.Set;
28-
2928
import javax.servlet.ServletException;
3029
import javax.servlet.http.HttpServletRequest;
3130

3231
import org.springframework.beans.factory.BeanFactoryUtils;
33-
import org.springframework.context.ApplicationContextException;
32+
import org.springframework.beans.factory.InitializingBean;
3433
import org.springframework.util.ClassUtils;
3534
import org.springframework.util.LinkedMultiValueMap;
3635
import org.springframework.util.MultiValueMap;
@@ -42,25 +41,26 @@
4241
/**
4342
* Abstract base class for {@link HandlerMapping} implementations that define a
4443
* mapping between a request and a {@link HandlerMethod}.
45-
*
46-
* <p>For each registered handler method, a unique mapping is maintained with
47-
* subclasses defining the details of the mapping type {@code <T>}.
48-
*
44+
*
45+
* <p>For each registered handler method, a unique mapping is maintained with
46+
* subclasses defining the details of the mapping type {@code <T>}.
47+
*
4948
* @param <T> The mapping for a {@link HandlerMethod} containing the conditions
50-
* needed to match the handler method to incoming request.
51-
*
49+
* needed to match the handler method to incoming request.
50+
*
5251
* @author Arjen Poutsma
5352
* @author Rossen Stoyanchev
5453
* @since 3.1
5554
*/
56-
public abstract class AbstractHandlerMethodMapping<T> extends AbstractHandlerMapping {
55+
public abstract class AbstractHandlerMethodMapping<T> extends AbstractHandlerMapping implements InitializingBean {
5756

5857
private boolean detectHandlerMethodsInAncestorContexts = false;
5958

6059
private final Map<T, HandlerMethod> handlerMethods = new LinkedHashMap<T, HandlerMethod>();
6160

6261
private final MultiValueMap<String, T> urlMap = new LinkedMultiValueMap<String, T>();
6362

63+
6464
/**
6565
* Whether to detect handler methods in beans in ancestor ApplicationContexts.
6666
* <p>Default is "false": Only beans in the current ApplicationContext are
@@ -72,20 +72,18 @@ public abstract class AbstractHandlerMethodMapping<T> extends AbstractHandlerMap
7272
public void setDetectHandlerMethodsInAncestorContexts(boolean detectHandlerMethodsInAncestorContexts) {
7373
this.detectHandlerMethodsInAncestorContexts = detectHandlerMethodsInAncestorContexts;
7474
}
75-
75+
7676
/**
7777
* Return a map with all handler methods and their mappings.
7878
*/
7979
public Map<T, HandlerMethod> getHandlerMethods() {
80-
return Collections.unmodifiableMap(handlerMethods);
80+
return Collections.unmodifiableMap(this.handlerMethods);
8181
}
8282

8383
/**
84-
* ApplicationContext initialization and handler method detection.
84+
* Detects handler methods at initialization.
8585
*/
86-
@Override
87-
public void initApplicationContext() throws ApplicationContextException {
88-
super.initApplicationContext();
86+
public void afterPropertiesSet() {
8987
initHandlerMethods();
9088
}
9189

@@ -99,7 +97,7 @@ protected void initHandlerMethods() {
9997
if (logger.isDebugEnabled()) {
10098
logger.debug("Looking for request mappings in application context: " + getApplicationContext());
10199
}
102-
100+
103101
String[] beanNames = (this.detectHandlerMethodsInAncestorContexts ?
104102
BeanFactoryUtils.beanNamesForTypeIncludingAncestors(getApplicationContext(), Object.class) :
105103
getApplicationContext().getBeanNamesForType(Object.class));
@@ -131,27 +129,26 @@ protected void handlerMethodsInitialized(Map<T, HandlerMethod> handlerMethods) {
131129
* @param handler the bean name of a handler or a handler instance
132130
*/
133131
protected void detectHandlerMethods(final Object handler) {
134-
Class<?> handlerType = (handler instanceof String) ?
132+
Class<?> handlerType = (handler instanceof String) ?
135133
getApplicationContext().getType((String) handler) : handler.getClass();
136134

137135
final Class<?> userType = ClassUtils.getUserClass(handlerType);
138-
136+
139137
Set<Method> methods = HandlerMethodSelector.selectMethods(userType, new MethodFilter() {
140138
public boolean matches(Method method) {
141139
return getMappingForMethod(method, userType) != null;
142140
}
143141
});
144-
142+
145143
for (Method method : methods) {
146144
T mapping = getMappingForMethod(method, userType);
147145
registerHandlerMethod(handler, method, mapping);
148146
}
149147
}
150148

151149
/**
152-
* Provide the mapping for a handler method. A method for which no
150+
* Provide the mapping for a handler method. A method for which no
153151
* mapping can be provided is not a handler method.
154-
*
155152
* @param method the method to provide a mapping for
156153
* @param handlerType the handler type, possibly a sub-type of the method's
157154
* declaring class
@@ -161,11 +158,10 @@ public boolean matches(Method method) {
161158

162159
/**
163160
* Register a handler method and its unique mapping.
164-
*
165161
* @param handler the bean name of the handler or the handler instance
166162
* @param method the method to register
167163
* @param mapping the mapping conditions associated with the handler method
168-
* @throws IllegalStateException if another method was already registered
164+
* @throws IllegalStateException if another method was already registered
169165
* under the same mapping
170166
*/
171167
protected void registerHandlerMethod(Object handler, Method method, T mapping) {
@@ -177,29 +173,29 @@ protected void registerHandlerMethod(Object handler, Method method, T mapping) {
177173
else {
178174
handlerMethod = new HandlerMethod(handler, method);
179175
}
180-
176+
181177
HandlerMethod oldHandlerMethod = handlerMethods.get(mapping);
182178
if (oldHandlerMethod != null && !oldHandlerMethod.equals(handlerMethod)) {
183179
throw new IllegalStateException("Ambiguous mapping found. Cannot map '" + handlerMethod.getBean()
184180
+ "' bean method \n" + handlerMethod + "\nto " + mapping + ": There is already '"
185181
+ oldHandlerMethod.getBean() + "' bean method\n" + oldHandlerMethod + " mapped.");
186182
}
187-
188-
handlerMethods.put(mapping, handlerMethod);
183+
184+
this.handlerMethods.put(mapping, handlerMethod);
189185
if (logger.isInfoEnabled()) {
190186
logger.info("Mapped \"" + mapping + "\" onto " + handlerMethod);
191187
}
192-
188+
193189
Set<String> patterns = getMappingPathPatterns(mapping);
194190
for (String pattern : patterns) {
195191
if (!getPathMatcher().isPattern(pattern)) {
196-
urlMap.add(pattern, mapping);
192+
this.urlMap.add(pattern, mapping);
197193
}
198194
}
199195
}
200196

201197
/**
202-
* Extract and return the URL paths contained in a mapping.
198+
* Extract and return the URL paths contained in a mapping.
203199
*/
204200
protected abstract Set<String> getMappingPathPatterns(T mapping);
205201

@@ -230,11 +226,9 @@ protected HandlerMethod getHandlerInternal(HttpServletRequest request) throws Ex
230226
/**
231227
* Look up the best-matching handler method for the current request.
232228
* If multiple matches are found, the best match is selected.
233-
*
234229
* @param lookupPath mapping lookup path within the current servlet mapping
235230
* @param request the current request
236231
* @return the best-matching handler method, or {@code null} if no match
237-
*
238232
* @see #handleMatch(Object, String, HttpServletRequest)
239233
* @see #handleNoMatch(Set, String, HttpServletRequest)
240234
*/
@@ -289,9 +283,8 @@ private void addMatchingMappings(Collection<T> mappings, List<Match> matches, Ht
289283
}
290284

291285
/**
292-
* Check if a mapping matches the current request and return a (potentially
286+
* Check if a mapping matches the current request and return a (potentially
293287
* new) mapping with conditions relevant to the current request.
294-
*
295288
* @param mapping the mapping to get a match for
296289
* @param request the current HTTP servlet request
297290
* @return the match, or {@code null} if the mapping doesn't match
@@ -308,7 +301,7 @@ private void addMatchingMappings(Collection<T> mappings, List<Match> matches, Ht
308301

309302
/**
310303
* Invoked when a matching mapping is found.
311-
* @param mapping the matching mapping
304+
* @param mapping the matching mapping
312305
* @param lookupPath mapping lookup path within the current servlet mapping
313306
* @param request the current request
314307
*/
@@ -325,9 +318,11 @@ protected void handleMatch(T mapping, String lookupPath, HttpServletRequest requ
325318
*/
326319
protected HandlerMethod handleNoMatch(Set<T> mappings, String lookupPath, HttpServletRequest request)
327320
throws Exception {
321+
328322
return null;
329323
}
330324

325+
331326
/**
332327
* A temporary container for a mapping matched to a request.
333328
*/
@@ -344,10 +339,11 @@ private Match(T mapping, HandlerMethod handlerMethod) {
344339

345340
@Override
346341
public String toString() {
347-
return mapping.toString();
342+
return this.mapping.toString();
348343
}
349344
}
350345

346+
351347
private class MatchComparator implements Comparator<Match> {
352348

353349
private final Comparator<T> comparator;
@@ -357,8 +353,8 @@ public MatchComparator(Comparator<T> comparator) {
357353
}
358354

359355
public int compare(Match match1, Match match2) {
360-
return comparator.compare(match1.mapping, match2.mapping);
356+
return this.comparator.compare(match1.mapping, match2.mapping);
361357
}
362358
}
363-
364-
}
359+
360+
}

0 commit comments

Comments
 (0)