我们何时必须使用@ModelAttribute及其工作方式 [英] When we must use @ModelAttribute, and how it works

查看:195
本文介绍了我们何时必须使用@ModelAttribute及其工作方式的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

您好,我对@ModelAttribute批注有疑问.据我了解,我们在方法参数中使用@ModelAttribute从模型中获取数据.但是,很难清楚地了解何时以及如何使用它. (代码示例摘自Spring in Action 5书) 为什么在这种情况下,在以下 public String processOrder()方法中的代码中,我们不对 @有效订单

Hello I have question about @ModelAttribute annotation. As i understand, we use @ModelAttribute in method arguments to get data from the model. But it's quite hard to understand clearly when and how its used. (Code samples are from Spring in Action 5 book) Why in this case in the code below in public String processOrder() method we do not use @ModelAttribute annotation on @Valid Order order

    @Controller
    @RequestMapping("/orders")
    @SessionAttributes("order")
    public class OrderController {

      private OrderRepository orderRepo;

      public OrderController(OrderRepository orderRepo) {
        this.orderRepo = orderRepo;
      }

      @GetMapping("/current")
      public String orderForm(@AuthenticationPrincipal User user, 
          @ModelAttribute Order order) {
        if (order.getDeliveryName() == null) {
          order.setDeliveryName(user.getFullname());
        }
        //following conditions

        return "orderForm";
      }


      @PostMapping
      public String processOrder(@Valid Order order, Errors errors,  // <<< Here
          SessionStatus sessionStatus, 
          @AuthenticationPrincipal User user) {

        if (errors.hasErrors()) {
          return "orderForm";
        }

        order.setUser(user);

        orderRepo.save(order);
        sessionStatus.setComplete();

        return "redirect:/";
      }


    }

但在这种情况下,在@Valid Taco taco上使用方法 processDesign()上的DesignTacoController类@ModelAttribute:

but in this case, DesignTacoController class, @ModelAttribute on a method processDesign() is used on @Valid Taco taco:

    @Slf4j
    @Controller
    @RequestMapping("/design")
    public class DesignTacoController {



      @PostMapping
 public String processDesign(@Valid @ModelAttribute("design") Taco design, // <<< Here   
 Errors errors, Model model) {
        if (errors.hasErrors()) {
          return "design";
        }

        // Save the taco design...
        // We'll do this in chapter 3
        log.info("Processing design: " + design);

        return "redirect:/orders/current";
      }

然后在下一章中,作者从同一DesignTacoController类的 processDesign()方法中删除@ModelAttribute.

And then in the next chapter author removes @ModelAttribute from processDesign() method from the same DesignTacoController class.

    @Controller
    @RequestMapping("/design")
    @SessionAttributes("order")
    @Slf4j
    public class DesignTacoController {

      @ModelAttribute(name = "order")
      public Order order() {
        return new Order();
      }

      @ModelAttribute(name = "design")
      public Taco design() {
        return new Taco();
      }


      @PostMapping
      public String processDesign(
          @Valid Taco taco, Errors errors, // <<< Here 
          @ModelAttribute Order order) {

        log.info("   --- Saving taco");

        if (errors.hasErrors()) {
          return "design";
        }

        Taco saved = tacoRepo.save(taco);
        order.addDesign(saved);

        return "redirect:/orders/current";
      }

在此代码段中(来自上面的代码):

And in this code snippet(from the code above):

    @PostMapping
          public String processDesign(
              @Valid Taco taco, Errors errors, // <<< Here 
              @ModelAttribute Order order) {
    ....
    }

书中的

引用:"Order参数用@ModelAttribute注释,以指示其 值应来自模型,并且Spring MVC不应尝试绑定 向其请求参数." 我不明白作者在这里的意思,因为在所有教程中都说@ModelAttribute用作方法参数时,它将请求参数绑定到它.将表单数据与POJO bean绑定,然后使用来自提交表单的数据填充模型属性.

quote from book: "The Order parameter is annotated with @ModelAttribute to indicate that its value should come from the model and that Spring MVC shouldn’t attempt to bind request parameters to it." This I don't understand what author meant here, because in all tutorials it is said that when @ModelAttribute is used as a method arguments,it binds request parameters to it. Binds the form data with a POJO bean, model attribute is populated with data from a form submitted.

推荐答案

我也不清楚.

在这里,我们需要指定模型属性的名称. 因为我们认为我们将其命名为"design"而不是"taco".

Here we need specify the name if the model attribute. Because in our view we assume it is named "design" and not "taco".

@PostMapping
public String processDesign(@Valid @ModelAttribute("design") Taco design, Errors errors) {

如果我们将Taco类重命名为Design ... 如果模型属性,我们不需要指定名称. 它将从类的简单名称推导出来. com.example.Design-> "design"

If we rename the Taco class to Design ... We don't need to specify the name if the model attribute. It will be deduced from the simple name of the class. com.example.Design -> "design"

@PostMapping
public String processDesign(@Valid Design design, Errors errors) {

请参见用于ModelAttribute的javadoc :

默认模型属性名称是从已声明的属性推断出来的 属性类型(即方法参数类型或方法返回类型), 基于不合格的类别名称:例如类的"orderAddress" "mypackage.OrderAddress"或"orderAddressList" 列表".

The default model attribute name is inferred from the declared attribute type (i.e. the method parameter type or method return type), based on the non-qualified class name: e.g. "orderAddress" for class "mypackage.OrderAddress", or "orderAddressList" for "List".

这篇关于我们何时必须使用@ModelAttribute及其工作方式的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆