Spring MVC 使用 GET 请求提交和绑定对象

Spring MVC submit and bind object with a GET Request

我喜欢在编辑表单中显示之前从另一页选择的对象。选择页面通过 GET 将所选对象的 ID 传输到我的控制器。

如何强制参数绑定到消息对象,然后使用我的 属性 编辑器自动初始化?

目前我总是得到一个设置了 id 属性 但未通过我的 属性 编辑器初始化的新对象。我的 GET 请求中缺少什么?

示例选择 JSP 页面,它将通过 GET 请求将 id 传输到我的控制器:

<a href="message?id=${message.id}">${message.title}</a>

我的带有 PropertyEditor class 和 InitBind 方法的控制器

@Controller
public class MessageController {

  @Autowired
  private MessageRepository messageRepository;

  @RequestMapping(value="/message", method = RequestMethod.GET)
  public String handleMessage(Model model,@ModelAttribute("message") Message message) {

    // ISSUE Here the message object has only the "id" property set but get not initialized through the binder 
    System.out.println(message);

    return "message";
  }

  // inline property editor for message class 
  public class MessagePropertyEditor extends PropertyEditorSupport {
       @Override
       public String getAsText() {
          return String.valueOf(((Message) getValue()).getId());
       }

      @Override
      public void setAsText(String id) throws IllegalArgumentException {
          Message message = messageRepository.getMessageById(Integer.valueOf(id));
        setValue(message);
      }
    }

  @InitBinder
  public void initBinder(WebDataBinder binder) {
     binder.registerCustomEditor(Message.class, new MessagePropertyEditor());
  }
}

示例消息 bean class

public class Message {
  private int id;

  private String title;

  private String text;

  // getter & setter methods
}

我建议在 @RequestMapping 方法旁边使用 @ModelAttribute 注释方法,而不是使用 PropertyEditor

@ModelAttribute
public Message modelAttribute(@RequestParam("id") int id) {
    return messageRepository.getMessageById(id);
}

保持 @RequestMapping 不变,您可以删除 MessagePropertyEditor@InitBinder 注释方法。这会导致这样的结果。

@Controller
@RequestMapping("/message")
public class MessageController {

  @Autowired
  private MessageRepository messageRepository;

  @ModelAttribute
  public Message modelAttribute(@RequestParam("id") int id) {
      return messageRepository.getMessageById(id);
  }

  @GetMapping
  public String handleMessage(Model model,@ModelAttribute("message") Message message) {
    System.out.println(message);

    return "message";
  }
}

将@RequestParam("id") 添加到参数消息中,如下所示:

public String handleMessage(Model model,@RequestParam("id") @ModelAttribute("message") Message message)