zoukankan      html  css  js  c++  java
  • SpringMVC常用注解(三)

    一、@Controller 、@RestController 和 @ControllerAdvice

    1. @Controller

    @Controller 用于标记在一个类上,使用它标记的类就是一个SpringMVC Controller 对象。分发处理器将会扫描使用了该注解的类的方法,并检测该方法是否使用了@RequestMapping 注解。
    使用@Controller 注解,在对应的方法上,视图解析器可以解析return 的jsp,html页面,并且跳转到相应页面;
    若返回json等内容到页面,则需要加@ResponseBody注解。

    2. @RestController

    @RestController注解相当于@ResponseBody + @Controller合在一起的作用。

    返回json数据不需要在方法前面加@ResponseBody注解了,但使用@RestController这个注解,就不能返回jsp,html页面,视图解析器无法解析jsp,html页面,返回的内容就是return 里的内容。

    若使用@RestController,又想返回页面,则需要使用ModelAndView:

    public ModelAndView login(){
            ModelAndView mv = new ModelAndView("index");
            return mv;
       }

    3. @ControllerAdvice

    @ControllerAdvice,是Spring3.2后提供的新注解,从名字上可以看出大体意思是控制器增强。

    ControllerAdvice拆分开来就是Controller Advice,关于Advice,其是用于封装一个切面所有属性的,包括切入点和需要织入的切面逻辑。这里ContrllerAdvice也可以这么理解,其抽象级别应该是用于对Controller进行“切面”环绕的,而具体的业务织入方式则是通过结合其他的注解来实现的(@ControllerAdvice并不是使用AOP的方式来织入业务逻辑的,而是Spring内置对其各个逻辑的织入方式进行了内置支持)。@ControllerAdvice是在类上声明的注解,其用法主要有三点:

    (1) 全局异常处理,结合方法型注解@ExceptionHandler,用于捕获Controller中抛出的指定类型的异常,从而达到不同类型的异常区别处理的目的

    @ControllerAdvice(basePackages = "mvc")
    public class SpringControllerAdvice {
      @ExceptionHandler(RuntimeException.class)
      public ModelAndView runtimeException(RuntimeException e) {
        e.printStackTrace();
        return new ModelAndView("error");
      }
    }

    在该接口中抛出了RuntimeException,那么理论上,这里的异常捕获器就会捕获该异常,然后返回默认的error视图。以下是UserController的代码:

    @RequestMapping(value = "/detail", method = RequestMethod.GET)
    public ModelAndView detail(@RequestParam("id") long id) {
        ModelAndView view = new ModelAndView("user");
        User user = userService.detail(id);
        view.addObject("user", user);
        throw new RuntimeException("mock user detail exception.");
    }

    在UserController中抛出的异常能够被SpringControllerAdvice捕获。

    这里需要注意的是,统一处理异常的controller需要放在和普通controller同级的包下,或者在ComponentScan的包下。在处理异常的时候可以使用System.out的方式,也可以使用logger.info,或者可以入到数据库中。

    (2) 全局数据绑定,结合方法型注解@InitBinder,用于request中自定义参数解析方式进行注册,从而达到自定义指定格式参数的目的;

    对于@InitBinder,该注解的主要作用是绑定一些自定义的参数。一般情况下我们使用的参数通过@RequestParam,@RequestBody或者@ModelAttribute等注解就可以进行绑定了,但对于一些特殊类型参数,比如Date,它们的绑定Spring是没有提供直接的支持的,我们只能为其声明一个转换器,将request中字符串类型的参数通过转换器转换为Date类型的参数,从而供给@RequestMapping标注的方法使用。

    @ControllerAdvice(basePackages = "mvc")
    public class SpringControllerAdvice {
      @InitBinder
      public void globalInitBinder(WebDataBinder binder) {
        binder.addCustomFormatter(new DateFormatter("yyyy-MM-dd"));
      }
    }

    @InitBinder标注的方法注册的Formatter在每次request请求进行参数转换时都会调用,用于判断指定的参数是否为其可以转换的参数。以下是UserController的代码:

    @RequestMapping(value = "/detail", method = RequestMethod.GET)
    public ModelAndView detail(@RequestParam("id") long id, Date date) {
        System.out.println(date);
        ModelAndView view = new ModelAndView("user");
        User user = userService.detail(id);
        view.addObject("user", user);
        return view;
    }

    (3) 全局数据预处理,结合方法型注解@ModelAttribute,表示其标注的方法将会在目标Controller方法执行之前执行。

    使用@ModelAttribute,如果声明在方法上,并且结合@ControllerAdvice,该方法将会在@ControllerAdvice所指定的范围内的所有接口方法执行之前执行,并且@ModelAttribute标注的方法的返回值还可以供给后续会调用的接口方法使用。

    @ControllerAdvice(basePackages = "mvc")
    public class SpringControllerAdvice {
      @ModelAttribute(value = "message")
      public String globalModelAttribute() {
        System.out.println("global model attribute.");
        return "this is from model attribute";
      }
    }

    这里需要注意的是,该方法提供了一个String类型的返回值,而@ModelAttribute中指定了该属性名称为message,这样在Controller层就可以接收该参数了,如下是UserController(普通的@Controller):

    @RequestMapping(value = "/detail", method = RequestMethod.GET)
    public ModelAndView detail(@RequestParam("id") long id, 
           @ModelAttribute("message") String message) {
        System.out.println(message);
        ModelAndView view = new ModelAndView("user");
        User user = userService.detail(id);
        view.addObject("user", user);
        return view;
    }

    @ModelAttribute标注的方法的执行是在所有拦截器的preHandle()方法执行之后才会执行。

    4. @ControllerAdvice和@RestControllerAdvice的区别

    //@ControllerAdvice和@RestControllerAdvice都可以指向控制器的一个子集
    // 指向所有带有注解@RestController的控制器
    @ControllerAdvice(annotations = RestController.class)
    public class AnnotationAdvice {}
    // 指向所有指定包中的控制器
    @ControllerAdvice("org.example.controllers")
    public class BasePackageAdvice {}
    // 指向所有带有指定签名的控制器
    @ControllerAdvice(assignableTypes = {ControllerInterface.class, AbstractController.class})
    public class AssignableTypesAdvice {}

    @ControllerAdvice和@RestControllerAdvice的区别 类似于 @RestController 与 @Controller的区别。

    二、@RequestBody 和 @ResponseBody

    1. @RequestBody

    @RequestBody是作用在形参列表上,用于将前台发送过来固定格式的数据【xml 格式或者 json等】封装为对应的 JavaBean 对象,封装时使用到的一个对象是系统默认配置的 HttpMessageConverter进行解析,然后封装到形参上。

    public Object login(@RequestBody User loginUuser, HttpSession session)

    2. @ResponseBody

    @ResponseBody是作用在方法上的,@ResponseBody 表示该方法的返回结果直接写入 HTTP response body 中,一般在异步获取数据时使用【也就是AJAX】,在使用 @RequestMapping后,返回值通常解析为跳转路径,但是加上 @ResponseBody 后返回结果不会被解析为跳转路径,而是直接写入 HTTP response body 中。 比如异步获取 json 数据,加上 @ResponseBody 后,会直接返回 json 数据。@RequestBody 将 HTTP 请求正文插入方法中,使用适合的 HttpMessageConverter 将请求体写入某个对象。

    @ResponseBody
    public Object login(String name, String password, HttpSession session) 

    三、@ModelAttribute 和 @SessionAttributes

    1. @ModelAttribute

    @ModelAttribute注释方法,被@ModelAttribute注释的方法会在此controller每个方法执行前被执行,因此对于一个controller映射多个URL的用法来说,要谨慎使用。

    (1) @ModelAttribute注释void返回值的方法

    @Controller
    public class HelloWorldController {
    
        @ModelAttribute
        public void populateModel(@RequestParam String abc, Model model) {
           model.addAttribute("attributeName", abc);
        }
    
        @RequestMapping(value = "/helloWorld")
        public String helloWorld() {
           return "helloWorld";
        }
    }

    (2) @ModelAttribute注释返回具体类的方法 

    @ModelAttribute
    public Account addAccount(@RequestParam String number) {
       return accountManager.findAccount(number);
    }

    这种情况,model属性的名称没有指定,它由返回类型隐含表示,如这个方法返回Account类型,那么这个model属性的名称是account。
    这个例子中model属性名称由返回对象类型隐含表示,model属性对象就是方法的返回值。它无须要特定的参数。

    (3) @ModelAttribute(value="")注释返回具体类的方法 

    @Controller
    public class HelloWorldController {
    
        @ModelAttribute("attributeName")
        public String addAccount(@RequestParam String abc) {
           return abc;
        }
    
        @RequestMapping(value = "/helloWorld")
        public String helloWorld() {
           return "helloWorld";
        }
    }

    这个例子中使用@ModelAttribute注释的value属性,来指定model属性的名称。model属性对象就是方法的返回值。它无须要特定的参数。

    (4) @ModelAttribute和@RequestMapping同时注释一个方法 

    @Controller
    public class HelloWorldController {
    
        @RequestMapping(value = "/helloWorld.do")
        @ModelAttribute("attributeName")
        public String helloWorld() {
           return "hi";
        }
    }

    这时这个方法的返回值并不是表示一个视图名称,而是model属性的值,视图名称由RequestToViewNameTranslator根据请求"/helloWorld.do"转换为逻辑视图helloWorld。
    Model属性名称由@ModelAttribute(value=””)指定,相当于在request中封装了key=attributeName,value=hi。

    @ModelAttribute注释一个方法的参数

    (1) 从model中获取

    @Controller
    public class HelloWorldController {
    
        @ModelAttribute("user")
        public User addAccount() {
           return new User("jz","123");
        }
    
        @RequestMapping(value = "/helloWorld")
        public String helloWorld(@ModelAttribute("user") User user) {
           user.setUserName("jizhou");
           return "helloWorld";
        }
    }

    在这个例子里,@ModelAttribute("user") User user注释方法参数,参数user的值来源于addAccount()方法中的model属性。
    此时如果方法体没有标注@SessionAttributes("user"),那么scope为request,如果标注了,那么scope为session。

    (2) 从Form表单或URL参数中获取(实际上,不做此注释也能拿到user对象) 

    @Controller
    public class HelloWorldController {
    
        @RequestMapping(value = "/helloWorld")
        public String helloWorld(@ModelAttribute User user) {
           return "helloWorld";
        }
    }

    注意这时候这个User类一定要有没有参数的构造函数。

    @ModelAttribute注解作用在方法上或者方法的参数上,表示将被注解的方法的返回值或者是被注解的参数作为Model的属性加入到Model中,然后Spring框架自会将这个Model传递给ViewResolver。Model的生命周期只有一个http请求的处理过程,请求处理完后,Model就销毁了。

    如果想让参数在多个请求间共享,那么可以用到要说到的@SessionAttribute注解。

    2. @SessionAttributes

    @SessionAttributes作用于处理器类上,用于在多个请求之间传递参数,类似于Session的Attribute,但不完全一样,一般来说@SessionAttribute设置的参数只用于暂时的传递,而不是长期的保存,长期保存的数据还是要放到Session中。

    通过@SessionAttributes注解设置的参数有3类用法:

    • 在视图中通过request.getAttribute或session.getAttribute获取
    • 在后面请求返回的视图中通过session.getAttribute或者从model中获取
    • 自动将参数设置到后面请求所对应处理器的Model类型参数或者有@ModelAttribute注释的参数里面。

    将一个参数设置到SessionAttribute中需要满足两个条件:

    • 在@SessionAttribute注解中设置了参数的名字或者类型
    • 在处理器中将参数设置到了model中。
    @Controller
    @RequestMapping("sc")
    @SessionAttributes("name")
    public class SessionController {
        @RequestMapping("session")
        public String sessions(Model model,HttpSession session){
            model.addAttribute("name", "winclpt");
            session.setAttribute("myName", "chke");
            return "session";
    }

    上面的代码将Model中的name参数保存到了session中(如果Model中没有name参数,而session中存在一个name参数,那么SessionAttribute会这个参数塞进Model中)

    SessionAttributes有两个参数:
    String[] value:要保存到session中的参数名称
    Class[] typtes:要保存的参数的类型,和value中顺序要对应上
    所以可以这样写:@SessionAttributes(types = {User.class,Dept.class},value={“attr1”,”attr2”})

    原理理解:它的做法大概可以理解为将Model中的被注解的attrName属性保存在一个SessionAttributesHandler中,在每个RequestMapping的方法执行后,这个SessionAttributesHandler都会将它自己管理的“属性”从Model中写入到真正的HttpSession;同样,在每个RequestMapping的方法执行前,SessionAttributesHandler会将HttpSession中的被@SessionAttributes注解的属性写入到新的Model中。

    如果想删除session中共享的参数,可以通过SessionStatus.setComplete(),这句只会删除通过@SessionAttributes保存到session中的参数

    四、 @Autowired

    首先要知道另一个东西,default-autowire,它是在xml文件中进行配置的,可以设置为byName、byType、constructor和autodetect;比如byName,不用显式的在bean中写出依赖的对象,它会自动的匹配其它bean中id名与本bean的set**相同的,并自动装载。
    @Autowired是用在JavaBean中的注解,通过byType形式,用来给指定的字段或方法注入所需的外部资源。

    • no:默认不使用autowiring。 必须显示的使用”“标签明确地指定bean。
    • byName:根据属性名自动装配。此选项将检查容器并根据名字查找与属性完全一致的bean,并将其与属性自动装配。
    • byType:如果容器中存在一个与指定属性类型相同的bean,那么将与该属性自动装配。如果存在多个该类型的bean,那么将会抛出异常,并指出不能使用byType方式进行自动装配。若没有找到相匹配的bean,则什么事都不发生,属性也不会被设置。如果你不希望这样,那么可以通过设置 dependency-check=”objects”让Spring抛出异常。
    • constructor:与byType的方式类似,不同之处在于它应用于构造器参数。如果在容器中没有找到与构造器参数类型一致的bean,那么将会抛出异常。
    • autodetect:通过bean类的自省机制(introspection)来决定是使用constructor还是byType方式进行自动装配。如果发现默认的构造器,那么将使用byType方式。

    在属性中使用该注解,不用再写setXXX方法。

    五、@Value、 @Required、@Validated

    1. @Validated

    @Valid是javax.validation里的。
    @Validated是@Valid 的一次封装,是Spring提供的校验机制使用。@Valid不提供分组功能。

    (1) 分组

    当一个实体类需要多种验证方式时,例:对于一个实体类的id来说,新增的时候是不需要的,对于更新时是必须的。
    可以通过groups对验证进行分组。

    //分组接口类(通过向groups分配不同类的class对象,达到分组目的):
    public interface First {
     
    }
    //在bean定义的时候:
    //在First分组时,判断不能为空
    @NotEmpty(groups={First.class})
    private String id;
    //控制类:
    //不需验证ID
    public String addPeople(@Validated People p,BindingResult result)
    //验证ID
    public String updatePeople(@Validated({First.class}) People p,BindingResult result)

    注意:

    • 不分配groups,默认每次都要进行验证
    • 对一个参数需要多种验证方式时,也可通过分配不同的组达到目的

    (2) 组序列

    默认情况下,不同组别的约束验证是无序的,然而在某些情况下,约束验证的顺序却很重要。

    //分组接口类
    public interface First {
     
    }
    
    public interface Second {
     
    }
    //通过@GroupSequence注解对组进行排序
    @GroupSequence({First.class,Second.class})
    public interface Group {
     
    }
    //验证ID
    public String addPeople(@Validated({Group.class}) People p,BindingResult result)

    2. @Value

    为了简化读取properties文件中的配置值,spring支持@value注解的方式来获取,这种方式大大简化了项目配置,提高业务中的灵活性。

    两种使用方式:

    • @Value("#{configProperties['key']}")
    • @Value("${key}")

    (1)  @Value("#{configProperties['key']}")

    配置方法一:

    <bean id="configProperties" class="org.springframework.beans.factory.config.PropertiesFactoryBean">
        <property name="locations">
            <list>
                <value>classpath:value.properties</value>
            </list>
        </property>
    </bean>

    配置方法二:

    <util:properties id="configProperties" location="classpath:value.properties"></util:properties>

    注:方法一和方法二是等价的,这种方法需要util标签,要引入util的xsd:

    http://www.springframework.org/schema/util
    http://www.springframework.org/schema/util/spring-util.xsd"
    value.properties
    key=1
    
    ValueDemo.java
    @Component
    public class ValueDemo {
        @Value("#{configProperties['key']}")
        private String value;
     
        public String getValue() {
            return value;
        }
    }

    (2) @Value("${key}")

    <!--在上面的配置基础上加上:-->
    <bean id="propertyConfigurer" class="org.springframework.beans.factory.config.PreferencesPlaceholderConfigurer">
        <property name="properties" ref="configProperties"/>
    </bean>
    <!--或直接完整指定:-->
    <bean id="appProperty"
              class="org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
        <property name="locations">
            <array>
                <value>classpath:value.properties</value>
            </array>
        </property>
    </bean>
    @Component
    public class ValueDemo {
        @Value("${key}")
        private String value;
     
        public String getValue() {
            return value;
        }
    }

    3. @Required

    @Required 注释应用于 bean 属性的 setter 方法,它表明受影响的 bean 属性在配置时必须放在 XML 配置文件中,否则容器就会抛出一个 BeanInitializationException 异常。

    <bean id="resultMessage" class="com.jake.ResultMessage">
       <property name="code" value="001" /><!--设置属性-->
    </bean>

    使用<context:annotation-config/>会隐式地注册RequiredAnnotationBeanPostProcessor,使@Required注解生效,如果没有就必须在xml文件中配置RequiredAnnotationBeanPostProcessor bean。

    注意:@Required只能设置在setter方法上

    六、@ExceptionHandler、@ResponseStatus

    @ExceptionHandler只有一个参数,可以是一个数组,表示要捕获的异常。
    @ResponseStatus
      注解中有两个参数,value属性设置异常的状态码,reaseon是异常的描述。
      状态码定义在HttpStatus上。

    七、@RequestMapping

    RequestMapping是一个用来处理请求地址映射的注解,可用于类或方法上。用于类上,表示类中的所有响应请求的方法都是以该地址作为父路径。

    @RequestMapping 除了修饰方法, 还可来修饰类 :

    • 类定义处: 提供初步的请求映射信息。相对于 WEB 应用的根目录;
    • 方法处: 提供进一步的细分映射信息。 相对于类定义处的 URL。
    • 若类定义处未标注 @RequestMapping,则方法处标记的 URL相对于 WEB 应用的根目录
    • 返回ModelAndView时的url会根据你的 @RequestMapping实际情况组成。
    • 对应项目jsp位置则是一级路径对应一级文件目录:如url为/default/index对应项目中webapp/default/index.jsp
    • 如果类上没有映射,那么url直接就是方法的映射;否则url为类上+方法上映射路径组合。

    RequestMapping注解有六个属性,下面我们把它分成三类进行说明:

    • value:指定请求的实际地址,指定的地址可以是URI Template 模式;
    • method: 指定请求的method类型, GET、POST、PUT、DELETE等,在RequestMethod定义;
    • consumes: 指定处理请求的提交内容类型(Content-Type),例如application/json, text/html;
    • produces: 指定返回的内容类型,仅当request请求头中的(Accept)类型中包含该指定类型才返回;
    • params: 指定request中必须包含某些参数值时,才让该方法处理;
    • headers: 指定request中必须包含某些指定的header值,才能让该方法处理请求;

    八、@InitBinder

    从字面意思可以看出这个的作用是给Binder做初始化的,被此注解的方法可以对WebDataBinder初始化。WebDataBinder是用于表单到方法的数据绑定的!
    @InitBinder只在@Controller中注解方法来为这个控制器注册一个绑定器初始化方法,方法只对本控制器有效。

    1. 对数据绑定进行设置

     WebDataBinder中有很多方法可以对数据绑定进行具体的设置:比如我们设置name属性为非绑定属性(也可以设置绑定值setAllowedFields):

    @InitBinder
    public void initBinder(WebDataBinder binder) {
            //setDisallowedFields表示禁止接收的参数
            binder.setDisallowedFields("name");
    }

    2. 注册已有的编辑器

    WebDataBinder是用来绑定请求参数到指定的属性编辑器.由于前台传到controller里的值是String类型的,当往Model里Set这个值的时候,如果set的这个属性是个对象,Spring就会去找到对应的editor进行转换,然后再set进去!Spring自己提供了大量的实现类(在org.springframwork.beans.propertyEditors下的所有editor),诸如CustomDateEditor ,CustomBooleanEditor,CustomNumberEditor等许多,基本上够用。  在平时使用SpringMVC时,会碰到javabean中有Date类型参数,表单中传来代表日期的字符串转化为日期类型,SpringMVC默认不支持这种类型的转换。我们就需要手动设置时间格式并在webDateBinder上注册这个编辑器!

    //这里我们在@RequestMapping参数上就可以直接使用Date类型的参数。
    CustomDateEditor editor = new CustomDateEditor(new SimpleDateFormat("yyyy-MM-dd"),true);
    binder.registerCustomEditor(Date.class, editor);

    3.  注册自定义编辑器

    用自定义编辑器就是在第二个的基础上添加个自定义编辑器就行了,自定义的编辑器类需要继承org.springframework.beans.propertyeditors.PropertiesEditor;,并重写setAsText和getAsText两个方法就行了!
    比如下面这个DoubleEditor:

    public class DoubleEditor extends PropertyEditorSupport {
        @Override
        public void setAsText(String text) throws IllegalArgumentException {
            if (text == null || text.equals("")) {
                text = "0";
            }
            setValue(Double.parseDouble(text));
        }
     
        @Override
        public String getAsText() {
            return getValue().toString();
        }
    }

    4. 设置属性的前缀可以实现参数绑定

    form表单:

    <form action="/testBean" method="post">
        name: <input type="text" name="u.name"> <br>
        age: <input type="text" name="u.age"> <br>
        name: <input type="text" name="s.name"> <br>
        age: <input type="text" name="s.age"> <br>
        <input type="submit">
    </form>

    Controller:

    @InitBinder("user")
    public void init1(WebDataBinder binder) {
        binder.setFieldDefaultPrefix("u.");
    }
    
    @InitBinder("stu")
    public void init2(WebDataBinder binder) {
        binder.setFieldDefaultPrefix("s.");
    }
    
    @RequestMapping("/testBean")
    public ModelAndView testBean(User user, @ModelAttribute("stu") Student stu) {
        System.out.println(stu);
        System.out.println(user);
        String viewName = "success";
        ModelAndView modelAndView = new ModelAndView(viewName);
        modelAndView.addObject("user", user);
        modelAndView.addObject("student", stu);
        return modelAndView;
    
    }

    九、@PathVariable

    @PathVariable 映射 URL 绑定的占位符:

    • 带占位符的 URL 是 Spring3.0 新增的功能,该功能在SpringMVC 向 REST 目标挺进发展过程中具有里程碑的意义
    • 通过 @PathVariable 可以将 URL 中占位符参数绑定到控制器处理方法的入参中:URL 中的 {xxx} 占位符可以通过@PathVariable(“xxx“) 绑定到操作方法的入参中。

    如:

    <a href="springmvc/testPathVariable/1">testPathVariable</a>
    //@PathVariable可以用来映射URL中的占位符到目标方法的参数中
    @RequestMapping("/testPathVariable/{id}")
    public String testPathVariable(@PathVariable("id") Integer id){
        System.out.println("testPathVariable:"+id);
        return SUCCESS;
    }

    REST的支持

    - /order/1 HTTP GET :得到 id = 1 的 order
    - /order/1 HTTP DELETE:删除 id = 1的 order
    - /order/1 HTTP PUT:更新id = 1的 order
    - /order HTTP POST:新增 order

    HiddenHttpMethodFilter:浏览器 form 表单只支持 GET与 POST 请求,而DELETE、PUT 等 method 并不支持,Spring3.0 添加了一个过滤器,可以将这些请求转换为标准的 http 方法,使得支持 GET、POST、PUT 与DELETE 请求。

    <!--
     配置org.springframework.web.filter.HiddenHttpMethodFilter:可以把POST请求转换成DELETE或者POST请求
      -->
    
    <filter>
      <filter-name>HiddenHttpMethodFilter</filter-name>
      <filter-class>org.springframework.web.filter.HiddenHttpMethodFilter</filter-class>
    </filter>   
    
    <filter-mapping>
      <filter-name>HiddenHttpMethodFilter</filter-name>
      <url-pattern>/*</url-pattern>
    </filter-mapping>

    十、@RequestHeader、@RequestParam、@CookieValue

    1. @RequestHeader

    @RequestHeader 注解,可以把Request请求header部分的值绑定到方法的参数上。
    这是一个Request 的header部分:

    • Host localhost:8080
    • Accept text/html,application/xhtml+xml,application/xml;q=0.9
    • Accept-Language fr,en-gb;q=0.7,en;q=0.3
    • Accept-Encoding gzip,deflate
    • Accept-Charset ISO-8859-1,utf-8;q=0.7,*;q=0.7
    • Keep-Alive 300

    2. @RequestParam 

    在SpringMvc后台进行获取数据,一般是两种。 

    • request.getParameter(“参数名”)
    • 用@RequestParam注解获取

    @RequestParam 有三个属性:

    (1) value:请求参数名(必须配置)

    (2) required:是否必需,默认为 true,即 请求中必须包含该参数,如果没有包含,将会抛出异常(可选配置)

    (3) defaultValue:默认值,如果设置了该值,required 将自动设为 false,无论你是否配置了required,配置了什么值,都是 false(可选配置)

    值得注意的是:如果方法上的@RequestMapping 配置了 params 属性,则请求中也必须包含该参数。

    //可以对传入参数指定参数名:
    // 下面的对传入参数指定为aa,如果前端不传aa参数名,会报错  
    @RequestParam(value="aa") String inputStr  
    
    //可以通过required=false或者true来要求@RequestParam配置的前端参数是否一定要传 
    // required=false表示不传的话,会给参数赋值为null,required=true就是必须要有  
    @RequestMapping("testRequestParam")    
    public String filesUpload(@RequestParam(value="aa", required=true) String inputStr, HttpServletRequest request) 
    
    /**如果@requestParam注解的参数是int类型,并且required=false,此时如果不传参数的话,会报错。原因是,required=false时,不传参数的话,会给参数赋值null,这样就会把null赋值给了int,因此会报错。*/
    // required=false表示不传的话,会给参数赋值为null,required=true就是必须要有  
    @RequestMapping("testRequestParam")    
    public String filesUpload(@RequestParam(value="aa", required=false) int inputStr, HttpServletRequest request) 
    //若是前端页面不传参的话,此处就会报错。当然可以用Integer代替int
    时刻与技术进步,每天一点滴,日久一大步!!! 本博客只为记录,用于学习,如有冒犯,请私信于我。
  • 相关阅读:
    UVa 541 Error Correction
    UVa 11045 My T-shirt suits me
    【模板】Ford-Fulkerson算法
    POJ 1273 Drainage Ditches
    UVa 10158 War
    UVa 658 It's not a Bug, it's a Feature!
    【模板】并查集
    【模板】Floyd-Warshall算法
    UVa 10034 Freckles
    UVa 10048 Audiophobia
  • 原文地址:https://www.cnblogs.com/myitnews/p/11567719.html
Copyright © 2011-2022 走看看