SpringMVC数据传输&ModelAttribute注解详细说明

SpringMVC数据传输&ModelAttribute注解详细说明

** 测试ModelAttribute注解;**

package com.pzx.controller;

import com.pzx.bean.Book;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;

import java.util.Map;

/**
 * Created with IntelliJ IDEA.
 * @Author: pzx
 * @Date: 2021/08/19    17:52
 * @Version:1.0
 *
 * 测试ModelAttribute注解;
 * 使用场景;以书城的图书修改为例;
 * 1)、页面端;
 *        显示要修改的图书信息,图书的所有字段都在
 *2)、servlet收到请求调用dao:
 *          String sql = "update bs_book set title=? ,
 *          author=?,price=?
 *          ,sales=?,stock=?,img_path=?
 *          where id =?"
 * 3)实际场景?
 *          并不是全字段修改;只会修改部分字符按,已修改用户信息为例
 *          username        password        address
 *          1)、不修改的字段可以在页面展示,但是不要提供修改输入框;
 *          2)、为了简单,Controller直接在参数位置来写Book对象
 *          3)、SpringMVC为我们自动封装book;(没有带的值是null)
 *          4)、如果接下来调用了一个全字段更新的dao操作;会将其他的字段变成null;
 *                  sql="update bs_book set"
 *                  if(book.getBookName()){
 *                      sql +="bookName=?,"
 *                      }
 *
 *                    if(book.getPrice()){
 *                    sql +="price=?"
 *                  }
 *
 *4)、如何能保证全字段更新的时候,只更新了页面携带的数据
 *      1)、修改dao:代价太大
 *      2)、Book对象是如何封装的?
 *              1)、SpringMVC创建一个book对象,bookName默认就是null;
 *                      1、让SpringMVC别创建对象,直接从数据库中先取出id等于100的book的信息
 *                      2、Book{id=100, bookName='西游记', author='彭着想', stock=200000, sales=19999}
 *              2)、将请求中所有的book对应的属性一一设置过来;
 *                      3、使用刚才从数据库中取出的book对象,给他设置值;(请求参数带了哪些就覆盖之前的值)
 *                      4、带了的字段就改为携带的值,没带的字段就保持之前的值
 *
 *              3)、调用全字段更新就有问题;
 *                      5、将之前从数据库中查到的对象,并且封装到请求参数的对象。进行保存;
 *
 *
 *
 *
 *
 */
@Controller
public class ModelAttributeTestController {


    private Object object1;
    private Object object2;
    private Object b1;
    private Object b2;


    /**
     *  可以告诉SpringMVC不要new这个book了,我刚才保存了一个book
     *  那个就是从数据库中查询出来的;用我这个book?
     *
     *  同是BindingAwareModelMap
     *
     * @param book
     * @return
     */
    @RequestMapping("/updateBook")
    public String updateBook(@ModelAttribute("book") Book book, Map<String,Object> map) {
        object2 = map;
        Object book1 = map.get("book");
        b2=book;
        System.out.println("传入的model" + map.getClass());
        System.out.println("object1==object2?" + (object1 == object2));
        System.out.println("b1==b2?" + (b1 == b2)+"--------------->b2==book1"+(b2==book1));


        System.out.println("页面提交过来的图书信息:" + book);


        //bookDao.update(book);
        //Book{id=100, bookName='null', author='彭着想', stock=200000, sales=19999}
        /**
         *  *          String sql = "update bs_book set title=? ,
         *  *          author=?,price=?
         *  *          ,sales=?,stock=?,img_path=?
         *  *          where id =?"
         */


        return "success";

    }


    /**
     *
     * 1)、SpringMVC要封装请求参数的Book对象不应该是自己去new对象。
     *      而应该是【从数据库中】拿到的准备好的对象
     *2)、再来使用这个对象来封装请求参数
     *
     *
     *
     * ModelAttribute
     *      能够标在:
     *              参数位置:取出刚才保存的数据
     *              方法位置:这个方法就会提前于目标方法先运行
     *                        1)、 @ModelAttribute 我们可以在这里提前查出数据库中图书的信息
     *                        2)、将这个图书信息保存起来(方便下一个方法使用)
     *
     */

    @ModelAttribute
    public void hahaMyModelAttribute(Map<String,Object> map) {
        Book book = new Book(100, "西游记", "吴承恩", 12.58, 1000, 100);
        System.out.println("数据库中查到的图书信息是" + book);
        map.put("book", book);
        object1 = map;
        b1=book;
        System.out.println("ModelAttribute方法....查询了图书并且保存了起来...他用的map类型" + map.getClass());
    }


}

SpringMVC数据传输

package com.pzx.controller;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.SessionAttributes;
import org.springframework.web.servlet.ModelAndView;

import java.util.Map;

/**
 * Created with IntelliJ IDEA.
 * @Author: pzx
 * @Date: 2021/08/19    13:07
 * @Version:1.0
 *
 *SpringMVC除过传入原生的request和session还能怎么样把数据带给页面
 *
 * 1)、可以在方法处传入Map或者Model或者ModelMap。
 * 给这些参数保存的数据都会放在域中。可以在页面获取(最终都放在了请求域中了)
 *     关系:
 *          Map,Model,ModelMap:最终都是BindingAwareModelMap在工作;
 *          相当于BindingAwareModelMap中保存的东西都会放在请求域中;
 *
 *          Map(interface(jdk))        Model(interface(Spring))
 *                 ||                      //
 *                 ||                     //
 *                 \/                   //
 *          ModelMap(class)            //
 *              \\                   //
 *               \\                 //
 *                \\              //
 *                ExtendedModelMap
 *                     ||
 *                    \/
 *              BindingAwareModelMap
 *
 *
 *2)、方法的返回值可以变为ModelAndView类型;
 *              既包含视图信息(页面地址)也包含模型信息(给页面带的数据);
 *              而且数据是放在请求域中的;
 *              request,session,application
 *
 *3)、SpringMVC提供了一种可以提供给Session域中保存数据的方式
 * 使用一个注解       @SessionAttributes(只能标在类上)
 *@SessionAttributes(value = "msg"):
 *                  给BindingAwareModelMap中保存的数据,或者是ModelAndView中的数据同时给session中放一份
 *                  value指定保存数据时要给session中放的key
 *      value={"msg"}:只要保存的是key的数据,给session中放一份
 *      types = {String.class}:只要保存的是这种类型的时候,给session也放一份
 *
 * 后来推荐@SessionAttributes别用了,可能会引发异常;
 * 给session中放数据请使用原生的API;
 *
 *
 *
 */
@Controller
@SessionAttributes(value = {"hah","msg"},types = {String.class})
public class OutputController {

    @RequestMapping("/handle01")
    public String handle01(Map<String,Object> map){
        map.put("msg","你好");
        map.put("hah","哈哈哈哈,傻逼");
        System.out.println("map的类型"+map.getClass());

        return "success";
    }


    /**
     *
     * @param model
     * @return
     */
    @RequestMapping("/handle02")
    public String handle02(Model model){
        model.addAttribute("msg","你好坏!");
        model.addAttribute("hah",18);
        System.out.println("model的类型"+model.getClass());
        return "success";
    }


    @RequestMapping("/handle03")
    public String handle03(ModelMap modelMap){
        modelMap.addAttribute("msg","你好骚!");
        System.out.println("modelMap的类型"+modelMap.getClass());
        return "success";
    }

    /**
     * 返回值是ModelAndView;可以为页面携带数据
     * @param modelMap
     * @return
     */
    @RequestMapping("/handle04")
    public ModelAndView handle04(ModelMap modelMap){
        //之前的返回值就叫视图名;视图名视图解析器会帮我们最终拼串得到页面的真实地址
        //这个success就是要跳转的页面
//        ModelAndView mv = new ModelAndView("success");
        ModelAndView mv = new ModelAndView();
        mv.setViewName("success");
        mv.addObject("msg","你好肿瘤君!");
        return mv;
    }



}

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值