From ba9597a81253e5601d8bca4f891f05ab05f897b2 Mon Sep 17 00:00:00 2001 From: zhou-hao Date: Thu, 12 Apr 2018 22:59:05 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BC=98=E5=8C=96=E6=9E=9A=E4=B8=BE=E5=AD=97?= =?UTF-8?q?=E5=85=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../dao/mybatis/EnumDictHandlerRegister.java | 104 ++++++++++++++++++ .../dao/mybatis/MyBatisAutoConfiguration.java | 8 +- .../builder/jpa/JpaAnnotationParser.java | 16 ++- .../builder/jpa/JpaAnnotationParserTest.java | 2 +- .../dao/mybatis/builder/jpa/TestEntity.java | 4 + .../web/commons/entity/DataStatus.java | 7 +- .../web/commons/entity/DataStatusEnum.java | 18 +++ .../org/hswebframework/web/dict/EnumDict.java | 18 ++- .../web/dict/defaults/TrueOrFalse.java | 19 ++++ .../web/validate/ValidateResults.java | 2 +- .../web/validate/ValidationException.java | 1 + .../web/bean/FastBeanCopierTest.java | 6 +- .../web/dict/DictDefineTest.java | 1 - .../AuthorizationSettingMenuService.java | 1 - .../simple/SimpleScheduleJobService.java | 42 ++++--- 15 files changed, 213 insertions(+), 36 deletions(-) create mode 100644 hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/EnumDictHandlerRegister.java create mode 100644 hsweb-commons/hsweb-commons-entity/src/main/java/org/hswebframework/web/commons/entity/DataStatusEnum.java create mode 100644 hsweb-core/src/main/java/org/hswebframework/web/dict/defaults/TrueOrFalse.java diff --git a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/EnumDictHandlerRegister.java b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/EnumDictHandlerRegister.java new file mode 100644 index 000000000..88df808ff --- /dev/null +++ b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/EnumDictHandlerRegister.java @@ -0,0 +1,104 @@ +package org.hswebframework.web.dao.mybatis; + +import lombok.AllArgsConstructor; +import lombok.Getter; +import lombok.Setter; +import lombok.extern.slf4j.Slf4j; +import org.apache.ibatis.type.JdbcType; +import org.apache.ibatis.type.MappedJdbcTypes; +import org.apache.ibatis.type.TypeHandler; +import org.apache.ibatis.type.TypeHandlerRegistry; +import org.hswebframework.web.dict.EnumDict; +import org.springframework.context.ConfigurableApplicationContext; +import org.springframework.core.io.Resource; +import org.springframework.core.io.support.PathMatchingResourcePatternResolver; +import org.springframework.core.io.support.ResourcePatternResolver; +import org.springframework.core.type.classreading.CachingMetadataReaderFactory; +import org.springframework.core.type.classreading.MetadataReader; +import org.springframework.core.type.classreading.MetadataReaderFactory; +import org.springframework.util.ClassUtils; + +import java.io.IOException; +import java.sql.*; + +import static org.springframework.util.StringUtils.tokenizeToStringArray; + +@Slf4j +public class EnumDictHandlerRegister { + + static TypeHandlerRegistry typeHandlerRegistry; + + private static MetadataReaderFactory metadataReaderFactory = new CachingMetadataReaderFactory(); + + private static ResourcePatternResolver resourcePatternResolver = new PathMatchingResourcePatternResolver(); + + + public static void register(String packages) { + register(tokenizeToStringArray(packages, + ConfigurableApplicationContext.CONFIG_LOCATION_DELIMITERS)); + } + + public static void register(String[] packages) { + if (typeHandlerRegistry == null) { + log.error("请在spring容器初始化后再调用此方法!"); + return; + } + for (String basePackage : packages) { + String packageSearchPath = ResourcePatternResolver.CLASSPATH_ALL_URL_PREFIX + + ClassUtils.convertClassNameToResourcePath(basePackage) + "/**/*.class"; + try { + Resource[] resources = resourcePatternResolver.getResources(packageSearchPath); + for (Resource resource : resources) { + try { + MetadataReader reader = metadataReaderFactory.getMetadataReader(resource); + Class enumType = Class.forName(reader.getClassMetadata().getClassName()); + if (enumType.isEnum() && EnumDict.class.isAssignableFrom(enumType)) { + log.debug("register typeHandler for enum dict:{}", enumType); + typeHandlerRegistry.register(enumType, new EnumDictHandler(enumType)); + } + } catch (Exception ignore) { + + } + } + } catch (IOException e) { + log.warn("register enum dict error", e); + } + } + } + + @Getter + @Setter + @AllArgsConstructor + @MappedJdbcTypes({JdbcType.VARCHAR, JdbcType.BIT, + JdbcType.BOOLEAN, JdbcType.NUMERIC, + JdbcType.TINYINT, JdbcType.INTEGER, + JdbcType.BIGINT, JdbcType.DECIMAL, + JdbcType.CHAR}) + static class EnumDictHandler implements TypeHandler { + + private Class type; + + @Override + public void setParameter(PreparedStatement ps, int i, T parameter, JdbcType jdbcType) throws SQLException { + ps.setObject(i, parameter.getValue()); + } + + @Override + public T getResult(ResultSet rs, String columnName) throws SQLException { + Object val = rs.getObject(columnName); + return EnumDict.findByValue(getType(), val).orElse(null); + } + + @Override + public T getResult(ResultSet rs, int columnIndex) throws SQLException { + Object val = rs.getObject(columnIndex); + return EnumDict.findByValue(getType(), val).orElse(null); + } + + @Override + public T getResult(CallableStatement cs, int columnIndex) throws SQLException { + Object val = cs.getObject(columnIndex); + return EnumDict.findByValue(getType(), val).orElse(null); + } + } +} diff --git a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/MyBatisAutoConfiguration.java b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/MyBatisAutoConfiguration.java index 4b11c8d33..dc89f3702 100644 --- a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/MyBatisAutoConfiguration.java +++ b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/MyBatisAutoConfiguration.java @@ -74,7 +74,6 @@ public class MyBatisAutoConfiguration { public SqlSessionFactory sqlSessionFactory(@Qualifier("dataSource") DataSource dataSource) throws Exception { SqlSessionFactoryBean factory = new SqlSessionFactoryBean(); MybatisProperties mybatisProperties = this.mybatisProperties(); - if (null != entityFactory) { factory.setObjectFactory(new MybatisEntityFactory(entityFactory)); } @@ -109,7 +108,11 @@ public class MyBatisAutoConfiguration { } factory.setTypeHandlersPackage(typeHandlers); factory.setMapperLocations(mybatisProperties.resolveMapperLocations()); + SqlSessionFactory sqlSessionFactory = factory.getObject(); + EnumDictHandlerRegister.typeHandlerRegistry = sqlSessionFactory.getConfiguration().getTypeHandlerRegistry(); + EnumDictHandlerRegister.register("org.hswebframework.web;" + mybatisProperties.getTypeHandlersPackage()); + ResultMapsUtils.setSqlSession(sqlSessionFactory); try { Class.forName("javax.persistence.Table"); @@ -117,6 +120,9 @@ public class MyBatisAutoConfiguration { } catch (@SuppressWarnings("all") Exception ignore) { } EasyOrmSqlBuilder.getInstance().entityFactory = entityFactory; + + sqlSessionFactory.getConfiguration().getTypeAliasRegistry(); + return sqlSessionFactory; } diff --git a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/builder/jpa/JpaAnnotationParser.java b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/builder/jpa/JpaAnnotationParser.java index aef48c25d..3f2252fd9 100644 --- a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/builder/jpa/JpaAnnotationParser.java +++ b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/main/java/org/hswebframework/web/dao/mybatis/builder/jpa/JpaAnnotationParser.java @@ -7,6 +7,8 @@ import org.hswebframework.ezorm.rdb.meta.RDBColumnMetaData; import org.hswebframework.ezorm.rdb.meta.RDBTableMetaData; import org.hswebframework.ezorm.rdb.meta.converter.DateTimeConverter; import org.hswebframework.ezorm.rdb.meta.converter.NumberValueConverter; +import org.hswebframework.utils.ClassUtils; +import org.hswebframework.web.dict.EnumDict; import org.springframework.core.annotation.AnnotationUtils; import javax.persistence.Column; @@ -59,6 +61,8 @@ public class JpaAnnotationParser { jdbcTypeMapping.put(java.sql.Date.class, JDBCType.TIMESTAMP); jdbcTypeMapping.put(java.sql.Timestamp.class, JDBCType.TIMESTAMP); + jdbcTypeMapping.put(Object.class, JDBCType.VARCHAR); + jdbcTypeConvert.add((type, property) -> { Enumerated enumerated = getAnnotation(type, property, Enumerated.class); return enumerated != null ? JDBCType.VARCHAR : null; @@ -67,6 +71,14 @@ public class JpaAnnotationParser { Lob enumerated = getAnnotation(type, property, Lob.class); return enumerated != null ? JDBCType.CLOB : null; }); + + jdbcTypeConvert.add((type, property) -> { + if (type.isEnum() && EnumDict.class.isAssignableFrom(type)) { + Class genType = ClassUtils.getGenericType(type); + return jdbcTypeMapping.getOrDefault(genType, JDBCType.OTHER); + } + return null; + }); } public static RDBTableMetaData parseMetaDataFromEntity(Class entityClass) { @@ -92,7 +104,9 @@ public class JpaAnnotationParser { columnMetaData.setPrecision(column.precision()); columnMetaData.setJavaType(descriptor.getPropertyType()); - JDBCType type = jdbcTypeMapping.get(descriptor.getPropertyType()); + Class propertyType = descriptor.getPropertyType(); + + JDBCType type = jdbcTypeMapping.get(propertyType); if (type == null) { type = jdbcTypeConvert.stream() .map(func -> func.apply(entityClass, descriptor)) diff --git a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/test/java/org/hswebframework/web/dao/mybatis/builder/jpa/JpaAnnotationParserTest.java b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/test/java/org/hswebframework/web/dao/mybatis/builder/jpa/JpaAnnotationParserTest.java index dd79aeaa8..4f106b074 100644 --- a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/test/java/org/hswebframework/web/dao/mybatis/builder/jpa/JpaAnnotationParserTest.java +++ b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/test/java/org/hswebframework/web/dao/mybatis/builder/jpa/JpaAnnotationParserTest.java @@ -20,6 +20,6 @@ public class JpaAnnotationParserTest { RDBTableMetaData metaData = JpaAnnotationParser.parseMetaDataFromEntity(TestEntity.class); Assert.assertNotNull(metaData); - Assert.assertEquals(metaData.getColumns().size(), 4); + Assert.assertEquals(metaData.getColumns().size(), 5); } } diff --git a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/test/java/org/hswebframework/web/dao/mybatis/builder/jpa/TestEntity.java b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/test/java/org/hswebframework/web/dao/mybatis/builder/jpa/TestEntity.java index caa846814..a67e004e3 100644 --- a/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/test/java/org/hswebframework/web/dao/mybatis/builder/jpa/TestEntity.java +++ b/hsweb-commons/hsweb-commons-dao/hsweb-commons-dao-mybatis/src/test/java/org/hswebframework/web/dao/mybatis/builder/jpa/TestEntity.java @@ -1,6 +1,7 @@ package org.hswebframework.web.dao.mybatis.builder.jpa; import lombok.Data; +import org.hswebframework.web.dict.defaults.TrueOrFalse; import javax.persistence.Column; import javax.persistence.Table; @@ -22,4 +23,7 @@ public class TestEntity extends AbstractEntity { @Column(name = "role_id") private String roleId; + @Column(name = "enabled") + private TrueOrFalse enabled; + } diff --git a/hsweb-commons/hsweb-commons-entity/src/main/java/org/hswebframework/web/commons/entity/DataStatus.java b/hsweb-commons/hsweb-commons-entity/src/main/java/org/hswebframework/web/commons/entity/DataStatus.java index c34cc9e79..176854663 100644 --- a/hsweb-commons/hsweb-commons-entity/src/main/java/org/hswebframework/web/commons/entity/DataStatus.java +++ b/hsweb-commons/hsweb-commons-entity/src/main/java/org/hswebframework/web/commons/entity/DataStatus.java @@ -1,12 +1,11 @@ package org.hswebframework.web.commons.entity; /** - * TODO 完成注释 - * * @author zhouhao + * @see DataStatusEnum */ public interface DataStatus { - Byte STATUS_ENABLED = 1; + Byte STATUS_ENABLED = 1; Byte STATUS_DISABLED = 0; - Byte STATUS_LOCKED = -1; + Byte STATUS_LOCKED = -1; } diff --git a/hsweb-commons/hsweb-commons-entity/src/main/java/org/hswebframework/web/commons/entity/DataStatusEnum.java b/hsweb-commons/hsweb-commons-entity/src/main/java/org/hswebframework/web/commons/entity/DataStatusEnum.java new file mode 100644 index 000000000..f0570e7cd --- /dev/null +++ b/hsweb-commons/hsweb-commons-entity/src/main/java/org/hswebframework/web/commons/entity/DataStatusEnum.java @@ -0,0 +1,18 @@ +package org.hswebframework.web.commons.entity; + +import lombok.AllArgsConstructor; +import lombok.Getter; +import org.hswebframework.web.dict.EnumDict; + +@AllArgsConstructor +@Getter +public enum DataStatusEnum implements EnumDict { + ENABLED((byte) 1, "正常"), + DISABLED((byte) 0, "禁用"), + LOCK((byte) -1, "锁定"), + DELETED((byte) -10, "删除"); + + private Byte value; + + private String text; +} diff --git a/hsweb-core/src/main/java/org/hswebframework/web/dict/EnumDict.java b/hsweb-core/src/main/java/org/hswebframework/web/dict/EnumDict.java index 1df648b8e..a7f71cf74 100644 --- a/hsweb-core/src/main/java/org/hswebframework/web/dict/EnumDict.java +++ b/hsweb-core/src/main/java/org/hswebframework/web/dict/EnumDict.java @@ -26,6 +26,20 @@ public interface EnumDict { */ String getText(); + /** + * 对比是否和value相等,对比地址,值,value转为string忽略大小写对比,text忽略大小写对比 + * + * @param v value + * @return 是否相等 + */ + default boolean eq(Object v) { + return getValue() == v + || getValue().equals(v) + || String.valueOf(getValue()).equalsIgnoreCase(String.valueOf(v)) + || getText().equalsIgnoreCase(String.valueOf(v)); + } + + /** * 枚举选项的描述,对一个选项进行详细的描述有时候是必要的.默认值为{@link this#getText()} * @@ -77,7 +91,7 @@ public interface EnumDict { * * @see this#find(Class, Predicate) */ - static Optional find(Class type, Object valueOrTextOrAlias) { - return Optional.ofNullable(findByValue(type, valueOrTextOrAlias).orElseGet(() -> findByText(type, String.valueOf(valueOrTextOrAlias)).orElse(null))); + static Optional find(Class type, Object target) { + return find(type, v->v.eq(target)); } } diff --git a/hsweb-core/src/main/java/org/hswebframework/web/dict/defaults/TrueOrFalse.java b/hsweb-core/src/main/java/org/hswebframework/web/dict/defaults/TrueOrFalse.java new file mode 100644 index 000000000..9ed6e7656 --- /dev/null +++ b/hsweb-core/src/main/java/org/hswebframework/web/dict/defaults/TrueOrFalse.java @@ -0,0 +1,19 @@ +package org.hswebframework.web.dict.defaults; + +import lombok.AllArgsConstructor; +import lombok.Getter; +import org.hswebframework.web.dict.EnumDict; + +@Getter +@AllArgsConstructor +public enum TrueOrFalse implements EnumDict { + + TRUE((byte) 1, "是"), + + FALSE((byte) 0, "否"); + + private Byte value; + + private String text; + +} diff --git a/hsweb-core/src/main/java/org/hswebframework/web/validate/ValidateResults.java b/hsweb-core/src/main/java/org/hswebframework/web/validate/ValidateResults.java index ffe8874e3..ba209fba2 100644 --- a/hsweb-core/src/main/java/org/hswebframework/web/validate/ValidateResults.java +++ b/hsweb-core/src/main/java/org/hswebframework/web/validate/ValidateResults.java @@ -22,7 +22,7 @@ import java.io.Serializable; import java.util.List; /** - * TODO 完成注释 + * 验证结果 * * @author zhouhao */ diff --git a/hsweb-core/src/main/java/org/hswebframework/web/validate/ValidationException.java b/hsweb-core/src/main/java/org/hswebframework/web/validate/ValidationException.java index 690af358c..71abf6eaf 100644 --- a/hsweb-core/src/main/java/org/hswebframework/web/validate/ValidationException.java +++ b/hsweb-core/src/main/java/org/hswebframework/web/validate/ValidationException.java @@ -24,6 +24,7 @@ import org.hswebframework.web.BusinessException; import java.util.List; public class ValidationException extends BusinessException { + private static final long serialVersionUID = 7807607467371210082L; private ValidateResults results; public ValidationException(String message) { diff --git a/hsweb-core/src/test/java/org/hswebframework/web/bean/FastBeanCopierTest.java b/hsweb-core/src/test/java/org/hswebframework/web/bean/FastBeanCopierTest.java index f53943f16..677f896ae 100644 --- a/hsweb-core/src/test/java/org/hswebframework/web/bean/FastBeanCopierTest.java +++ b/hsweb-core/src/test/java/org/hswebframework/web/bean/FastBeanCopierTest.java @@ -1,7 +1,9 @@ package org.hswebframework.web.bean; +import org.apache.commons.beanutils.BeanUtils; import org.junit.Test; +import java.lang.reflect.InvocationTargetException; import java.util.Collections; import java.util.HashMap; import java.util.Map; @@ -13,7 +15,7 @@ import java.util.Map; public class FastBeanCopierTest { @Test - public void test() { + public void test() throws InvocationTargetException, IllegalAccessException { Source source = new Source(); source.setAge(100); source.setName("测试"); @@ -31,8 +33,8 @@ public class FastBeanCopierTest { Target target = new Target(); FastBeanCopier.copy(source, target); + long t = System.currentTimeMillis(); -// Copier copier = FastBeanCopier.getCopier(source, target, true); for (int i = 10_0000; i > 0; i--) { FastBeanCopier.copy(source, target); } diff --git a/hsweb-core/src/test/java/org/hswebframework/web/dict/DictDefineTest.java b/hsweb-core/src/test/java/org/hswebframework/web/dict/DictDefineTest.java index c746e9f44..419fd5a26 100644 --- a/hsweb-core/src/test/java/org/hswebframework/web/dict/DictDefineTest.java +++ b/hsweb-core/src/test/java/org/hswebframework/web/dict/DictDefineTest.java @@ -29,7 +29,6 @@ public class DictDefineTest { Assert.assertEquals(UserCode.SIMPLE, EnumDict.findByText(UserCode.class, UserCode.SIMPLE.getText()).orElse(null)); Assert.assertEquals(UserCode.SIMPLE, EnumDict.find(UserCode.class, UserCode.SIMPLE.getText()).orElse(null)); - } @Test diff --git a/hsweb-system/hsweb-system-authorization/hsweb-system-authorization-service/hsweb-system-authorization-service-api/src/main/java/org/hswebframework/web/service/authorization/AuthorizationSettingMenuService.java b/hsweb-system/hsweb-system-authorization/hsweb-system-authorization-service/hsweb-system-authorization-service-api/src/main/java/org/hswebframework/web/service/authorization/AuthorizationSettingMenuService.java index 1d40672d2..4a51989a7 100644 --- a/hsweb-system/hsweb-system-authorization/hsweb-system-authorization-service/hsweb-system-authorization-service-api/src/main/java/org/hswebframework/web/service/authorization/AuthorizationSettingMenuService.java +++ b/hsweb-system/hsweb-system-authorization/hsweb-system-authorization-service/hsweb-system-authorization-service-api/src/main/java/org/hswebframework/web/service/authorization/AuthorizationSettingMenuService.java @@ -7,7 +7,6 @@ import org.hswebframework.web.service.TreeService; import java.util.List; /** - * TODO 完成注释 * * @author zhouhao */ diff --git a/hsweb-system/hsweb-system-schedule/hsweb-system-schedule-service/hsweb-system-schedule-service-simple/src/main/java/org/hswebframework/web/service/schedule/simple/SimpleScheduleJobService.java b/hsweb-system/hsweb-system-schedule/hsweb-system-schedule-service/hsweb-system-schedule-service-simple/src/main/java/org/hswebframework/web/service/schedule/simple/SimpleScheduleJobService.java index 4ac97cd91..5d0d1a5b1 100644 --- a/hsweb-system/hsweb-system-schedule/hsweb-system-schedule-service/hsweb-system-schedule-service-simple/src/main/java/org/hswebframework/web/service/schedule/simple/SimpleScheduleJobService.java +++ b/hsweb-system/hsweb-system-schedule/hsweb-system-schedule-service/hsweb-system-schedule-service-simple/src/main/java/org/hswebframework/web/service/schedule/simple/SimpleScheduleJobService.java @@ -8,7 +8,6 @@ import org.hswebframework.web.commons.entity.DataStatus; import org.hswebframework.web.dao.schedule.ScheduleJobDao; import org.hswebframework.web.entity.schedule.ScheduleJobEntity; import org.hswebframework.web.id.IDGenerator; -import org.hswebframework.web.service.EnableCacheGenericEntityService; import org.hswebframework.web.service.GenericEntityService; import org.hswebframework.web.service.schedule.ScheduleJobService; import org.hswebframework.web.service.schedule.ScheduleTriggerBuilder; @@ -16,7 +15,6 @@ import org.quartz.*; import org.quartz.spi.MutableTrigger; import org.quartz.spi.OperableTrigger; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.cache.annotation.CacheConfig; import org.springframework.stereotype.Service; import org.springframework.util.StringUtils; @@ -83,18 +81,18 @@ public class SimpleScheduleJobService extends GenericEntityService0) { - startJob(selectByPk(id)); - } + if (size > 0) { + startJob(selectByPk(id)); + } } private void deleteJob(ScheduleJobEntity jobEntity) { @@ -150,10 +148,10 @@ public class SimpleScheduleJobService extends GenericEntityService0) { - deleteJob(selectByPk(id)); - } + if (size > 0) { + deleteJob(selectByPk(id)); + } } }