Spring MVC @PathVariable가 잘림
정보에 대한 RESTful 액세스를 제공하는 컨트롤러가 있습니다.
@RequestMapping(method = RequestMethod.GET, value = Routes.BLAH_GET + "/{blahName}")
public ModelAndView getBlah(@PathVariable String blahName, HttpServletRequest request,
HttpServletResponse response) {
내가 겪고있는 문제는 특수 문자가있는 경로 변수로 서버를 치면 잘립니다. 예를 들면 다음과 같습니다. http : // localhost : 8080 / blah-server / blah / get / blah2010.08.19-02 : 25 : 47
blahName 매개 변수는 blah2010.08입니다.
그러나 request.getRequestURI () 호출에는 전달 된 모든 정보가 포함됩니다.
Spring이 @PathVariable을 자르지 못하게하는 방법에 대한 아이디어가 있습니까?
@RequestMapping
인수에 대한 정규식을 시도하십시오 .
RequestMapping(method = RequestMethod.GET, value = Routes.BLAH_GET + "/{blahName:.+}")
이것은 아마도 SPR-6164 와 밀접한 관련이 있습니다. 간단히 말해, 프레임 워크는 URI 해석에 스마트를 적용하여 파일 확장자라고 생각하는 것을 제거하려고합니다. 이것은 파일 확장자 라고 생각하기 때문에 blah2010.08.19-02:25:47
로 바뀌는 효과가 있습니다.blah2010.08
.19-02:25:47
연결된 문제에 설명 된대로 DefaultAnnotationHandlerMapping
앱 컨텍스트에서 고유 한 Bean 을 선언 하고 해당 useDefaultSuffixPattern
속성을로 설정 하여이 동작을 비활성화 할 수 있습니다 false
. 이것은 기본 동작을 무시하고 데이터를 희롱하는 것을 중지합니다.
봄의 마지막 점 뒤에 아무것도 같은 파일 확장자를 것을 고려 .json
하거나 .xml
당신의 매개 변수를 검색을 절단.
그래서 당신이 가지고 있다면 /{blahName}
:
/param
,/param.json
,/param.xml
또는/param.anything
값으로 될 것이다 PARAMparam
/param.value.json
,/param.value.xml
또는/param.value.anything
값으로 될 것이다 PARAMparam.value
매핑을 /{blahName:.+}
제안대로 변경 하면 마지막 점을 포함한 점이 매개 변수의 일부로 간주됩니다.
/param
가치가있는 매개 변수가됩니다param
/param.json
가치가있는 매개 변수가됩니다param.json
/param.xml
가치가있는 매개 변수가됩니다param.xml
/param.anything
가치가있는 매개 변수가됩니다param.anything
/param.value.json
가치가있는 매개 변수가됩니다param.value.json
- ...
확장 인식을 신경 쓰지 않으면 mvc:annotation-driven
automagic 을 재정 의하여 확장 인식을 비활성화 할 수 있습니다 .
<bean id="handlerMapping"
class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping">
<property name="contentNegotiationManager" ref="contentNegotiationManager"/>
<property name="useSuffixPatternMatch" value="false"/>
</bean>
따라서 다시 한 번 /{blahName}
:
/param
,/param.json
,/param.xml
또는/param.anything
값으로 될 것이다 PARAMparam
/param.value.json
,/param.value.xml
또는/param.value.anything
값으로 될 것이다 PARAMparam.value
참고 : 기본 구성과의 차이점은와 같은 매핑이있는 경우에만 표시됩니다 /something.{blahName}
. Resthub 프로젝트 문제를 참조하십시오 .
확장 관리를 유지하려면 Spring 3.2부터 suffixPattern 인식을 활성화하지만 등록 된 확장으로 제한하기 위해 RequestMappingHandlerMapping Bean의 useRegisteredSuffixPatternMatch 특성을 설정할 수도 있습니다.
여기에 json 및 xml 확장자 만 정의하십시오.
<bean id="handlerMapping"
class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping">
<property name="contentNegotiationManager" ref="contentNegotiationManager"/>
<property name="useRegisteredSuffixPatternMatch" value="true"/>
</bean>
<bean id="contentNegotiationManager" class="org.springframework.web.accept.ContentNegotiationManagerFactoryBean">
<property name="favorPathExtension" value="false"/>
<property name="favorParameter" value="true"/>
<property name="mediaTypes">
<value>
json=application/json
xml=application/xml
</value>
</property>
</bean>
mvc : annotation-driven은 이제 customN을 제공하기 위해 contentNegotiation 옵션을 허용하지만 RequestMappingHandlerMapping의 특성을 true (기본값 false)로 변경해야합니다 ( https://jira.springsource.org/browse/SPR-7632). ).
이러한 이유로 여전히 모든 mvc : annotation-driven 구성을 대체해야합니다. 사용자 정의 RequestMappingHandlerMapping을 요청하기 위해 Spring 티켓을 열었습니다 ( https://jira.springsource.org/browse/SPR-11253) . 관심이 있으시면 투표하십시오.
재정의하는 동안 사용자 지정 실행 관리 재정의도 고려해야합니다. 그렇지 않으면 모든 사용자 지정 예외 매핑이 실패합니다. messageCoverters를 목록 Bean과 함께 재사용해야합니다.
<bean id="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean" />
<bean id="conversionService" class="org.springframework.format.support.FormattingConversionServiceFactoryBean" />
<util:list id="messageConverters">
<bean class="your.custom.message.converter.IfAny"></bean>
<bean class="org.springframework.http.converter.ByteArrayHttpMessageConverter"></bean>
<bean class="org.springframework.http.converter.StringHttpMessageConverter"></bean>
<bean class="org.springframework.http.converter.ResourceHttpMessageConverter"></bean>
<bean class="org.springframework.http.converter.xml.SourceHttpMessageConverter"></bean>
<bean class="org.springframework.http.converter.xml.XmlAwareFormHttpMessageConverter"></bean>
<bean class="org.springframework.http.converter.xml.Jaxb2RootElementHttpMessageConverter"></bean>
<bean class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter"></bean>
</util:list>
<bean name="exceptionHandlerExceptionResolver"
class="org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver">
<property name="order" value="0"/>
<property name="messageConverters" ref="messageConverters"/>
</bean>
<bean name="handlerAdapter"
class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter">
<property name="webBindingInitializer">
<bean class="org.springframework.web.bind.support.ConfigurableWebBindingInitializer">
<property name="conversionService" ref="conversionService" />
<property name="validator" ref="validator" />
</bean>
</property>
<property name="messageConverters" ref="messageConverters"/>
</bean>
<bean id="handlerMapping"
class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping">
</bean>
오픈 소스 프로젝트 인 Resthub 에서 이러한 주제에 대한 일련의 테스트를 구현했습니다. https://github.com/resthub/resthub-spring-stack/pull/219/files 및 https : //를 참조 하십시오 . github.com/resthub/resthub-spring-stack/issues/217
마지막 점 뒤의 모든 것은 파일 확장자로 해석되며 기본적으로 잘립니다.
귀하의 스프링 구성 XML에서는 추가 할 수 있습니다 DefaultAnnotationHandlerMapping
및 설정 useDefaultSuffixPattern
에 false
(기본값은 true
).
따라서 스프링 XML을 열거 mvc-config.xml
나 호출하십시오.
<bean class="org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMapping">
<property name="useDefaultSuffixPattern" value="false" />
</bean>
이제 당신의 @PathVariable
blahName
(그리고 다른 모든 것들도) 모든 점을 포함한 성명을 포함해야합니다.
또한 같은 문제가 발생하여 속성을 false로 설정해도 도움이되지 않았습니다. 그러나 API는 다음 과 같이 말합니다 .
".xxx"접미사를 포함하거나 "/"로 끝나는 경로는 이미 기본 접미사 패턴을 사용하여 변환되지 않습니다.
RESTful URL에 "/ end"를 추가하려고했는데 문제가 해결되었습니다. 나는 해결책에 만족하지 않지만 효과가 있었다.
BTW, 나는 스프링 디자이너가이 "기능"을 추가 한 다음 기본적으로 켰을 때 무슨 생각을했는지 모르겠다. IMHO, 제거해야합니다.
올바른 Java 구성 클래스 사용
@Configuration
@EnableWebMvc
public class WebConfig extends WebMvcConfigurerAdapter
{
@Override
public void configureContentNegotiation(ContentNegotiationConfigurer configurer)
{
configurer.favorPathExtension(false);
}
@Override
public void configurePathMatch(PathMatchConfigurer configurer)
{
configurer.setUseSuffixPatternMatch(false);
}
}
이 핵으로 해결
1) 아래와 같이 @PathVariable에 HttpServletRequest를 추가했습니다.
@PathVariable("requestParam") String requestParam, HttpServletRequest request) throws Exception {
2) 요청에서 URL을 직접 가져옵니다 (이 수준에서는 잘리지 않음)
request.getPathInfo()
점 (.)이있는 Spring MVC @PathVariable이 잘립니다.
방금 이것에 부딪 쳤으며 여기의 솔루션은 일반적으로 예상대로 작동하지 않았습니다.
SpEL 표현식과 여러 매핑을 사용하는 것이 좋습니다.
@RequestMapping(method = RequestMethod.GET,
value = {Routes.BLAH_GET + "/{blahName:.+}",
Routes.BLAH_GET + "/{blahName}/"})
파일 확장자 문제는 매개 변수가 URL의 마지막 부분에있는 경우에만 존재합니다. 변화
@RequestMapping(method = RequestMethod.GET, value = Routes.BLAH_GET + "/{blahName}")
에
@RequestMapping(
method = RequestMethod.GET, value = Routes.BLAH_GET + "/{blahName}/safe")
그리고 모든 것이 다시 잘 될 것입니다.
요청이 전송되는 주소를 편집 할 수있는 경우 간단한 슬래시를 추가하고 @RequestMapping
값 에 슬래시를 추가하면됩니다 .
/path/{variable}/
매핑은 다음과 같습니다.
RequestMapping(method = RequestMethod.GET, value = Routes.BLAH_GET + "/{blahName}/")
도트 (.)가있는 Spring MVC @PathVariable 도 잘립니다 .
//in your xml dispatcher add this property to your default annotation mapper bean as follow
<bean class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping">
<property name="alwaysUseFullPath" value="true"></property>
</bean>
":. +"를 추가하면 외부 괄호를 제거 할 때까지는 효과가 없었습니다.
value = {"/username/{id:.+}"}
작동하지 않았다
value = "/username/{id:.+}"
공장
누군가를 도왔기를 바랍니다.
자르지 않도록하는 Java 기반 구성 솔루션 (더 이상 사용되지 않는 클래스 사용) :
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurationSupport;
import org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping;
@Configuration
public class PolRepWebConfig extends WebMvcConfigurationSupport {
@Override
@Bean
public RequestMappingHandlerMapping requestMappingHandlerMapping() {
final RequestMappingHandlerMapping handlerMapping = super
.requestMappingHandlerMapping();
// disable the truncation after .
handlerMapping.setUseSuffixPatternMatch(false);
// disable the truncation after ;
handlerMapping.setRemoveSemicolonContent(false);
return handlerMapping;
}
}
출처 : http://www.javacodegeeks.com/2013/01/spring-mvc-customizing-requestmappinghandlermapping.html
최신 정보:
위의 접근법을 사용할 때 스프링 부트 자동 구성에 문제가 있음을 깨달았습니다 (일부 자동 구성은 효과적이지 않습니다).
대신, 나는 그 BeanPostProcessor
접근법 을 사용하기 시작했다 . 더 잘 작동하는 것 같습니다.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.config.BeanPostProcessor;
public class MyBeanPostProcessor implements BeanPostProcessor {
private static final Logger logger = LoggerFactory
.getLogger(MyBeanPostProcessor.class);
@Override
public Object postProcessAfterInitialization(Object bean, String beanName)
throws BeansException {
return bean;
}
@Override
public Object postProcessBeforeInitialization(Object bean, String beanName)
throws BeansException {
if (bean instanceof RequestMappingHandlerMapping) {
setRemoveSemicolonContent((RequestMappingHandlerMapping) bean,
beanName);
setUseSuffixPatternMatch((RequestMappingHandlerMapping) bean,
beanName);
}
return bean;
}
private void setRemoveSemicolonContent(
RequestMappingHandlerMapping requestMappingHandlerMapping,
String beanName) {
logger.info(
"Setting 'RemoveSemicolonContent' on 'RequestMappingHandlerMapping'-bean to false. Bean name: {}",
beanName);
requestMappingHandlerMapping.setRemoveSemicolonContent(false);
}
private void setUseSuffixPatternMatch(
RequestMappingHandlerMapping requestMappingHandlerMapping,
String beanName) {
logger.info(
"Setting 'UseSuffixPatternMatch' on 'RequestMappingHandlerMapping'-bean to false. Bean name: {}",
beanName);
requestMappingHandlerMapping.setUseSuffixPatternMatch(false);
}
}
영감을 얻은 사이트 : http://ronaldxq.blogspot.com/2014/10/spring-mvc-setting-alwaysusefullpath-on.html
텍스트가 기본 확장자와 일치하지 않는 경우 아래 코드를 사용할 수 있습니다.
@Configuration
@EnableWebMvc
public class WebConfig extends WebMvcConfigurerAdapter {
@Override
public void configurePathMatch(PathMatchConfigurer configurer) {
configurer.setUseRegisteredSuffixPatternMatch(true);
}
}
Spring MVC @PathVariable이 잘리지 않도록하는 가장 좋은 해결책은 경로 변수 끝에 슬래시를 추가하는 것입니다.
예를 들면 다음과 같습니다.
@RequestMapping(value ="/email/{email}/")
따라서 요청은 다음과 같습니다.
http://localhost:8080/api/email/test@test.com/
The problem that you are facing is due to spring interpreting the last part of the uri after the dot (.) as a file extension like .json or .xml . So when spring tries to resolve the path variable it simply truncates the rest of the data after it encounters a dot (.) at the end of the uri. Note: also this happens only if you keep the path variable at the end of the uri.
For example consider uri : https://localhost/example/gallery.df/link.ar
@RestController
public class CustomController {
@GetMapping("/example/{firstValue}/{secondValue}")
public void example(@PathVariable("firstValue") String firstValue,
@PathVariable("secondValue") String secondValue) {
// ...
}
}
In the above url firstValue = "gallery.df" and secondValue="link" , the last bit after the . gets truncated when the path variable gets interpreted.
So, to prevent this there is two possible ways:
1.) Using a regexp mapping
Use a regex at the end part of mapping
@GetMapping("/example/{firstValue}/{secondValue:.+}")
public void example(
@PathVariable("firstValue") String firstValue,
@PathVariable("secondValue") String secondValue) {
//...
}
By using + , we indicate any value after the dot will also be part of the path variable.
2.) Adding a slash at the end of our @PathVariable
@GetMapping("/example/{firstValue}/{secondValue}/")
public void example(
@PathVariable("firstValue") String firstValue,
@PathVariable("secondValue") String secondValue) {
//...
}
This will enclose our second variable protecting it from Spring’s default behavior.
3) By overriding Spring's default webmvc configuration
Spring provides ways to override the default configurations that gets imported by using the annotations @EnableWebMvc.We can customize the Spring MVC configuration by declaring our own DefaultAnnotationHandlerMapping bean in the application context and setting its useDefaultSuffixPattern property to false. Example:
@Configuration
public class CustomWebConfiguration extends WebMvcConfigurationSupport {
@Bean
public RequestMappingHandlerMapping
requestMappingHandlerMapping() {
RequestMappingHandlerMapping handlerMapping
= super.requestMappingHandlerMapping();
handlerMapping.setUseSuffixPatternMatch(false);
return handlerMapping;
}
}
Keep in mind that overriding this default configuration, affects all urls.
Note : here we are extending the WebMvcConfigurationSupport class to override the default methods. There is one more way to override the deault configurations by implementing the WebMvcConfigurer interface. For more details on this read : https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/web/servlet/config/annotation/EnableWebMvc.html
참고URL : https://stackoverflow.com/questions/3526523/spring-mvc-pathvariable-getting-truncated
'Programming' 카테고리의 다른 글
클래스 선택기와 속성 선택기를 jQuery와 결합 (0) | 2020.06.27 |
---|---|
Java 8 스트림과 RxJava 옵저버 블의 차이점 (0) | 2020.06.27 |
C ++ 14 자동 반환 유형 공제는 언제 사용해야합니까? (0) | 2020.06.24 |
Java 용 SQL 파서 라이브러리 (0) | 2020.06.24 |
영어 단어 데이터베이스를 얻는 방법? (0) | 2020.06.24 |