Browse Source

Config OptLock & MetaObject will cause updateFill() not work for updateById()

yuxiaobin 8 years ago
parent
commit
1922fe262a

+ 8 - 1
src/main/java/com/baomidou/mybatisplus/MybatisDefaultParameterHandler.java

@@ -138,7 +138,14 @@ public class MybatisDefaultParameterHandler extends DefaultParameterHandler {
                     if (map.containsKey("et")) {
                     if (map.containsKey("et")) {
                         Object et = map.get("et");
                         Object et = map.get("et");
                         if (et != null) {
                         if (et != null) {
-                            tableInfo = TableInfoHelper.getTableInfo(et.getClass());
+                            if(et instanceof Map){
+                                Map realEtMap = (Map) et;
+                                if(realEtMap.containsKey("MP_OPTLOCK_ET_ORIGINAL")){//refer to OptimisticLockerInterceptor.MP_OPTLOCK_ET_ORIGINAL
+                                    tableInfo = TableInfoHelper.getTableInfo(realEtMap.get("MP_OPTLOCK_ET_ORIGINAL").getClass());
+                                }
+                            }else {
+                                tableInfo = TableInfoHelper.getTableInfo(et.getClass());
+                            }
                         }
                         }
                     }
                     }
                 } else {
                 } else {

+ 2 - 0
src/main/java/com/baomidou/mybatisplus/plugins/OptimisticLockerInterceptor.java

@@ -56,6 +56,7 @@ public class OptimisticLockerInterceptor implements Interceptor {
 
 
     private static final String MP_OPTLOCK_VERSION_ORIGINAL = "MP_OPTLOCK_VERSION_ORIGINAL";
     private static final String MP_OPTLOCK_VERSION_ORIGINAL = "MP_OPTLOCK_VERSION_ORIGINAL";
     private static final String MP_OPTLOCK_VERSION_COLUMN = "MP_OPTLOCK_VERSION_COLUMN";
     private static final String MP_OPTLOCK_VERSION_COLUMN = "MP_OPTLOCK_VERSION_COLUMN";
+    public static final String MP_OPTLOCK_ET_ORIGINAL = "MP_OPTLOCK_ET_ORIGINAL";
     private static final String NAME_ENTITY = "et";
     private static final String NAME_ENTITY = "et";
     private static final String NAME_ENTITY_WRAPPER = "ew";
     private static final String NAME_ENTITY_WRAPPER = "ew";
     private static final String PARAM_UPDATE_METHOD_NAME = "update";
     private static final String PARAM_UPDATE_METHOD_NAME = "update";
@@ -134,6 +135,7 @@ public class OptimisticLockerInterceptor implements Interceptor {
                         entityMap.put(versionField.getName(), getUpdatedVersionVal(originalVersionVal));
                         entityMap.put(versionField.getName(), getUpdatedVersionVal(originalVersionVal));
                         entityMap.put(MP_OPTLOCK_VERSION_ORIGINAL, originalVersionVal);
                         entityMap.put(MP_OPTLOCK_VERSION_ORIGINAL, originalVersionVal);
                         entityMap.put(MP_OPTLOCK_VERSION_COLUMN, versionColumnName);
                         entityMap.put(MP_OPTLOCK_VERSION_COLUMN, versionColumnName);
+                        entityMap.put(MP_OPTLOCK_ET_ORIGINAL, et);
                         map.put(NAME_ENTITY, entityMap);
                         map.put(NAME_ENTITY, entityMap);
                     }
                     }
                 }
                 }

+ 193 - 0
src/test/java/com/baomidou/mybatisplus/test/h2/H2MetaObjAndVersionAndOptLockTest.java

@@ -0,0 +1,193 @@
+package com.baomidou.mybatisplus.test.h2;
+
+import java.io.IOException;
+import java.math.BigDecimal;
+import java.sql.Connection;
+import java.sql.SQLException;
+import java.sql.Statement;
+import java.text.SimpleDateFormat;
+import java.util.Calendar;
+import java.util.Date;
+
+import javax.sql.DataSource;
+
+import org.junit.Assert;
+import org.junit.BeforeClass;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.context.ApplicationContext;
+import org.springframework.context.support.ClassPathXmlApplicationContext;
+import org.springframework.test.context.ContextConfiguration;
+import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
+
+import com.baomidou.mybatisplus.mapper.Condition;
+import com.baomidou.mybatisplus.mapper.EntityWrapper;
+import com.baomidou.mybatisplus.test.h2.config.DBConfig;
+import com.baomidou.mybatisplus.test.h2.config.MybatisConfigMetaObjOptLockConfig;
+import com.baomidou.mybatisplus.test.h2.entity.mapper.H2UserVersionAndLogicDeleteMapper;
+import com.baomidou.mybatisplus.test.h2.entity.persistent.H2UserVersionAndLogicDeleteEntity;
+
+/**
+ * <p>
+ * </p>
+ *
+ * @author yuxiaobin
+ * @date 2017/6/29
+ */
+@RunWith(SpringJUnit4ClassRunner.class)
+@ContextConfiguration(classes = {DBConfig.class, MybatisConfigMetaObjOptLockConfig.class})
+public class H2MetaObjAndVersionAndOptLockTest extends H2Test{
+
+    @BeforeClass
+    public static void initDB() throws SQLException, IOException {
+        @SuppressWarnings("resource")
+        ApplicationContext context = new ClassPathXmlApplicationContext("classpath:h2/spring-test-h2-metaobj.xml");
+        DataSource ds = (DataSource) context.getBean("dataSource");
+        try (Connection conn = ds.getConnection()) {
+            String createTableSql = readFile("user.ddl.sql");
+            Statement stmt = conn.createStatement();
+            stmt.execute(createTableSql);
+            stmt.execute("truncate table h2user");
+            executeSql(stmt, "user.insert.sql");
+            conn.commit();
+        }
+    }
+
+    @Autowired
+    H2UserVersionAndLogicDeleteMapper userMapper;
+
+    @Test
+    public void testInsert(){
+        Long id = 991L;
+        H2UserVersionAndLogicDeleteEntity user = new H2UserVersionAndLogicDeleteEntity();
+        user.setId(id);
+        user.setName("991");
+        user.setAge(91);
+        user.setPrice(BigDecimal.TEN);
+        user.setDesc("asdf");
+        user.setTestType(1);
+        user.setVersion(1);
+        userMapper.insertAllColumn(user);
+
+        H2UserVersionAndLogicDeleteEntity userDB = userMapper.selectById(id);
+        Assert.assertEquals(null, userDB.getTestDate());
+
+        userDB.setName("991");
+        userMapper.updateById(userDB);
+
+        userDB = userMapper.selectById(id);
+        Assert.assertEquals("991", userDB.getName());
+    }
+
+    @Test
+    public void testUpdateByEntityWrapperNoDateVersion() {
+        Long id = 992L;
+        H2UserVersionAndLogicDeleteEntity user = new H2UserVersionAndLogicDeleteEntity();
+        user.setId(id);
+        user.setName("992");
+        user.setAge(92);
+        user.setPrice(BigDecimal.TEN);
+        user.setDesc("asdf");
+        user.setTestType(1);
+        user.setVersion(1);
+        userMapper.insertAllColumn(user);
+
+        H2UserVersionAndLogicDeleteEntity userDB = userMapper.selectById(id);
+
+        H2UserVersionAndLogicDeleteEntity updUser = new H2UserVersionAndLogicDeleteEntity();
+        updUser.setName("999");
+
+        userMapper.update(updUser, new EntityWrapper<>(userDB));
+
+        userDB = userMapper.selectById(id);
+        Assert.assertEquals("999", userDB.getName());
+    }
+
+    @Test
+    public void testUpdateByIdWithDateVersion() {
+        Long id = 994L;
+        H2UserVersionAndLogicDeleteEntity user = new H2UserVersionAndLogicDeleteEntity();
+        user.setId(id);
+        user.setName("994");
+        user.setAge(91);
+        user.setPrice(BigDecimal.TEN);
+        user.setDesc("asdf");
+        user.setTestType(1);
+        user.setVersion(1);
+        Calendar cal = Calendar.getInstance();
+        cal.add(Calendar.DAY_OF_MONTH, -1);
+        user.setTestDate(cal.getTime());
+        userMapper.insertAllColumn(user);
+
+        System.out.println("before update: testDate=" + user.getTestDate());
+        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH");
+        H2UserVersionAndLogicDeleteEntity userDB = userMapper.selectById(id);
+
+        Assert.assertNotNull(userDB.getTestDate());
+        String originalDateVersionStr = sdf.format(cal.getTime());
+        Assert.assertEquals(originalDateVersionStr, sdf.format(userDB.getTestDate()));
+
+        userDB.setName("991");
+        userMapper.updateById(userDB);
+        userDB = userMapper.selectById(id);
+        Assert.assertEquals("991", userDB.getName());
+        Date versionDate = userDB.getTestDate();
+        System.out.println("after update: testDate=" + versionDate);
+        String versionDateStr = sdf.format(versionDate);
+        Assert.assertEquals(sdf.format(new Date()), versionDateStr);
+
+        Assert.assertNotEquals(originalDateVersionStr, versionDateStr);
+
+    }
+
+    @Test
+    public void testUpdateByEntityWrapperWithDateVersion() {
+        Long id = 993L;
+        H2UserVersionAndLogicDeleteEntity user = new H2UserVersionAndLogicDeleteEntity();
+        user.setId(id);
+        user.setName("992");
+        user.setAge(92);
+        user.setPrice(BigDecimal.TEN);
+        user.setDesc("asdf");
+        user.setTestType(1);
+        user.setVersion(1);
+        Calendar cal = Calendar.getInstance();
+        cal.add(Calendar.DAY_OF_MONTH, -1);
+        user.setTestDate(cal.getTime());
+        userMapper.insertAllColumn(user);
+
+        H2UserVersionAndLogicDeleteEntity userDB = userMapper.selectById(id);
+
+        H2UserVersionAndLogicDeleteEntity updUser = new H2UserVersionAndLogicDeleteEntity();
+        updUser.setName("999");
+        userDB.setVersion(null);
+        userMapper.update(updUser, new EntityWrapper<>(userDB));
+
+        System.out.println("before update: testDate=" + userDB.getTestDate());
+        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH");
+
+        userDB = userMapper.selectById(id);
+        Assert.assertEquals("999", userDB.getName());
+
+        Date versionDate = userDB.getTestDate();
+        System.out.println("after update: testDate=" + versionDate);
+        String versionDateStr = sdf.format(versionDate);
+        Assert.assertEquals(sdf.format(new Date()), versionDateStr);
+    }
+
+
+    @Test
+    public void testLogicDeleted() {
+        H2UserVersionAndLogicDeleteEntity user = new H2UserVersionAndLogicDeleteEntity();
+        user.setAge(1);
+        user.setPrice(new BigDecimal("9.99"));
+        user.setVersion(-1);
+        userMapper.insert(user);
+        Long id = user.getId();
+        Assert.assertNotNull(id);
+        Assert.assertNotNull(userMapper.selectList(Condition.create().orderBy("age")));
+        H2UserVersionAndLogicDeleteEntity userFromDB = userMapper.selectById(user.getId());
+        Assert.assertNull(userFromDB);
+    }
+}

+ 64 - 0
src/test/java/com/baomidou/mybatisplus/test/h2/config/MybatisConfigMetaObjOptLockConfig.java

@@ -0,0 +1,64 @@
+package com.baomidou.mybatisplus.test.h2.config;
+
+import javax.sql.DataSource;
+
+import org.apache.ibatis.plugin.Interceptor;
+import org.apache.ibatis.session.SqlSessionFactory;
+import org.apache.ibatis.type.JdbcType;
+import org.mybatis.spring.annotation.MapperScan;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.core.io.ResourceLoader;
+
+import com.baomidou.mybatisplus.MybatisConfiguration;
+import com.baomidou.mybatisplus.MybatisXMLLanguageDriver;
+import com.baomidou.mybatisplus.entity.GlobalConfiguration;
+import com.baomidou.mybatisplus.mapper.LogicSqlInjector;
+import com.baomidou.mybatisplus.plugins.OptimisticLockerInterceptor;
+import com.baomidou.mybatisplus.plugins.PaginationInterceptor;
+import com.baomidou.mybatisplus.plugins.PerformanceInterceptor;
+import com.baomidou.mybatisplus.spring.MybatisSqlSessionFactoryBean;
+import com.baomidou.mybatisplus.test.h2.H2MetaObjectHandler;
+
+/**
+ * <p>
+ * MetaObj
+ * </p>
+ *
+ * @author yuxiaobin
+ * @date 2017/6/29
+ */
+@Configuration
+@MapperScan("com.baomidou.mybatisplus.test.h2.entity.mapper")
+public class MybatisConfigMetaObjOptLockConfig {
+
+    @Bean("mybatisSqlSession")
+    public SqlSessionFactory sqlSessionFactory(DataSource dataSource, ResourceLoader resourceLoader, GlobalConfiguration globalConfiguration) throws Exception {
+        MybatisSqlSessionFactoryBean sqlSessionFactory = new MybatisSqlSessionFactoryBean();
+        sqlSessionFactory.setDataSource(dataSource);
+//        sqlSessionFactory.setConfigLocation(resourceLoader.getResource("classpath:mybatis-config.xml"));
+        sqlSessionFactory.setTypeAliasesPackage("com.baomidou.mybatisplus.test.h2.entity.persistent");
+        MybatisConfiguration configuration = new MybatisConfiguration();
+        configuration.setDefaultScriptingLanguage(MybatisXMLLanguageDriver.class);
+        configuration.setJdbcTypeForNull(JdbcType.NULL);
+        sqlSessionFactory.setConfiguration(configuration);
+        PaginationInterceptor pagination = new PaginationInterceptor();
+        sqlSessionFactory.setPlugins(new Interceptor[]{
+                pagination,
+                new PerformanceInterceptor(),
+                new OptimisticLockerInterceptor()
+        });
+        sqlSessionFactory.setGlobalConfig(globalConfiguration);
+        return sqlSessionFactory.getObject();
+    }
+
+    @Bean
+    public GlobalConfiguration globalConfiguration() {
+        GlobalConfiguration globalConfiguration = new GlobalConfiguration(new LogicSqlInjector());
+        globalConfiguration.setLogicDeleteValue("-1");
+        globalConfiguration.setLogicNotDeleteValue("1");
+        globalConfiguration.setIdType(2);
+        globalConfiguration.setMetaObjectHandler(new H2MetaObjectHandler());
+        return globalConfiguration;
+    }
+}

+ 16 - 0
src/test/java/com/baomidou/mybatisplus/test/h2/entity/mapper/H2UserVersionAndLogicDeleteMapper.java

@@ -0,0 +1,16 @@
+package com.baomidou.mybatisplus.test.h2.entity.mapper;
+
+import com.baomidou.mybatisplus.mapper.BaseMapper;
+import com.baomidou.mybatisplus.test.h2.entity.persistent.H2UserVersionAndLogicDeleteEntity;
+
+/**
+ * <p>
+ * 带version和逻辑删除
+ * </p>
+ *
+ * @author yuxiaobin
+ * @date 2017/6/29
+ */
+public interface H2UserVersionAndLogicDeleteMapper extends BaseMapper<H2UserVersionAndLogicDeleteEntity>{
+
+}

+ 114 - 0
src/test/java/com/baomidou/mybatisplus/test/h2/entity/persistent/H2UserVersionAndLogicDeleteEntity.java

@@ -0,0 +1,114 @@
+/**
+ * Copyright (c) 2011-2014, hubin (jobob@qq.com).
+ * <p>
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ * <p>
+ * http://www.apache.org/licenses/LICENSE-2.0
+ * <p>
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+package com.baomidou.mybatisplus.test.h2.entity.persistent;
+
+import java.io.Serializable;
+import java.math.BigDecimal;
+import java.util.Date;
+
+import com.baomidou.mybatisplus.annotations.TableField;
+import com.baomidou.mybatisplus.annotations.TableId;
+import com.baomidou.mybatisplus.annotations.TableLogic;
+import com.baomidou.mybatisplus.annotations.TableName;
+import com.baomidou.mybatisplus.annotations.Version;
+import com.baomidou.mybatisplus.enums.FieldStrategy;
+
+import lombok.Data;
+import lombok.experimental.Accessors;
+
+/**
+ * <p>
+ * 测试用户类
+ * </p>
+ *
+ * @author hubin sjy
+ */
+/* 表名 value 注解【 驼峰命名可无 】, resultMap 注解测试【 映射 xml 的 resultMap 内容 】 */
+@Data
+@Accessors(chain = true)
+@TableName("h2user")
+public class H2UserVersionAndLogicDeleteEntity implements Serializable {
+
+    /* 表字段注解,false 表中不存在的字段,可无该注解 默认 true */
+    @TableField(exist = false)
+    private static final long serialVersionUID = 1L;
+
+    /* 主键ID 注解,value 字段名,type 用户输入ID */
+    @TableId(value = "test_id")
+    private Long id;
+
+    /* 测试忽略验证 */
+    private String name;
+
+    private Integer age;
+
+    /*BigDecimal 测试*/
+    private BigDecimal price;
+
+    /* 测试下划线字段命名类型, 字段填充 */
+    @TableField(value = "test_type", strategy = FieldStrategy.IGNORED)
+    private Integer testType;
+
+    private String desc;
+
+    @TableLogic
+    private Integer version;
+
+    @TableField(value = "test_date")
+    @Version
+    private Date testDate;
+
+    public H2UserVersionAndLogicDeleteEntity() {
+
+    }
+
+    public H2UserVersionAndLogicDeleteEntity(String name) {
+        this.name = name;
+    }
+
+    public H2UserVersionAndLogicDeleteEntity(Integer testType) {
+        this.testType = testType;
+    }
+
+    public H2UserVersionAndLogicDeleteEntity(String name, Integer age) {
+        this.name = name;
+        this.age = age;
+    }
+
+    public H2UserVersionAndLogicDeleteEntity(Long id, String name) {
+        this.id = id;
+        this.name = name;
+    }
+
+    public H2UserVersionAndLogicDeleteEntity(Long id, Integer age) {
+        this.id = id;
+        this.age = age;
+    }
+
+    public H2UserVersionAndLogicDeleteEntity(Long id, String name, Integer age, Integer testType) {
+        this.id = id;
+        this.name = name;
+        this.age = age;
+        this.testType = testType;
+    }
+
+    public H2UserVersionAndLogicDeleteEntity(String name, Integer age, Integer testType) {
+        this.name = name;
+        this.age = age;
+        this.testType = testType;
+    }
+
+}