Wednesday, January 25, 2017

Spring MVC



http://liubo.loan/2016/12/03/PathVariable%E6%88%AA%E6%96%ADip%E9%97%AE%E9%A2%98/
路径传参ip被截断
@PathVariable出现点号"."时导致路径参数截断获取不全的解决办法
SpringMVC项目中通过下面的URL进行GET请求,ip地址包含多个.号,192.168.1.1 会截为 192.168.1 丢失部分
在@RequestMapping的value中使用SpEL来表示,value中的{ip}换成{ip:.+}。
https://stackoverflow.com/questions/16332092/spring-mvc-pathvariable-with-dot-is-getting-truncated
@GetMapping("/statusByEmail/{email:.+}/")
public String statusByEmail(@PathVariable(value = "email") String email){
  //code
}
http://alanscodingdairy.blogspot.com/2011/10/spring-mvc-responsebody-and-manage.html
List handle(HttpServletResponse response,
@RequestHeader("headerID") String headerString) {
response.setHeader("responseHeaderProperty", String);
return service.doSomething();
}
http://stackoverflow.com/questions/16332092/spring-mvc-pathvariable-with-dot-is-getting-truncated
Spring considers that anything behind the last dot is a file extension such as .jsonor .xml and trucate it to retrieve your parameter.
So if you have /somepath/{variable} :
  • /somepath/param/somepath/param.json/somepath/param.xml or /somepath/param.anything will result in a param with value param
  • /somepath/param.value.json/somepath/param.value.xml or /somepath/param.value.anything will result in a param with value param.value
if you change your mapping to /somepath/{variable:.+} as suggested, any dot, including the last one will be consider as part of your parameter :
  • /somepath/param will result in a param with value param
  • /somepath/param.json will result in a param with value param.json
  • /somepath/param.xml will result in a param with value param.xml
  • /somepath/param.anything will result in a param with value param.anything
  • /somepath/param.value.json will result in a param with value param.value.json
  • ...
If you don't care of extension recognition, you can disable it by overriding mvc:annotation-drivenautomagic :
<bean id="handlerMapping"
      class="org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerMapping">
    <property name="contentNegotiationManager" ref="contentNegotiationManager"/>
    <property name="useSuffixPatternMatch" value="false"/>
</bean>
So, again, if you have /somepath/{variable} :
  • /somepath/param/somepath/param.json/somepath/param.xml or /somepath/param.anything will result in a param with value param
  • /somepath/param.value.json/somepath/param.value.xml or /somepath/param.value.anything will result in a param with value param.value
note : the difference from the default config is visible only if you have a mapping like somepath/something.{variable}. see Resthub project issue
if you want to keep extension management, since Spring 3.2 you can also set the useRegisteredSuffixPatternMatch property of RequestMappingHandlerMapping bean in order to keep suffixPattern recognition activated but limited to registered extension.
n addition to Martin Frey's answer, this can also be fixed by adding a trailing slash in the RequestMapping value:
/path/{variable}/
Keep in mind that this fix does not support maintainability. It now requires all URI's to have a trailing slash - something that may not be apparent to API users / new developers. Because it's likely not all parameters may have a . in them, it may also create intermittent bugs
https://spring.io/blog/2013/11/01/exception-handling-in-spring-mvc
  @ResponseStatus(value=HttpStatus.CONFLICT,
                  reason="Data integrity violation")  // 409
  @ExceptionHandler(DataIntegrityViolationException.class)
  public void conflict() {
    // Nothing to do
  }
  
  // Specify name of a specific view that will be used to display the error:
  @ExceptionHandler({SQLException.class,DataAccessException.class})
  public String databaseError() {
    // Nothing to do.  Returns the logical view name of an error page, passed
    // to the view-resolver(s) in usual way.
    // Note that the exception is NOT available to this view (it is not added
    // to the model) but see "Extending ExceptionHandlerExceptionResolver"
    // below.
    return "databaseError";
  }

  // Total control - setup a model and return the view name yourself. Or
  // consider subclassing ExceptionHandlerExceptionResolver (see below).
  @ExceptionHandler(Exception.class)
  public ModelAndView handleError(HttpServletRequest req, Exception ex) {
    logger.error("Request: " + req.getRequestURL() + " raised " + ex);

    ModelAndView mav = new ModelAndView();
    mav.addObject("exception", ex);
    mav.addObject("url", req.getRequestURL());
    mav.setViewName("error");
    return mav;
  }

Using @ControllerAdvice Classes

A controller advice allows you to use exactly the same exception handling techniques but apply them across the whole application, not just to an individual controller. You can think of them as an annotation driven interceptor.
Any class annotated with @ControllerAdvice becomes a controller-advice and three types of method are supported:
  • Exception handling methods annotated with @ExceptionHandler.
  • Model enhancement methods (for adding additional data to the model) annotated with
    @ModelAttribute. Note that these attributes are not available to the exception handling views.
  • Binder initialization methods (used for configuring form-handling) annotated with
    @InitBinder.
http://www.mkyong.com/spring-mvc/spring-mvc-exceptionhandler-example/
https://www.mkyong.com/spring-mvc/spring-mvc-file-upload-example/
 // Bean name must be "multipartResolver", by default Spring uses method name as bean name.
    @Bean
    public MultipartResolver multipartResolver() {
        return new StandardServletMultipartResolver();
    }
 /*
 // if the method name is different, you must define the bean name manually like this :
 @Bean(name = "multipartResolver")
    public MultipartResolver createMultipartResolver() {
        return new StandardServletMultipartResolver();
    }*/
4. Single File Upload
    @PostMapping("/upload") // //new annotation since 4.3
    public String singleFileUpload(@RequestParam("file") MultipartFile file,
                                   RedirectAttributes redirectAttributes) {
5. Multiple File Upload
@PostMapping("/uploadMulti")
public String multiFileUpload(@RequestParam("files") MultipartFile[] files,
                              RedirectAttributes redirectAttributes) {

To handle the popular max upload size exceeded exception, declares a @ControllerAdvice and catch the MultipartException
@ControllerAdvice
public class GlobalExceptionHandler {

    @ExceptionHandler(MultipartException.class)
    public String handleError1(MultipartException e, RedirectAttributes redirectAttributes) {

        redirectAttributes.addFlashAttribute("message", e.getCause().getMessage());
        return "redirect:/uploadStatus";

    }
http://www.baeldung.com/spring-file-upload


https://www.mkyong.com/spring-mvc/spring-mvc-pathvariable-dot-get-truncated/
@RequestMapping("/site")
public class SiteController {

    @RequestMapping(value = "/{q}", method = RequestMethod.GET)
    public ModelAndView display(@PathVariable("q") String q) 

http://stackoverflow.com/questions/30204974/spring-mvc-restcontroller-return-json-string

http://stackoverflow.com/questions/20019819/spring-mvc-return-raw-json-string
The problem is that your custom converter takes precedence over the default ones. It's thus called, considers the String as a raw String that must be converted to JSON, and thus escapes the double quotes.
I'm not sure if and how it's possible with XML to register a converter after (and not before) the default ones, but you could set register-defaults to false and provide an explicit list of all the converters you want to apply. If org.springframework.http.converter.StringHttpMessageConverteris registered before your custom one, it will be called first and will send the returned String as is.
http://stackoverflow.com/questions/15507064/return-literal-json-strings-in-spring-mvc-responsebody
 guess what you want is producing a response with content-type application/json. In your case, when you have the json-data as a raw string, do the following:
In your controller add produces="application/json" to your @RequestMapping attribute:
@RequestMapping(value = "test", method = RequestMethod.GET, produces="application/json")
public @ResponseBody
String getTest() {
    return "{\"a\":1, \"b\":\"foo\"}";
}
Then you have to configure the StringHttpMessageConverter to accept the application/json media-type.
With Java-config:
@Override
public void configureMessageConverters(
        List<HttpMessageConverter<?>> converters) {
    StringHttpMessageConverter stringConverter = new StringHttpMessageConverter(
            Charset.forName("UTF-8"));
    stringConverter.setSupportedMediaTypes(Arrays.asList( //
            MediaType.TEXT_PLAIN, //
            MediaType.TEXT_HTML, //
            MediaType.APPLICATION_JSON));
    converters.add(stringConverter);
}

https://www.javacodegeeks.com/2013/07/spring-mvc-requestbody-and-responsebody-demystified.html
If you annotate a method with @ResponseBody, spring will try to convert its return value and write it to the http response automatically. If you annotate a methods parameter with @RequestBody, spring will try to convert the content of the incoming request body to your parameter object on the fly.

Depending on your configuration, spring has a list of HttpMessageConverters registered in the background. A HttpMessageConverters responsibility is to convert the request body to a specific class and back to the response body again, depending on a predefined mime type. Every time an issued request is hitting a @RequestBody or @ResponseBody annotation spring loops through all registered HttpMessageConverters seeking for the first that fits the given mime type and class and then uses it for the actual conversion.
http://stackoverflow.com/questions/3977973/whats-the-difference-between-mvcannotation-driven-and-contextannotation

<context:annotation-config> declares support for general annotations such as @Required@Autowired@PostConstruct, and so on.
<mvc:annotation-driven /> declares explicit support for annotation-driven MVC controllers (i.e. @RequestMapping@Controller, although support for those is the default behaviour), as well as adding support for declarative validation via @Valid and message body marshalling with @RequestBody/ResponseBody.
mvc:annotation-driven is a tag added in Spring 3.0 which does the following:
  1. Configures the Spring 3 Type ConversionService (alternative to PropertyEditors)
  2. Adds support for formatting Number fields with @NumberFormat
  3. Adds support for formatting Date, Calendar, and Joda Time fields with @DateTimeFormat, if Joda Time is on the classpath
  4. Adds support for validating @Controller inputs with @Valid, if a JSR-303 Provider is on the classpath
  5. Adds support for support for reading and writing XML, if JAXB is on the classpath (HTTP message conversion with @RequestBody/@ResponseBody)
  6. Adds support for reading and writing JSON, if Jackson is on the classpath (along the same lines as #5)
context:annotation-config Looks for annotations on beans in the same application context it is defined and declares support for all the general annotations like @Autowired, @Resource, @Required, @PostConstruct etc etc.

When you're using Java code (as opposed to XML) to configure your Spring application, @EnableWebMvc is used to enable Spring MVC. If you're not already familiar with Spring's support for Java configuration, this is a good place to start.
@EnableWebMvc is equivalent to <mvc:annotation-driven /> in XML. It enables support for @Controller-annotated classes that use @RequestMapping to map incoming requests to a certain method. You can read detailed information about what it configures by default and how to customise the configuration in the reference documentation.

org.springframework.beans.factory.support.level=FINEST
org.springframework.security.level=FINEST
http://stackoverflow.com/questions/12514285/registrer-mappingjackson2httpmessageconverter-in-spring-3-1-2-with-jaxb-annotati
<mvc:annotation-driven>
    <mvc:message-converters register-defaults="false">
        <bean id="jacksonMessageConverter" class="org.springframework.http.converter.json.MappingJackson2HttpMessageConverter">
            <property name="objectMapper" ref="jacksonObjectMapper" />
            <property name="supportedMediaTypes">
                <list>
                    <bean class="org.springframework.http.MediaType">
                        <constructor-arg index="0" value="application" />
                        <constructor-arg index="1" value="json" />
                        <constructor-arg index="2" value="UTF-8" />
                    </bean>
                </list>
            </property>

        </bean>
    </mvc:message-converters>
</mvc:annotation-driven>

<bean id="jaxbAnnotationInspector" class="com.fasterxml.jackson.module.jaxb.JaxbAnnotationIntrospector" />

<bean id="jacksonObjectMapper" class="com.fasterxml.jackson.databind.ObjectMapper">
    <property name="annotationIntrospector" ref="jaxbAnnotationInspector" />
</bean>

https://pub.scotch.io/@ethanmillar/spring-mvc-component-scan-annotation-config-annotation-driven
  • annotation-config allow us to use @Autowire, @Required and @Qualifier annotations.
  • component-scan allow @Component, @Service, @Controller, etc.. annotations.
  • annotation-driven <mvc:annotation-driven /> declares explicit support for annotation-driven MVC controllers (i.e. @RequestMapping, @Controller, although support for those is the default behaviour), as well as adding support for declrative validation via @Valid and message body marshalling with @RequestBody/ResponseBody.

Labels

Review (572) System Design (334) System Design - Review (198) Java (189) Coding (75) Interview-System Design (65) Interview (63) Book Notes (59) Coding - Review (59) to-do (45) Linux (43) Knowledge (39) Interview-Java (35) Knowledge - Review (32) Database (31) Design Patterns (31) Big Data (29) Product Architecture (28) MultiThread (27) Soft Skills (27) Concurrency (26) Cracking Code Interview (26) Miscs (25) Distributed (24) OOD Design (24) Google (23) Career (22) Interview - Review (21) Java - Code (21) Operating System (21) Interview Q&A (20) System Design - Practice (20) Tips (19) Algorithm (17) Company - Facebook (17) Security (17) How to Ace Interview (16) Brain Teaser (14) Linux - Shell (14) Redis (14) Testing (14) Tools (14) Code Quality (13) Search (13) Spark (13) Spring (13) Company - LinkedIn (12) How to (12) Interview-Database (12) Interview-Operating System (12) Solr (12) Architecture Principles (11) Resource (10) Amazon (9) Cache (9) Git (9) Interview - MultiThread (9) Scalability (9) Trouble Shooting (9) Web Dev (9) Architecture Model (8) Better Programmer (8) Cassandra (8) Company - Uber (8) Java67 (8) Math (8) OO Design principles (8) SOLID (8) Design (7) Interview Corner (7) JVM (7) Java Basics (7) Kafka (7) Mac (7) Machine Learning (7) NoSQL (7) C++ (6) Chrome (6) File System (6) Highscalability (6) How to Better (6) Network (6) Restful (6) CareerCup (5) Code Review (5) Hash (5) How to Interview (5) JDK Source Code (5) JavaScript (5) Leetcode (5) Must Known (5) Python (5)

Popular Posts