美文网首页慕课电商项目一期的思考与总结
[慕课电商项目] 01.对 mybatis 逆向工程生成的 xm

[慕课电商项目] 01.对 mybatis 逆向工程生成的 xm

作者: KK在1996 | 来源:发表于2018-09-21 10:34 被阅读0次

一、insert 语句的总结

1. 插入的时候,如果插入了自增的id

  • id值如果在该表中不存在,并且其他字段没有错误的话,mysql 会插入该行数据。
    • 如果插入的 id 的值大于表自增的值,那么表自增的值就更新到这个id值。例如,表的自增主键在被手动插入后的最大的 id 值为100,那么下一个自动插入的 id 就递增到了101。
  • id值在该表中已经存在了,那么就会报异常org.springframework.dao.DuplicateKeyException

2. 对返回值的处理

  我们应该事先初始化一个值为0的 int 变量,然后对执行 insert 的方法进行 try-catch 异常捕获,根据是否捕获到异常来决定接下来怎么做。

3. 代码演示:

    @Test
    public void insertSelectiveWithoutTime() throws Exception {
        //RandomUser.getNormalUser() 没有设置createTime, updateTime 
        //它们都为null
        User user = RandomUser.getNormalUser();

        //故意设置一个重复的 自增id,那么会捕获到异常,count 将为 0
        //user.setId(90);
        System.out.println(user);

        int count = 0;
        try {
            count = userMapper.insertSelectiveWithoutTime(user);
        }catch (Exception e) {
            System.out.println("出现了异常: " + e);
        }

        System.out.println("count: " + count);
    }

二、对 mybatis 逆向工程生成的 xml 的改进

1.问题缘由:

   电商项目中数据库的每一张表都包含创建时间和更新时间字段,为什么所有的表都需要这两个字段呢?
  • 好处:不仅可以简单的记录下操作时间,而且这两个字段也可以用于以后数据分析中。
  • 必要性:
    • 创建时间:大部分数据在创建了之后就不会更新了。
    • 更新时间:如果数据需要大量的更新,那么我们也不可能记录每一次的更新时间,最好的方式是记录最后一次的更新时间。

2.思考点:

(1)创建时间和更新时间的值有必要交给 java 代码来做吗?
(2)让数据库去做这个是不是更适合,更方便些?

3.对 mybatis 逆向工程生成的映射文件的改进

(1) 分析

   我们只需要修改 xml 中的 insert 和 update 语句即可。insert 语句插入的是一条全新的记录,我们要让数据库给出更新时间,创建时间的值。而对于 update 语句,我们只管最后的更新时间即可,创建时间已经在 insert 的时候插入到数据库中了。所以,数据库要给出更新时间的值,还要删掉原来 update 语句中的 create_time 的相关片段。在这里使用 mysql 的 now() 来生成时间。

   注意: 在 mybatis 生成的 xml 中有一种 Selective 的实现。我们在 service 代码中也经常会调用它。这里的 insert 语句会包含(列名1,列名2,... ,列名n)values (值1,值2,... ,值n)。它根据传来的 pojo 的属性值是否为 null 来决定是否要更改数据库对应的那一列。

/* 列中包含的字段:(列名1,列名2,... ,列名n) */
<trim prefix="(" suffix=")" suffixOverrides="," >
      <if test="id != null" >
        id,
      </if>
      <if test="username != null" >
        username,
      </if>
      ...
</trim>
/* values 中包含的字段:values (值1,值2,... ,值n) */
<trim prefix="values (" suffix=")" suffixOverrides="," >
      <if test="id != null" >
        #{id,jdbcType=INTEGER},
      </if>
      <if test="username != null" >
        #{username,jdbcType=VARCHAR},
      </if>
       ...
</trim>

   我们要想,每次 insert 都一定要插入创建时间和更新时间的,而不是根据传来的 pojo 的 createTime ,updateTime 的值是否为null 来决定插入。所以,我们要在 Selective 类型的实现中,不让这两个属性 Selective ,而是直接确定好。
   (createTime 和 updateTime 内心OS:这是不是有一种钦定的感觉?)

(2) 具体代码

(注意对应的列与值的位置,在更改的时候很容易搞混)

  1. 复杂的 insert

insert:

<insert id="insertWithoutTime" parameterType="top.kongk.mmall.pojo.User">
    insert into mmall_user (id, username, password,email, phone, question, answer, role,
      create_time, update_time)
    values (#{id,jdbcType=INTEGER}, #{username,jdbcType=VARCHAR}, #{password,jdbcType=VARCHAR},#{email,jdbcType=VARCHAR},
      #{phone,jdbcType=VARCHAR}, #{question,jdbcType=VARCHAR}, #{answer,jdbcType=VARCHAR}, #{role,jdbcType=INTEGER},
      now(), now())
  /*这两个 now() 对应 create_time 和 update_time*/
  </insert>

insertSelective :

<insert id="insertSelectiveWithoutTime" parameterType="top.kongk.mmall.pojo.User" >
    insert into mmall_user
    <trim prefix="(" suffix=")" suffixOverrides="," >
      <if test="id != null" >
        id,
      </if>
      <if test="username != null" >
        username,
      </if>
      <if test="password != null" >
        password,
      </if>
      <if test="email != null" >
        email,
      </if>
      <if test="phone != null" >
        phone,
      </if>
      <if test="question != null" >
        question,
      </if>
      <if test="answer != null" >
        answer,
      </if>
      <if test="role != null" >
        role,
      </if>
        /*被钦定的 createTime 和 updateTime 的列名*/
        create_time, update_time,
    </trim>

    <trim prefix="values (" suffix=")" suffixOverrides="," >
      <if test="id != null" >
        #{id,jdbcType=INTEGER},
      </if>
      <if test="username != null" >
        #{username,jdbcType=VARCHAR},
      </if>
      <if test="password != null" >
        #{password,jdbcType=VARCHAR},
      </if>
      <if test="email != null" >
        #{email,jdbcType=VARCHAR},
      </if>
      <if test="phone != null" >
        #{phone,jdbcType=VARCHAR},
      </if>
      <if test="question != null" >
        #{question,jdbcType=VARCHAR},
      </if>
      <if test="answer != null" >
        #{answer,jdbcType=VARCHAR},
      </if>
      <if test="role != null" >
        #{role,jdbcType=INTEGER},
      </if>
        /*被钦定的 createTime 和 updateTime 的值*/
        now(), now(),
    </trim>
  </insert>

2.简单的 update

updateByPrimaryKey :

<update id="updateByPrimaryKey" parameterType="top.kongk.mmall.pojo.User" >
    update mmall_user
    set username = #{username,jdbcType=VARCHAR},
      password = #{password,jdbcType=VARCHAR},
      email = #{email,jdbcType=VARCHAR},
      phone = #{phone,jdbcType=VARCHAR},
      question = #{question,jdbcType=VARCHAR},
      answer = #{answer,jdbcType=VARCHAR},
      role = #{role,jdbcType=INTEGER},
      /*被注释的 create_time = */
      update_time = now()
    where id = #{id,jdbcType=INTEGER}
  </update>

updateByPrimaryKeySelective :

<update id="updateByPrimaryKeySelective" parameterType="top.kongk.mmall.pojo.User" >
    update mmall_user
    <set >
      <if test="username != null" >
        username = #{username,jdbcType=VARCHAR},
      </if>
      <if test="password != null" >
        password = #{password,jdbcType=VARCHAR},
      </if>
      <if test="email != null" >
        email = #{email,jdbcType=VARCHAR},
      </if>
      <if test="phone != null" >
        phone = #{phone,jdbcType=VARCHAR},
      </if>
      <if test="question != null" >
        question = #{question,jdbcType=VARCHAR},
      </if>
      <if test="answer != null" >
        answer = #{answer,jdbcType=VARCHAR},
      </if>
      <if test="role != null" >
        role = #{role,jdbcType=INTEGER},
      </if>
      <!-- 被注释掉的 createTime 
        <if test="createTime != null" >
          create_time = #{createTime,jdbcType=TIMESTAMP},
        </if>
      -->
      <if test="updateTime != null" >
        update_time = now(),
      </if>
    </set>
    where id = #{id,jdbcType=INTEGER}
  </update>

相关文章

网友评论

    本文标题:[慕课电商项目] 01.对 mybatis 逆向工程生成的 xm

    本文链接:https://www.haomeiwen.com/subject/xlfanftx.html