Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
爱吃血肠
spring-framework
提交
a30ab30e
S
spring-framework
项目概览
爱吃血肠
/
spring-framework
通知
1
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
S
spring-framework
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
a30ab30e
编写于
4月 25, 2016
作者:
R
Rossen Stoyanchev
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Introduce HandlerMapping introspection API
Issue: SPR-14321
上级
a25c43f6
变更
7
隐藏空白更改
内联
并排
Showing
7 changed file
with
554 addition
and
11 deletion
+554
-11
spring-webmvc/src/main/java/org/springframework/web/servlet/handler/AbstractHandlerMapping.java
...framework/web/servlet/handler/AbstractHandlerMapping.java
+19
-9
spring-webmvc/src/main/java/org/springframework/web/servlet/handler/AbstractUrlHandlerMapping.java
...mework/web/servlet/handler/AbstractUrlHandlerMapping.java
+18
-1
spring-webmvc/src/main/java/org/springframework/web/servlet/mvc/method/annotation/RequestMappingHandlerMapping.java
...t/mvc/method/annotation/RequestMappingHandlerMapping.java
+17
-1
spring-webmvc/src/main/java/org/springframework/web/servlet/support/HandlerMappingIntrospector.java
...ework/web/servlet/support/HandlerMappingIntrospector.java
+192
-0
spring-webmvc/src/main/java/org/springframework/web/servlet/support/MatchableHandlerMapping.java
...ramework/web/servlet/support/MatchableHandlerMapping.java
+41
-0
spring-webmvc/src/main/java/org/springframework/web/servlet/support/RequestMatchResult.java
...ringframework/web/servlet/support/RequestMatchResult.java
+77
-0
spring-webmvc/src/test/java/org/springframework/web/servlet/support/HandlerMappingIntrospectorTests.java
.../web/servlet/support/HandlerMappingIntrospectorTests.java
+190
-0
未找到文件。
spring-webmvc/src/main/java/org/springframework/web/servlet/handler/AbstractHandlerMapping.java
浏览文件 @
a30ab30e
...
...
@@ -27,21 +27,21 @@ import javax.servlet.http.HttpServletResponse;
import
org.springframework.beans.BeansException
;
import
org.springframework.beans.factory.BeanFactoryUtils
;
import
org.springframework.core.Ordered
;
import
org.springframework.web.HttpRequestHandler
;
import
org.springframework.web.cors.UrlBasedCorsConfigurationSource
;
import
org.springframework.web.cors.CorsProcessor
;
import
org.springframework.web.cors.CorsConfiguration
;
import
org.springframework.web.cors.CorsConfigurationSource
;
import
org.springframework.util.AntPathMatcher
;
import
org.springframework.util.Assert
;
import
org.springframework.util.PathMatcher
;
import
org.springframework.web.HttpRequestHandler
;
import
org.springframework.web.context.request.WebRequestInterceptor
;
import
org.springframework.web.context.support.WebApplicationObjectSupport
;
import
org.springframework.web.cors.CorsConfiguration
;
import
org.springframework.web.cors.CorsConfigurationSource
;
import
org.springframework.web.cors.CorsProcessor
;
import
org.springframework.web.cors.CorsUtils
;
import
org.springframework.web.cors.DefaultCorsProcessor
;
import
org.springframework.web.cors.UrlBasedCorsConfigurationSource
;
import
org.springframework.web.servlet.HandlerExecutionChain
;
import
org.springframework.web.servlet.HandlerInterceptor
;
import
org.springframework.web.servlet.HandlerMapping
;
import
org.springframework.web.cors.DefaultCorsProcessor
;
import
org.springframework.web.cors.CorsUtils
;
import
org.springframework.web.util.UrlPathHelper
;
/**
...
...
@@ -471,7 +471,7 @@ public abstract class AbstractHandlerMapping extends WebApplicationObjectSupport
}
private
class
PreFlightHandler
implements
HttpRequestHandler
{
private
class
PreFlightHandler
implements
HttpRequestHandler
,
CorsConfigurationSource
{
private
final
CorsConfiguration
config
;
...
...
@@ -485,10 +485,15 @@ public abstract class AbstractHandlerMapping extends WebApplicationObjectSupport
corsProcessor
.
processRequest
(
this
.
config
,
request
,
response
);
}
@Override
public
CorsConfiguration
getCorsConfiguration
(
HttpServletRequest
request
)
{
return
this
.
config
;
}
}
private
class
CorsInterceptor
extends
HandlerInterceptorAdapter
{
private
class
CorsInterceptor
extends
HandlerInterceptorAdapter
implements
CorsConfigurationSource
{
private
final
CorsConfiguration
config
;
...
...
@@ -502,6 +507,11 @@ public abstract class AbstractHandlerMapping extends WebApplicationObjectSupport
return
corsProcessor
.
processRequest
(
this
.
config
,
request
,
response
);
}
@Override
public
CorsConfiguration
getCorsConfiguration
(
HttpServletRequest
request
)
{
return
this
.
config
;
}
}
}
spring-webmvc/src/main/java/org/springframework/web/servlet/handler/AbstractUrlHandlerMapping.java
浏览文件 @
a30ab30e
...
...
@@ -30,6 +30,8 @@ import org.springframework.util.Assert;
import
org.springframework.util.CollectionUtils
;
import
org.springframework.web.servlet.HandlerExecutionChain
;
import
org.springframework.web.servlet.HandlerMapping
;
import
org.springframework.web.servlet.support.MatchableHandlerMapping
;
import
org.springframework.web.servlet.support.RequestMatchResult
;
/**
* Abstract base class for URL-mapped {@link org.springframework.web.servlet.HandlerMapping}
...
...
@@ -50,7 +52,8 @@ import org.springframework.web.servlet.HandlerMapping;
* @author Arjen Poutsma
* @since 16.04.2003
*/
public
abstract
class
AbstractUrlHandlerMapping
extends
AbstractHandlerMapping
{
public
abstract
class
AbstractUrlHandlerMapping
extends
AbstractHandlerMapping
implements
MatchableHandlerMapping
{
private
Object
rootHandler
;
...
...
@@ -279,6 +282,20 @@ public abstract class AbstractUrlHandlerMapping extends AbstractHandlerMapping {
request
.
setAttribute
(
HandlerMapping
.
URI_TEMPLATE_VARIABLES_ATTRIBUTE
,
uriTemplateVariables
);
}
@Override
public
RequestMatchResult
match
(
HttpServletRequest
request
,
String
pattern
)
{
String
lookupPath
=
getUrlPathHelper
().
getLookupPathForRequest
(
request
);
if
(
getPathMatcher
().
match
(
pattern
,
lookupPath
))
{
return
new
RequestMatchResult
(
pattern
,
lookupPath
,
getPathMatcher
());
}
else
if
(
useTrailingSlashMatch
())
{
if
(!
pattern
.
endsWith
(
"/"
)
&&
getPathMatcher
().
match
(
pattern
+
"/"
,
lookupPath
))
{
return
new
RequestMatchResult
(
pattern
+
"/"
,
lookupPath
,
getPathMatcher
());
}
}
return
null
;
}
/**
* Register the specified handler for the given URL paths.
* @param urlPaths the URLs that the bean should be mapped to
...
...
spring-webmvc/src/main/java/org/springframework/web/servlet/mvc/method/annotation/RequestMappingHandlerMapping.java
浏览文件 @
a30ab30e
...
...
@@ -20,6 +20,8 @@ import java.lang.reflect.AnnotatedElement;
import
java.lang.reflect.Method
;
import
java.util.Arrays
;
import
java.util.List
;
import
java.util.Set
;
import
javax.servlet.http.HttpServletRequest
;
import
org.springframework.context.EmbeddedValueResolverAware
;
import
org.springframework.core.annotation.AnnotatedElementUtils
;
...
...
@@ -38,6 +40,8 @@ import org.springframework.web.servlet.mvc.condition.CompositeRequestCondition;
import
org.springframework.web.servlet.mvc.condition.RequestCondition
;
import
org.springframework.web.servlet.mvc.method.RequestMappingInfo
;
import
org.springframework.web.servlet.mvc.method.RequestMappingInfoHandlerMapping
;
import
org.springframework.web.servlet.support.MatchableHandlerMapping
;
import
org.springframework.web.servlet.support.RequestMatchResult
;
/**
* Creates {@link RequestMappingInfo} instances from type and method-level
...
...
@@ -50,7 +54,7 @@ import org.springframework.web.servlet.mvc.method.RequestMappingInfoHandlerMappi
* @since 3.1
*/
public
class
RequestMappingHandlerMapping
extends
RequestMappingInfoHandlerMapping
implements
EmbeddedValueResolverAware
{
implements
EmbeddedValueResolverAware
,
MatchableHandlerMapping
{
private
boolean
useSuffixPatternMatch
=
true
;
...
...
@@ -274,6 +278,18 @@ public class RequestMappingHandlerMapping extends RequestMappingInfoHandlerMappi
}
}
@Override
public
RequestMatchResult
match
(
HttpServletRequest
request
,
String
pattern
)
{
RequestMappingInfo
info
=
RequestMappingInfo
.
paths
(
pattern
).
options
(
this
.
config
).
build
();
RequestMappingInfo
matchingInfo
=
info
.
getMatchingCondition
(
request
);
if
(
matchingInfo
==
null
)
{
return
null
;
}
Set
<
String
>
patterns
=
matchingInfo
.
getPatternsCondition
().
getPatterns
();
String
lookupPath
=
getUrlPathHelper
().
getLookupPathForRequest
(
request
);
return
new
RequestMatchResult
(
patterns
.
iterator
().
next
(),
lookupPath
,
getPathMatcher
());
}
@Override
protected
CorsConfiguration
initCorsConfiguration
(
Object
handler
,
Method
method
,
RequestMappingInfo
mappingInfo
)
{
HandlerMethod
handlerMethod
=
createHandlerMethod
(
handler
,
method
);
...
...
spring-webmvc/src/main/java/org/springframework/web/servlet/support/HandlerMappingIntrospector.java
0 → 100644
浏览文件 @
a30ab30e
/*
* Copyright 2002-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package
org.springframework.web.servlet.support
;
import
java.io.IOException
;
import
java.util.ArrayList
;
import
java.util.List
;
import
java.util.Map
;
import
java.util.Properties
;
import
javax.servlet.http.HttpServletRequest
;
import
javax.servlet.http.HttpServletRequestWrapper
;
import
org.springframework.beans.factory.BeanFactoryUtils
;
import
org.springframework.context.ApplicationContext
;
import
org.springframework.core.annotation.AnnotationAwareOrderComparator
;
import
org.springframework.core.io.ClassPathResource
;
import
org.springframework.core.io.Resource
;
import
org.springframework.core.io.support.PropertiesLoaderUtils
;
import
org.springframework.util.ClassUtils
;
import
org.springframework.util.StringUtils
;
import
org.springframework.web.cors.CorsConfiguration
;
import
org.springframework.web.cors.CorsConfigurationSource
;
import
org.springframework.web.servlet.DispatcherServlet
;
import
org.springframework.web.servlet.HandlerExecutionChain
;
import
org.springframework.web.servlet.HandlerInterceptor
;
import
org.springframework.web.servlet.HandlerMapping
;
/**
* Helper class to get information from the {@code HandlerMapping} that would
* serve a specific request.
*
* <p>Provides the following methods:
* <ul>
* <li>{@link #getMatchableHandlerMapping} -- obtain a {@code HandlerMapping}
* to check request-matching criteria against.
* <li>{@link #getCorsConfiguration} -- obtain the CORS configuration for the
* request.
* </ul>
*
* @author Rossen Stoyanchev
* @since 4.3
*/
public
class
HandlerMappingIntrospector
implements
CorsConfigurationSource
{
private
final
List
<
HandlerMapping
>
handlerMappings
;
/**
* Constructor that detects the configured {@code HandlerMapping}s in the
* given {@code ApplicationContext} or falling back on
* "DispatcherServlet.properties" like the {@code DispatcherServlet}.
*/
public
HandlerMappingIntrospector
(
ApplicationContext
context
)
{
this
.
handlerMappings
=
initHandlerMappings
(
context
);
}
private
static
List
<
HandlerMapping
>
initHandlerMappings
(
ApplicationContext
context
)
{
Map
<
String
,
HandlerMapping
>
beans
=
BeanFactoryUtils
.
beansOfTypeIncludingAncestors
(
context
,
HandlerMapping
.
class
,
true
,
false
);
if
(!
beans
.
isEmpty
())
{
List
<
HandlerMapping
>
mappings
=
new
ArrayList
<
HandlerMapping
>(
beans
.
values
());
AnnotationAwareOrderComparator
.
sort
(
mappings
);
return
mappings
;
}
return
initDefaultHandlerMappings
(
context
);
}
private
static
List
<
HandlerMapping
>
initDefaultHandlerMappings
(
ApplicationContext
context
)
{
Properties
props
;
String
path
=
"DispatcherServlet.properties"
;
try
{
Resource
resource
=
new
ClassPathResource
(
path
,
DispatcherServlet
.
class
);
props
=
PropertiesLoaderUtils
.
loadProperties
(
resource
);
}
catch
(
IOException
ex
)
{
throw
new
IllegalStateException
(
"Could not load '"
+
path
+
"': "
+
ex
.
getMessage
());
}
String
value
=
props
.
getProperty
(
HandlerMapping
.
class
.
getName
());
String
[]
names
=
StringUtils
.
commaDelimitedListToStringArray
(
value
);
List
<
HandlerMapping
>
result
=
new
ArrayList
<
HandlerMapping
>(
names
.
length
);
for
(
String
name
:
names
)
{
try
{
Class
<?>
clazz
=
ClassUtils
.
forName
(
name
,
DispatcherServlet
.
class
.
getClassLoader
());
Object
mapping
=
context
.
getAutowireCapableBeanFactory
().
createBean
(
clazz
);
result
.
add
((
HandlerMapping
)
mapping
);
}
catch
(
ClassNotFoundException
ex
)
{
throw
new
IllegalStateException
(
"Could not find default HandlerMapping ["
+
name
+
"]"
);
}
}
return
result
;
}
/**
* Return the configured HandlerMapping's.
*/
public
List
<
HandlerMapping
>
getHandlerMappings
()
{
return
this
.
handlerMappings
;
}
/**
* Find the {@link HandlerMapping} that would handle the given request and
* return it as a {@link MatchableHandlerMapping} that can be used to
* test request-matching criteria. If the matching HandlerMapping is not an
* instance of {@link MatchableHandlerMapping}, an IllegalStateException is
* raised.
*
* @param request the current request
* @return the resolved matcher, or {@code null}
* @throws Exception if any of the HandlerMapping's raise an exception
*/
public
MatchableHandlerMapping
getMatchableHandlerMapping
(
HttpServletRequest
request
)
throws
Exception
{
HttpServletRequest
wrapper
=
new
RequestAttributeChangeIgnoringWrapper
(
request
);
for
(
HandlerMapping
handlerMapping
:
this
.
handlerMappings
)
{
Object
handler
=
handlerMapping
.
getHandler
(
wrapper
);
if
(
handler
==
null
)
{
continue
;
}
if
(
handlerMapping
instanceof
MatchableHandlerMapping
)
{
return
((
MatchableHandlerMapping
)
handlerMapping
);
}
throw
new
IllegalStateException
(
"HandlerMapping is not a MatchableHandlerMapping"
);
}
return
null
;
}
@Override
public
CorsConfiguration
getCorsConfiguration
(
HttpServletRequest
request
)
{
HttpServletRequest
wrapper
=
new
RequestAttributeChangeIgnoringWrapper
(
request
);
for
(
HandlerMapping
handlerMapping
:
this
.
handlerMappings
)
{
HandlerExecutionChain
handler
=
null
;
try
{
handler
=
handlerMapping
.
getHandler
(
wrapper
);
}
catch
(
Exception
ex
)
{
// Ignore
}
if
(
handler
==
null
)
{
continue
;
}
if
(
handler
.
getInterceptors
()
!=
null
)
{
for
(
HandlerInterceptor
interceptor
:
handler
.
getInterceptors
())
{
if
(
interceptor
instanceof
CorsConfigurationSource
)
{
return
((
CorsConfigurationSource
)
interceptor
).
getCorsConfiguration
(
wrapper
);
}
}
}
if
(
handler
.
getHandler
()
instanceof
CorsConfigurationSource
)
{
return
((
CorsConfigurationSource
)
handler
.
getHandler
()).
getCorsConfiguration
(
wrapper
);
}
}
return
null
;
}
/**
* Request wrapper that ignores request attribute changes.
*/
private
static
class
RequestAttributeChangeIgnoringWrapper
extends
HttpServletRequestWrapper
{
private
RequestAttributeChangeIgnoringWrapper
(
HttpServletRequest
request
)
{
super
(
request
);
}
@Override
public
void
setAttribute
(
String
name
,
Object
value
)
{
// Ignore attribute change
}
}
}
\ No newline at end of file
spring-webmvc/src/main/java/org/springframework/web/servlet/support/MatchableHandlerMapping.java
0 → 100644
浏览文件 @
a30ab30e
/*
* Copyright 2002-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package
org.springframework.web.servlet.support
;
import
javax.servlet.http.HttpServletRequest
;
import
org.springframework.web.servlet.HandlerMapping
;
/**
* Additional interface that a {@link HandlerMapping} can implement to expose
* a request matching API aligned with its internal request matching
* configuration and implementation.
*
* @author Rossen Stoyanchev
* @since 4.3
* @see HandlerMappingIntrospector
*/
public
interface
MatchableHandlerMapping
{
/**
* Whether the given request matches the request criteria.
* @param request the current request
* @param pattern the pattern to match
* @return the result from request matching or {@code null}
*/
RequestMatchResult
match
(
HttpServletRequest
request
,
String
pattern
);
}
spring-webmvc/src/main/java/org/springframework/web/servlet/support/RequestMatchResult.java
0 → 100644
浏览文件 @
a30ab30e
/*
* Copyright 2002-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package
org.springframework.web.servlet.support
;
import
java.util.Collections
;
import
java.util.Map
;
import
org.springframework.util.Assert
;
import
org.springframework.util.PathMatcher
;
/**
* Container for the result from request pattern matching via
* {@link MatchableHandlerMapping} with a method to further extract URI template
* variables from the pattern.
*
* @author Rossen Stoyanchev
* @since 4.3
*/
public
class
RequestMatchResult
{
private
final
String
matchingPattern
;
private
final
String
lookupPath
;
private
final
PathMatcher
pathMatcher
;
/**
* Create an instance with a matching pattern.
* @param matchingPattern the matching pattern, possibly not the same as the
* input pattern, e.g. inputPattern="/foo" and matchingPattern="/foo/".
* @param lookupPath the lookup path extracted from the request
* @param pathMatcher the PathMatcher used
*/
public
RequestMatchResult
(
String
matchingPattern
,
String
lookupPath
,
PathMatcher
pathMatcher
)
{
Assert
.
hasText
(
matchingPattern
,
"'matchingPattern' is required"
);
Assert
.
hasText
(
lookupPath
,
"'lookupPath' is required"
);
Assert
.
notNull
(
pathMatcher
,
"'pathMatcher' is required"
);
this
.
matchingPattern
=
matchingPattern
;
this
.
lookupPath
=
lookupPath
;
this
.
pathMatcher
=
pathMatcher
;
}
/**
* Whether the pattern was matched to the request.
*/
public
boolean
isMatch
()
{
return
(
this
.
matchingPattern
!=
null
);
}
/**
* Extract URI template variables from the matching pattern as defined in
* {@link PathMatcher#extractUriTemplateVariables}.
* @return a map with URI template variables
*/
public
Map
<
String
,
String
>
extractUriTemplateVariables
()
{
if
(!
isMatch
())
{
return
Collections
.<
String
,
String
>
emptyMap
();
}
return
this
.
pathMatcher
.
extractUriTemplateVariables
(
this
.
matchingPattern
,
this
.
lookupPath
);
}
}
spring-webmvc/src/test/java/org/springframework/web/servlet/support/HandlerMappingIntrospectorTests.java
0 → 100644
浏览文件 @
a30ab30e
/*
* Copyright 2002-2016 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package
org.springframework.web.servlet.support
;
import
java.util.Arrays
;
import
java.util.Collections
;
import
java.util.List
;
import
javax.servlet.http.HttpServletRequest
;
import
org.junit.Test
;
import
org.springframework.beans.MutablePropertyValues
;
import
org.springframework.context.annotation.Bean
;
import
org.springframework.context.annotation.Configuration
;
import
org.springframework.http.HttpHeaders
;
import
org.springframework.mock.web.test.MockHttpServletRequest
;
import
org.springframework.stereotype.Controller
;
import
org.springframework.web.bind.annotation.CrossOrigin
;
import
org.springframework.web.bind.annotation.PostMapping
;
import
org.springframework.web.context.support.AnnotationConfigWebApplicationContext
;
import
org.springframework.web.context.support.StaticWebApplicationContext
;
import
org.springframework.web.cors.CorsConfiguration
;
import
org.springframework.web.servlet.HandlerExecutionChain
;
import
org.springframework.web.servlet.HandlerMapping
;
import
org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping
;
import
org.springframework.web.servlet.handler.SimpleUrlHandlerMapping
;
import
org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping
;
import
org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping
;
import
static
org
.
junit
.
Assert
.
assertEquals
;
import
static
org
.
junit
.
Assert
.
assertNotNull
;
import
static
org
.
junit
.
Assert
.
assertNull
;
import
static
org
.
springframework
.
web
.
servlet
.
HandlerMapping
.
BEST_MATCHING_PATTERN_ATTRIBUTE
;
/**
* Unit tests for {@link HandlerMappingIntrospector}.
* @author Rossen Stoyanchev
*/
public
class
HandlerMappingIntrospectorTests
{
@Test
public
void
detectHandlerMappings
()
throws
Exception
{
StaticWebApplicationContext
cxt
=
new
StaticWebApplicationContext
();
cxt
.
registerSingleton
(
"hmA"
,
SimpleUrlHandlerMapping
.
class
);
cxt
.
registerSingleton
(
"hmB"
,
SimpleUrlHandlerMapping
.
class
);
cxt
.
registerSingleton
(
"hmC"
,
SimpleUrlHandlerMapping
.
class
);
cxt
.
refresh
();
List
<?>
expected
=
Arrays
.
asList
(
cxt
.
getBean
(
"hmA"
),
cxt
.
getBean
(
"hmB"
),
cxt
.
getBean
(
"hmC"
));
List
<
HandlerMapping
>
actual
=
new
HandlerMappingIntrospector
(
cxt
).
getHandlerMappings
();
assertEquals
(
expected
,
actual
);
}
@Test
public
void
detectHandlerMappingsOrdered
()
throws
Exception
{
StaticWebApplicationContext
cxt
=
new
StaticWebApplicationContext
();
MutablePropertyValues
pvs
=
new
MutablePropertyValues
(
Collections
.
singletonMap
(
"order"
,
"3"
));
cxt
.
registerSingleton
(
"hmA"
,
SimpleUrlHandlerMapping
.
class
,
pvs
);
pvs
=
new
MutablePropertyValues
(
Collections
.
singletonMap
(
"order"
,
"2"
));
cxt
.
registerSingleton
(
"hmB"
,
SimpleUrlHandlerMapping
.
class
,
pvs
);
pvs
=
new
MutablePropertyValues
(
Collections
.
singletonMap
(
"order"
,
"1"
));
cxt
.
registerSingleton
(
"hmC"
,
SimpleUrlHandlerMapping
.
class
,
pvs
);
cxt
.
refresh
();
List
<?>
expected
=
Arrays
.
asList
(
cxt
.
getBean
(
"hmC"
),
cxt
.
getBean
(
"hmB"
),
cxt
.
getBean
(
"hmA"
));
List
<
HandlerMapping
>
actual
=
new
HandlerMappingIntrospector
(
cxt
).
getHandlerMappings
();
assertEquals
(
expected
,
actual
);
}
@Test
@SuppressWarnings
(
"deprecation"
)
public
void
defaultHandlerMappings
()
throws
Exception
{
StaticWebApplicationContext
cxt
=
new
StaticWebApplicationContext
();
cxt
.
refresh
();
List
<
HandlerMapping
>
actual
=
new
HandlerMappingIntrospector
(
cxt
).
getHandlerMappings
();
assertEquals
(
2
,
actual
.
size
());
assertEquals
(
BeanNameUrlHandlerMapping
.
class
,
actual
.
get
(
0
).
getClass
());
assertEquals
(
DefaultAnnotationHandlerMapping
.
class
,
actual
.
get
(
1
).
getClass
());
}
@Test
public
void
getMatchable
()
throws
Exception
{
MutablePropertyValues
pvs
=
new
MutablePropertyValues
(
Collections
.
singletonMap
(
"urlMap"
,
Collections
.
singletonMap
(
"/path"
,
new
Object
())));
StaticWebApplicationContext
cxt
=
new
StaticWebApplicationContext
();
cxt
.
registerSingleton
(
"hm"
,
SimpleUrlHandlerMapping
.
class
,
pvs
);
cxt
.
refresh
();
MockHttpServletRequest
request
=
new
MockHttpServletRequest
(
"GET"
,
"/path"
);
MatchableHandlerMapping
hm
=
new
HandlerMappingIntrospector
(
cxt
).
getMatchableHandlerMapping
(
request
);
assertEquals
(
cxt
.
getBean
(
"hm"
),
hm
);
assertNull
(
"Attributes changes not ignored"
,
request
.
getAttribute
(
BEST_MATCHING_PATTERN_ATTRIBUTE
));
}
@Test
(
expected
=
IllegalStateException
.
class
)
public
void
getMatchableWhereHandlerMappingDoesNotImplementMatchableInterface
()
throws
Exception
{
StaticWebApplicationContext
cxt
=
new
StaticWebApplicationContext
();
cxt
.
registerSingleton
(
"hm1"
,
TestHandlerMapping
.
class
);
cxt
.
refresh
();
MockHttpServletRequest
request
=
new
MockHttpServletRequest
();
new
HandlerMappingIntrospector
(
cxt
).
getMatchableHandlerMapping
(
request
);
}
@Test
public
void
getCorsConfigurationPreFlight
()
throws
Exception
{
AnnotationConfigWebApplicationContext
cxt
=
new
AnnotationConfigWebApplicationContext
();
cxt
.
register
(
TestConfig
.
class
);
cxt
.
refresh
();
// PRE-FLIGHT
MockHttpServletRequest
request
=
new
MockHttpServletRequest
(
"OPTIONS"
,
"/path"
);
request
.
addHeader
(
"Origin"
,
"http://localhost:9000"
);
request
.
addHeader
(
HttpHeaders
.
ACCESS_CONTROL_REQUEST_METHOD
,
"POST"
);
CorsConfiguration
corsConfig
=
new
HandlerMappingIntrospector
(
cxt
).
getCorsConfiguration
(
request
);
assertNotNull
(
corsConfig
);
assertEquals
(
Collections
.
singletonList
(
"http://localhost:9000"
),
corsConfig
.
getAllowedOrigins
());
assertEquals
(
Collections
.
singletonList
(
"POST"
),
corsConfig
.
getAllowedMethods
());
}
@Test
public
void
getCorsConfigurationActual
()
throws
Exception
{
AnnotationConfigWebApplicationContext
cxt
=
new
AnnotationConfigWebApplicationContext
();
cxt
.
register
(
TestConfig
.
class
);
cxt
.
refresh
();
MockHttpServletRequest
request
=
new
MockHttpServletRequest
(
"POST"
,
"/path"
);
request
.
addHeader
(
"Origin"
,
"http://localhost:9000"
);
CorsConfiguration
corsConfig
=
new
HandlerMappingIntrospector
(
cxt
).
getCorsConfiguration
(
request
);
assertNotNull
(
corsConfig
);
assertEquals
(
Collections
.
singletonList
(
"http://localhost:9000"
),
corsConfig
.
getAllowedOrigins
());
assertEquals
(
Collections
.
singletonList
(
"POST"
),
corsConfig
.
getAllowedMethods
());
}
private
static
class
TestHandlerMapping
implements
HandlerMapping
{
@Override
public
HandlerExecutionChain
getHandler
(
HttpServletRequest
request
)
throws
Exception
{
return
new
HandlerExecutionChain
(
new
Object
());
}
}
@Configuration
@SuppressWarnings
({
"WeakerAccess"
,
"unused"
})
static
class
TestConfig
{
@Bean
public
RequestMappingHandlerMapping
handlerMapping
()
{
return
new
RequestMappingHandlerMapping
();
}
@Bean
public
TestController
testController
()
{
return
new
TestController
();
}
}
@CrossOrigin
(
"http://localhost:9000"
)
@Controller
private
static
class
TestController
{
@PostMapping
(
"/path"
)
public
void
handle
()
{
}
}
}
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录