Mybatis实现批量插入和更新(Mybatis3.2源码修改)

来源:互联网 发布:matlab矩阵某两行相加 编辑:程序博客网 时间:2024/06/15 13:56


Mybatis框架针对批量方便存在一些缺陷,本文针对inser和update批量对Mybatis源码进行了修改,供大家参考:

 

PreparedStatementHandler.java

  public int update(Statement statement) throws SQLException {
    PreparedStatement ps = (PreparedStatement) statement;
    int rows=0 ;
//    System.out.println("this.mappedStatement.getId()"+this.mappedStatement.getId());
    if (this.mappedStatement.getId().endsWith("insertMany")||this.mappedStatement.getId().endsWith("updateManyByPrimaryKey")){
     int[] ints=ps.executeBatch();
     for(int i=0;i<ints.length;i++){
      rows +=ints[i];
     }
   
}else{
        ps.execute();
        rows = ps.getUpdateCount();
    }
    Object parameterObject = boundSql.getParameterObject();
    KeyGenerator keyGenerator = mappedStatement.getKeyGenerator();
    keyGenerator.processAfter(executor, mappedStatement, ps, parameterObject);
    return rows;
  }



DefaultParameterHandler.java

   public void setParameters(PreparedStatement ps) throws SQLException {
    ErrorContext.instance().activity("setting parameters").object(mappedStatement.getParameterMap().getId());
    List<ParameterMapping> parameterMappings = boundSql.getParameterMappings();
    if (parameterMappings != null) {
//      if (parameterObject!=null && parameterObject instanceof StrictMap ){
        if (this.mappedStatement.getId().endsWith("insertMany")||this.mappedStatement.getId().endsWith("updateManyByPrimaryKey")){
       List parameterObjectList =(List)((StrictMap )parameterObject).get("list");
       //List parameterObjectList =(List)parameterObject;
       for(int n=0;n<parameterObjectList.size();n++){
        Object paraObj=parameterObjectList.get(n); 
           for (int i = 0; i < parameterMappings.size(); i++) {
              ParameterMapping parameterMapping = parameterMappings.get(i);
              if (parameterMapping.getMode() != ParameterMode.OUT) {
                Object value;
                String propertyName = parameterMapping.getProperty();
                if (boundSql.hasAdditionalParameter(propertyName)) { // issue #448 ask first for additional params
                  value = boundSql.getAdditionalParameter(propertyName);
                } else if (paraObj == null) {
                  value = null;
                } else if (typeHandlerRegistry.hasTypeHandler(paraObj.getClass())) {
                  value = paraObj;
                } else {
                  MetaObject metaObject = configuration.newMetaObject(paraObj);
                  value = metaObject.getValue(propertyName);
                }
                TypeHandler typeHandler = parameterMapping.getTypeHandler();
                JdbcType jdbcType = parameterMapping.getJdbcType();
                if (value == null && jdbcType == null) jdbcType = configuration.getJdbcTypeForNull();
                typeHandler.setParameter(ps, i + 1, value, jdbcType);
              }
      }
         ps.addBatch(); 
       }
   
   }else{
       for (int i = 0; i < parameterMappings.size(); i++) {
         ParameterMapping parameterMapping = parameterMappings.get(i);
         if (parameterMapping.getMode() != ParameterMode.OUT) {
           Object value;
           String propertyName = parameterMapping.getProperty();
           if (boundSql.hasAdditionalParameter(propertyName)) { // issue #448 ask first for additional params
             value = boundSql.getAdditionalParameter(propertyName);
           } else if (parameterObject == null) {
             value = null;
           } else if (typeHandlerRegistry.hasTypeHandler(parameterObject.getClass())) {
             value = parameterObject;
           } else {
             MetaObject metaObject = configuration.newMetaObject(parameterObject);
             value = metaObject.getValue(propertyName);
           }
           TypeHandler typeHandler = parameterMapping.getTypeHandler();
           JdbcType jdbcType = parameterMapping.getJdbcType();
           if (value == null && jdbcType == null) jdbcType = configuration.getJdbcTypeForNull();
           typeHandler.setParameter(ps, i + 1, value, jdbcType);
         }
       }
      }  
    }
  }



修改Mybatis-generator代码生成器,使代码增加insertMany和updateManyByPrimaryKey两个方法:

Mapper.xml代码示例:

  <insert id="insertMany" parameterType="java.util.List">
    <!--
      WARNING - @mbggenerated
      This element is automatically generated by MyBatis Generator, do not modify.
    -->
    insert into Sys_User_Log_Info (ID, FUN_ID, OP_USER,
      OP_USER_NAME, OP_TXT, OP_DATE,
      F1, F2)
    values
(#{id,jdbcType=BIGINT}, #{funId,jdbcType=VARCHAR}, #{opUser,jdbcType=VARCHAR},
      #{opUserName,jdbcType=VARCHAR}, #{opTxt,jdbcType=VARCHAR}, #{opDate,jdbcType=DATE},
      #{f1,jdbcType=INTEGER}, #{f2,jdbcType=DECIMAL})
  </insert>


  <update id="updateManyByPrimaryKey" parameterType="java.util.List">
    <!--
      WARNING - @mbggenerated
      This element is automatically generated by MyBatis Generator, do not modify.
    -->
    update Sys_User_Log_Info
    set FUN_ID = #{funId,jdbcType=VARCHAR},
      OP_USER = #{opUser,jdbcType=VARCHAR},
      OP_USER_NAME = #{opUserName,jdbcType=VARCHAR},
      OP_TXT = #{opTxt,jdbcType=VARCHAR},
      OP_DATE = #{opDate,jdbcType=DATE},
      F1 = #{f1,jdbcType=INTEGER},
      F2 = #{f2,jdbcType=DECIMAL}
    where ID = #{id,jdbcType=BIGINT}
  </update>

Mapper代码示例:

int insertMany(List<SysUserLogInfo> list);
int updateManyByPrimaryKey(List<SysUserLogInfo> list);

修改之后可以实现:

 String resource = "mybatis-config.xml";
  try{
   //PropertyConfigurator.configure("log4j.properties");  
   long  start=System.currentTimeMillis();
           
   InputStream inputStream = Resources.getResourceAsStream(resource);
   SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
   long end=System.currentTimeMillis();
   System.out.println((end-start)/1000.0);
   
   SqlSession session = sqlSessionFactory.openSession();
   long end1=System.currentTimeMillis();
   System.out.println((end1-end)/1000.0);
   try {
    SysUserLogInfoMapper mapper=session.getMapper(SysUserLogInfoMapper.class);
    SysUserLogInfo sysInfo =mapper.selectByPrimaryKey(1000l);
    System.out.println(sysInfo.getOpUser()+sysInfo.getOpDate()+sysInfo.getF1()+sysInfo.getF2());
    List<SysUserLogInfo> ilist=UserSQLExecutor.queryList("select * from Sys_User_Log_Info", SysUserLogInfo.class,session.getConnection());
    sysInfo =ilist.get(0);
    System.out.println(sysInfo.getOpUser()+sysInfo.getOpDate()+sysInfo.getF1()+sysInfo.getF2());
    
    SysUserLogInfo sysInfo1=new SysUserLogInfo();
    SysUserLogInfo sysInfo2=new SysUserLogInfo();
    sysInfo1.setId(1003l);
    sysInfo1.setOpUser("1001 user1");
    sysInfo2.setId(1004l);
    sysInfo2.setOpUser("1002 user2");
    ArrayList<SysUserLogInfo> sysInfoList =new ArrayList<SysUserLogInfo>();
    sysInfoList.add(sysInfo1);
    sysInfoList.add(sysInfo2);
//    mapper.insertMany(sysInfoList);
    mapper.insertMany(sysInfoList);
    sysInfo1.setOpUser("1001 user3");
    sysInfo2.setOpUser("1002 user4");
    mapper.updateManyByPrimaryKey(sysInfoList);  

     session.commit();
   }catch(Exception e){
    session.rollback();
    e.printStackTrace();
    //session.rollback();
   } finally {
    session.close();
   }   

  }catch(Exception e){
   e.printStackTrace();

  }
  

   




0 0