#
Junjie
1 天以前 536e17a446c170a8b214aaf188b98817ee6258c1
#
1个文件已删除
38个文件已添加
1个文件已修改
3195 ■■■■■ 已修改文件
pom.xml 8 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/annotations/AppAuth.java 20 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/annotations/CoolTranslate.java 13 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/annotations/ManagerAuth.java 20 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/AesUtils.java 50 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/Arith.java 77 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/BaseRes.java 13 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/Cache.java 61 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/Cools.java 318 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/DateUtils.java 161 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/Protocol.java 80 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/R.java 58 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/RadixTools.java 131 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/SnowflakeIdWorker.java 78 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/common/SpringUtils.java 35 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/config/CoolBaseConfig.java 26 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/controller/AbstractBaseController.java 74 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/domain/KeyValueVo.java 32 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/domain/QueryField.java 17 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/domain/QueryType.java 20 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/exception/ApplicationException.java 14 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/exception/CoolException.java 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/generators/CoolGenerator.java 853 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/generators/constant/SqlOsType.java 6 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/generators/domain/Column.java 265 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/generators/utils/GeneratorUtils.java 134 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/utils/Algorithm.java 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/core/utils/SignUtils.java 30 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/META-INF/spring.factories 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/Controller.txt 139 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/Entity.txt 16 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/Html.txt 70 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/HtmlDetail.txt 48 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/Js.txt 244 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/Mapper.txt 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/Service.txt 8 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/ServiceImpl.txt 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/Sql.txt 18 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/Xml.txt 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
version/lib/cool-framework-install.txt 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
pom.xml
@@ -15,7 +15,6 @@
    <properties>
        <java.version>1.8</java.version>
        <cool.version>3.4.0</cool.version>
        <mysql-driver.version>5.1.47</mysql-driver.version>
        <mybatis-plus.version>2.3.2</mybatis-plus.version>
        <fastjson.version>1.2.83</fastjson.version>
@@ -36,13 +35,6 @@
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-redis</artifactId>
        </dependency>
        <dependency>
            <groupId>cn.cool</groupId>
            <artifactId>framework</artifactId>
            <version>3.4.0</version>
            <scope>system</scope>
            <systemPath>${project.basedir}/version/lib/framework-3.4.0.jar</systemPath>
        </dependency>
        <dependency>
            <groupId>mysql</groupId>
src/main/java/com/core/annotations/AppAuth.java
New file
@@ -0,0 +1,20 @@
package com.core.annotations;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface AppAuth {
    Auth value() default Auth.CHECK;
    String memo() default "";
    enum Auth {
        CHECK,
        NONE
    }
}
src/main/java/com/core/annotations/CoolTranslate.java
New file
@@ -0,0 +1,13 @@
package com.core.annotations;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target({ElementType.TYPE, ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
public @interface CoolTranslate {
    String value() default "";
}
src/main/java/com/core/annotations/ManagerAuth.java
New file
@@ -0,0 +1,20 @@
package com.core.annotations;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @interface ManagerAuth {
    Auth value() default Auth.CHECK;
    String memo() default "";
    enum Auth {
        CHECK,
        NONE
    }
}
src/main/java/com/core/common/AesUtils.java
New file
@@ -0,0 +1,50 @@
package com.core.common;
import javax.crypto.Cipher;
import javax.crypto.spec.SecretKeySpec;
import java.nio.charset.StandardCharsets;
public class AesUtils {
    private static final String DEFAULT_CHARSET = "utf-8";
    private static final int DEFAULT_KEY_LENGTH = 16;
    public static String encrypt(String data, String key) {
        try {
            if (key == null || "".equals(key) || key.length() != DEFAULT_KEY_LENGTH) {
                return null;
            }
            byte[] raw = key.getBytes(StandardCharsets.UTF_8);
            SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES");
            Cipher cipher = Cipher.getInstance("AES/ECB/PKCS5Padding");
            cipher.init(Cipher.ENCRYPT_MODE, skeySpec);
            byte[] encrypted = cipher.doFinal(data.getBytes(StandardCharsets.UTF_8));
            return RadixTools.bytesToHexStr(encrypted);
        } catch (Exception ex) {
            return null;
        }
    }
    public static String decrypt(String data, String key) {
        try {
            if (key == null || "".equals(key) || key.length() != DEFAULT_KEY_LENGTH) {
                return null;
            }
            byte[] raw = key.getBytes(StandardCharsets.UTF_8);
            SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES");
            Cipher cipher = Cipher.getInstance("AES/ECB/PKCS5Padding");
            cipher.init(Cipher.DECRYPT_MODE, skeySpec);
            byte[] original = cipher.doFinal(RadixTools.hexStringToBytes(data));
            return new String(original, StandardCharsets.UTF_8);
        } catch (Exception ex) {
            return null;
        }
    }
    public static void main(String[] args) {
        String key = "123456";
        String data = "15988786205&timestamp=" + (System.currentTimeMillis() + 5000000L);
        System.out.println(System.currentTimeMillis() + 5000000L);
        System.out.println(encrypt(data, key));
    }
}
src/main/java/com/core/common/Arith.java
New file
@@ -0,0 +1,77 @@
package com.core.common;
import java.math.BigDecimal;
import java.math.RoundingMode;
public class Arith {
    private enum ArithType {
        ADD(0),
        DIVIDE(1),
        SUBTRACT(2),
        MULTIPLY(3);
        private final int value;
        ArithType(int value) {
            this.value = value;
        }
        public int getValue() {
            return value;
        }
    }
    public static double add(int scale, Number... nums) {
        return getAirth(scale, ArithType.ADD.getValue(), nums);
    }
    public static double subtract(int scale, Number... nums) {
        return getAirth(scale, ArithType.SUBTRACT.getValue(), nums);
    }
    public static double multiplys(int scale, Number... nums) {
        return getAirth(scale, ArithType.MULTIPLY.getValue(), nums);
    }
    public static double divides(int scale, Number... nums) {
        return getAirth(scale, ArithType.DIVIDE.getValue(), nums);
    }
    public static int percentage(Number... nums) {
        return (int) (divides(2, nums) * 100);
    }
    public static double remainder(Number... nums) {
        return new BigDecimal(nums[0].toString())
                .remainder(new BigDecimal(String.valueOf(nums[1])))
                .doubleValue();
    }
    private static double getAirth(int scale, int type, Number... nums) {
        if (nums == null || nums.length == 0) {
            return 0D;
        }
        BigDecimal result = new BigDecimal(nums[0].toString());
        for (int i = 1; i < nums.length; i++) {
            BigDecimal current = new BigDecimal(String.valueOf(nums[i]));
            switch (type) {
                case 0:
                    result = result.add(current);
                    break;
                case 1:
                    result = result.divide(current, scale, RoundingMode.HALF_UP);
                    break;
                case 2:
                    result = result.subtract(current);
                    break;
                case 3:
                    result = result.multiply(current);
                    break;
                default:
                    return 0D;
            }
        }
        return result.setScale(scale, RoundingMode.HALF_UP).doubleValue();
    }
}
src/main/java/com/core/common/BaseRes.java
New file
@@ -0,0 +1,13 @@
package com.core.common;
public interface BaseRes {
    String OK = "200-操作成功";
    String EMPTY = "201-暂无数据";
    String LIMIT = "202-无权限";
    String PARAM = "401-参数为空";
    String DENIED = "403-请重新登录";
    String REPEAT = "407-已存在";
    String NO_ACTIVATION = "409-请先激活系统";
    String ERROR = "500-服务器错误";
}
src/main/java/com/core/common/Cache.java
New file
@@ -0,0 +1,61 @@
package com.core.common;
import com.core.exception.ApplicationException;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.function.Supplier;
public class Cache {
    private Map<String, Object> caches = new ConcurrentHashMap<>();
    public <T> T get(Class<T> clazz) {
        return (T) get(clazz.getName());
    }
    public Object get(String key) {
        return get(key, true);
    }
    public <T> T get(String key, Supplier<T> supplier) {
        if (!hasKey(key)) {
            put(key, supplier.get());
        }
        return (T) get(key);
    }
    public Object get(String key, boolean require) {
        if (require && !hasKey(key)) {
            throw new ApplicationException(this + "-找不到缓存对象:" + key);
        }
        return caches.get(key);
    }
    public Cache put(Object value) {
        String key = value.getClass().getName();
        put(key, value);
        return this;
    }
    public Cache put(String key, Object value) {
        put(key, value, true);
        return this;
    }
    public Cache put(String key, Object value, boolean requireNotExists) {
        if (requireNotExists && hasKey(key)) {
            throw new ApplicationException(this + "-缓存" + key + "已存在");
        }
        caches.put(key, value);
        return this;
    }
    public boolean hasKey(Class<?> clazz) {
        return hasKey(clazz.getName());
    }
    public boolean hasKey(String key) {
        return caches.containsKey(key);
    }
}
src/main/java/com/core/common/Cools.java
New file
@@ -0,0 +1,318 @@
package com.core.common;
import com.core.annotations.CoolTranslate;
import java.lang.reflect.Array;
import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Modifier;
import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Set;
public class Cools {
    private static final char[] HEX_DIGITS = {
            '0', '1', '2', '3', '4', '5', '6', '7',
            '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'
    };
    public static boolean isEmpty(Object... objects) {
        for (Object object : objects) {
            if (isEmpty(object)) {
                return true;
            }
        }
        return false;
    }
    public static boolean isEmpty(Object object) {
        if (object == null) {
            return true;
        }
        if (object instanceof String) {
            return "".equals(object.toString().trim());
        }
        if (object instanceof List) {
            return ((List<?>) object).size() == 0;
        }
        if (object instanceof Map) {
            return ((Map<?, ?>) object).size() == 0;
        }
        if (object instanceof Set) {
            return ((Set<?>) object).size() == 0;
        }
        if (object instanceof Object[]) {
            return ((Object[]) object).length == 0;
        }
        if (object instanceof int[]) {
            return ((int[]) object).length == 0;
        }
        if (object instanceof long[]) {
            return ((long[]) object).length == 0;
        }
        return false;
    }
    public static int sqlLimitIndex(Integer curr, Integer limit) {
        return (curr.intValue() - 1) * limit.intValue();
    }
    public static String enToken(String data, String key) {
        return AesUtils.encrypt(data, zerofill(key, Integer.valueOf(16)));
    }
    public static String deTokn(String data, String key) {
        return AesUtils.decrypt(data, zerofill(key, Integer.valueOf(16)));
    }
    public static String zerofill(String str, Integer length) {
        if (str.length() == length.intValue()) {
            return str;
        }
        if (str.length() > length.intValue()) {
            return str.substring(0, 16);
        }
        StringBuilder builder = new StringBuilder(str);
        for (int i = 0; i < length.intValue() - str.length(); i++) {
            builder.append("0");
        }
        return builder.toString();
    }
    public static String deleteChar(String str, boolean end) {
        if (isEmpty(str)) {
            return "";
        }
        if (end) {
            return str.substring(0, str.length() - 1);
        }
        return str.substring(1);
    }
    public static String deleteChar(String str) {
        return deleteChar(str, true);
    }
    public static <T> T conver(Map<? extends String, ?> map, Class<T> clazz) {
        T target = null;
        try {
            Constructor<T> constructor = clazz.getDeclaredConstructor();
            boolean accessible = constructor.isAccessible();
            constructor.setAccessible(true);
            target = constructor.newInstance();
            constructor.setAccessible(accessible);
        } catch (IllegalAccessException | InstantiationException | NoSuchMethodException | InvocationTargetException e) {
            e.printStackTrace();
        }
        Class<?> current = clazz;
        while (current != null && !Object.class.equals(current)) {
            for (Field field : current.getDeclaredFields()) {
                if (Modifier.isFinal(field.getModifiers())
                        || Modifier.isStatic(field.getModifiers())
                        || Modifier.isTransient(field.getModifiers())) {
                    continue;
                }
                String fieldName = field.getName();
                Object val = map.containsKey(fieldName) ? map.get(fieldName) : null;
                if (val == null) {
                    continue;
                }
                boolean accessible = field.isAccessible();
                field.setAccessible(true);
                Class<?> fieldType = field.getType();
                try {
                    field.set(target, convertFieldValue(fieldType, val));
                } catch (Exception ex) {
                    System.err.println("convert error ===> Class[" + current + "],Field:[" + fieldName
                            + "],Type:[" + fieldType + "],Value:[" + val + "]");
                }
                field.setAccessible(accessible);
            }
            current = current.getSuperclass();
        }
        return target;
    }
    private static Object convertFieldValue(Class<?> fieldType, Object val)
            throws NoSuchMethodException, IllegalAccessException, InvocationTargetException, InstantiationException {
        if (fieldType.isInstance(val)) {
            return val;
        }
        if (fieldType == String.class) {
            return String.valueOf(val);
        }
        if (fieldType == Integer.class || fieldType == int.class) {
            return Integer.valueOf(String.valueOf(val));
        }
        if (fieldType == Long.class || fieldType == long.class) {
            return Long.valueOf(String.valueOf(val));
        }
        if (fieldType == Short.class || fieldType == short.class) {
            return Short.valueOf(String.valueOf(val));
        }
        if (fieldType == Double.class || fieldType == double.class) {
            return Double.valueOf(String.valueOf(val));
        }
        if (fieldType == Float.class || fieldType == float.class) {
            return Float.valueOf(String.valueOf(val));
        }
        if (fieldType == Boolean.class || fieldType == boolean.class) {
            return Boolean.valueOf(String.valueOf(val));
        }
        if (fieldType == Byte.class || fieldType == byte.class) {
            return Byte.valueOf(String.valueOf(val));
        }
        if (fieldType.isEnum()) {
            return Enum.valueOf((Class<? extends Enum>) fieldType, String.valueOf(val));
        }
        Constructor<?> constructor = fieldType.getDeclaredConstructor(String.class);
        boolean constructorAccessible = constructor.isAccessible();
        constructor.setAccessible(true);
        Object result = constructor.newInstance(String.valueOf(val));
        constructor.setAccessible(constructorAccessible);
        return result;
    }
    public static Map<String, Object> conver(Object object) {
        Field[] fields = getAllFields(object.getClass());
        Map<String, Object> result = new HashMap<>();
        for (Field field : fields) {
            String fieldName = field.getName();
            boolean accessible = field.isAccessible();
            field.setAccessible(true);
            Object val = null;
            try {
                val = field.get(object);
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }
            field.setAccessible(accessible);
            if (val != null) {
                result.put(fieldName, val);
            }
        }
        return result;
    }
    public static Field[] getAllFields(Class<?> clazz) {
        return getAllFields(clazz, null);
    }
    private static Field[] getAllFields(Class<?> clazz, Field[] fields) {
        Field[] allFields = fields == null ? clazz.getDeclaredFields() : fields;
        Class<?> superClass = clazz.getSuperclass();
        if (superClass == null || superClass == Object.class) {
            return allFields;
        }
        Field[] superFields = superClass.getDeclaredFields();
        allFields = addAll(allFields, superFields);
        return getAllFields(superClass, allFields);
    }
    public static <T> T[] addAll(T[] array1, T... array2) {
        if (array1 == null) {
            return clone(array2);
        }
        if (array2 == null) {
            return clone(array1);
        }
        Class<?> type1 = array1.getClass().getComponentType();
        T[] joined = (T[]) Array.newInstance(type1, array1.length + array2.length);
        System.arraycopy(array1, 0, joined, 0, array1.length);
        try {
            System.arraycopy(array2, 0, joined, array1.length, array2.length);
            return joined;
        } catch (ArrayStoreException ex) {
            Class<?> type2 = array2.getClass().getComponentType();
            if (!type1.isAssignableFrom(type2)) {
                throw new RuntimeException("Cannot store" + type2.getName() + " in an array of" + type1.getName(), ex);
            }
            throw ex;
        }
    }
    private static <T> T[] clone(T[] array) {
        return array == null ? null : (T[]) array.clone();
    }
    public static CoolMap add(String key, Object value) {
        CoolMap map = new CoolMap();
        map.put(key, value);
        return map;
    }
    public static String md5(String str) {
        try {
            MessageDigest digest = MessageDigest.getInstance("MD5");
            byte[] bytes = digest.digest(str.getBytes(StandardCharsets.UTF_8));
            char[] chars = new char[bytes.length * 2];
            for (int i = 0; i < bytes.length; i++) {
                int val = bytes[i];
                chars[i * 2] = HEX_DIGITS[(val & 0xF0) >> 4];
                chars[i * 2 + 1] = HEX_DIGITS[val & 0x0F];
            }
            return new String(chars).toLowerCase();
        } catch (Exception e) {
            e.printStackTrace();
            throw new RuntimeException("md5加密失败,str=".concat(str));
        }
    }
    public static Map<String, Object> translate(Object object) {
        Field[] fields = getAllFields(object.getClass());
        Map<String, Object> result = new HashMap<>();
        for (Field field : fields) {
            String fieldName = field.getName();
            if (field.isAnnotationPresent(CoolTranslate.class)) {
                CoolTranslate translate = field.getAnnotation(CoolTranslate.class);
                if (!isEmpty(translate.value())) {
                    fieldName = translate.value();
                }
            }
            boolean accessible = field.isAccessible();
            field.setAccessible(true);
            Object val = null;
            try {
                val = field.get(object);
            } catch (IllegalAccessException e) {
                e.printStackTrace();
            }
            field.setAccessible(accessible);
            if (val != null) {
                result.put(fieldName, val);
            }
        }
        return result;
    }
    public static boolean eq(String left, String right) {
        if (isEmpty(left) && isEmpty(right)) {
            return true;
        }
        if (isEmpty(left) && !isEmpty(right)) {
            return false;
        }
        if (isEmpty(right) && !isEmpty(left)) {
            return false;
        }
        return left.equals(right);
    }
    public static class CoolMap extends HashMap<String, Object> {
        public CoolMap add(String key, Object value) {
            put(key, value);
            return this;
        }
        public CoolMap $(String key, Object value) {
            put(key, value);
            return this;
        }
    }
}
src/main/java/com/core/common/DateUtils.java
New file
@@ -0,0 +1,161 @@
package com.core.common;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Date;
import java.util.Objects;
import java.util.concurrent.TimeUnit;
public class DateUtils {
    public static final String yyyyMMdd_C = "yyyy年MM月dd日";
    public static final String yyyyMM_F = "yyyy-MM";
    public static final String yyyyMMdd_F = "yyyy-MM-dd";
    public static final String yyyyMMddHHmmss_F = "yyyy-MM-dd HH:mm:ss";
    public static final String yyyyMMddHHmmsssss_F = "yyyy-MM-dd HH:mm:ss:SSS";
    public static final String yyyy = "yyyy";
    public static final String yyyyMM = "yyyyMM";
    public static final String yyyyMMdd = "yyyyMMdd";
    public static final String yyyyMMddHH = "yyyyMMddHH";
    public static final String yyyyMMddHHmmss = "yyyyMMddHHmmss";
    public static final String YYMMDDHHMMSS = "yyMMddHHmmss";
    public static final String yyyyMMddHHmmsssss = "yyyyMMddHHmmssSSS";
    public static String convert(Date date, String format) {
        return new SimpleDateFormat(format).format(date);
    }
    public static String convert(Date date) {
        return convert(date, yyyyMMddHHmmss_F);
    }
    public static Date convert(String text, String format) {
        if (text.length() < format.length()) {
            throw new RuntimeException("时间解析失败 ==>>" + text);
        }
        if (text.length() > format.length()) {
            text = text.substring(0, format.length());
        }
        try {
            return new SimpleDateFormat(format).parse(text);
        } catch (ParseException e) {
            throw new RuntimeException("时间解析失败 ==>>" + text);
        }
    }
    public static Date convert(String text) {
        return convert(text, yyyyMMddHHmmss_F);
    }
    public static int diff(Date start, Date end) {
        return getDaysByTimestamp(Math.abs(end.getTime() - start.getTime()));
    }
    public static long diffToMinute(Date start, Date end) {
        return Math.abs(end.getTime() - start.getTime()) / 1000L / 60L;
    }
    public static long diffToSeconds(Date start, Date end) {
        return Math.abs(end.getTime() - start.getTime()) / 1000L;
    }
    private static int getDaysByTimestamp(long timestamp) {
        double days = Arith.divides(2, timestamp, 86400000);
        int value = (int) days;
        if (days > value) {
            return value + 1;
        }
        return value;
    }
    public static int diffToNow(Date date) {
        long val = new Date().getTime() - date.getTime();
        return (int) (Math.abs(val) / 1000L);
    }
    public static String createTimeStamp() {
        return Long.toString(System.currentTimeMillis() / 1000L);
    }
    public static Date calculate(Date date, Long amount, TimeUnit unit, boolean before) {
        if (Objects.isNull(date) || Objects.isNull(amount) || Objects.isNull(unit)) {
            return null;
        }
        return new Date(before ? date.getTime() - unit.toMillis(amount) : date.getTime() + unit.toMillis(amount));
    }
    public static Date calculate(Date date, Long amount, TimeUnit unit) {
        return calculate(date, amount, unit, false);
    }
    public static DateEntity getDateEntity(Date date) {
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(date);
        DateEntity entity = new DateEntity();
        entity.setYear(calendar.get(Calendar.YEAR));
        entity.setMonth(calendar.get(Calendar.MONTH));
        entity.setDay(calendar.get(Calendar.DAY_OF_MONTH));
        entity.setHour(calendar.get(Calendar.HOUR_OF_DAY));
        entity.setMinute(calendar.get(Calendar.MINUTE));
        entity.setSecond(calendar.get(Calendar.SECOND));
        return entity;
    }
    public static class DateEntity {
        private int year;
        private int month;
        private int day;
        private int hour;
        private int minute;
        private int second;
        public int getYear() {
            return year;
        }
        public void setYear(int year) {
            this.year = year;
        }
        public int getMonth() {
            return month;
        }
        public void setMonth(int month) {
            this.month = month;
        }
        public int getDay() {
            return day;
        }
        public void setDay(int day) {
            this.day = day;
        }
        public int getHour() {
            return hour;
        }
        public void setHour(int hour) {
            this.hour = hour;
        }
        public int getMinute() {
            return minute;
        }
        public void setMinute(int minute) {
            this.minute = minute;
        }
        public int getSecond() {
            return second;
        }
        public void setSecond(int second) {
            this.second = second;
        }
    }
}
src/main/java/com/core/common/Protocol.java
New file
@@ -0,0 +1,80 @@
package com.core.common;
import java.io.Serializable;
public class Protocol<T> implements Serializable {
    private static final long serialVersionUID = 1L;
    private int code;
    private String msg;
    private T data;
    public Protocol() {
    }
    public Protocol(int code, String msg, T data) {
        setCode(code);
        setMsg(msg);
        setData(data);
    }
    public Protocol(int code, String msg) {
        this(code, msg, null);
    }
    public static <T> Protocol<T> ok() {
        return parse(BaseRes.OK);
    }
    public static <T> Protocol<T> ok(T data) {
        Protocol<T> protocol = parse(BaseRes.OK);
        protocol.setData(data);
        return protocol;
    }
    public static <T> Protocol<T> error() {
        return parse(BaseRes.ERROR);
    }
    public static <T> Protocol<T> error(String msg) {
        Protocol<T> protocol = parse(BaseRes.ERROR);
        protocol.setMsg(msg);
        return protocol;
    }
    public static <T> Protocol<T> parse(String baseRes) {
        if (Cools.isEmpty(baseRes)) {
            return parse(BaseRes.ERROR);
        }
        String[] arr = baseRes.split("-");
        if (arr.length == 2) {
            return new Protocol<>(Integer.parseInt(arr[0]), arr[1]);
        }
        return parse("500-".concat(baseRes));
    }
    public int getCode() {
        return code;
    }
    public void setCode(int code) {
        this.code = code;
    }
    public String getMsg() {
        return msg;
    }
    public void setMsg(String msg) {
        this.msg = msg;
    }
    public T getData() {
        return data;
    }
    public void setData(T data) {
        this.data = data;
    }
}
src/main/java/com/core/common/R.java
New file
@@ -0,0 +1,58 @@
package com.core.common;
import java.util.HashMap;
public class R extends HashMap<String, Object> {
    private static final long serialVersionUID = 1L;
    private static final String CODE = "code";
    private static final String MSG = "msg";
    private static final String DATA = "data";
    public R(Integer code, String msg) {
        super();
        put(CODE, code);
        put(MSG, msg);
    }
    public static R ok() {
        return parse(BaseRes.OK);
    }
    public static R ok(String msg) {
        R r = ok();
        r.put(MSG, msg);
        return r;
    }
    public static R ok(Object data) {
        return parse(BaseRes.OK).add(data);
    }
    public static R error() {
        return parse(BaseRes.ERROR);
    }
    public static R error(String msg) {
        R r = error();
        r.put(MSG, msg);
        return r;
    }
    public R add(Object data) {
        put(DATA, data);
        return this;
    }
    public static R parse(String baseRes) {
        if (Cools.isEmpty(baseRes)) {
            return parse(BaseRes.ERROR);
        }
        String[] arr = baseRes.split("-");
        if (arr.length == 2) {
            return new R(Integer.parseInt(arr[0]), arr[1]);
        }
        return parse("500-".concat(baseRes));
    }
}
src/main/java/com/core/common/RadixTools.java
New file
@@ -0,0 +1,131 @@
package com.core.common;
import java.io.UnsupportedEncodingException;
import java.nio.charset.Charset;
public class RadixTools {
    public static void main(String[] args) {
        String val = toBinaryString((byte) 1);
        System.out.println(val);
        for (int i = val.length() - 1; i >= 0; i--) {
            char c = val.charAt(i);
            if (i == 7 && c == '1') {
                System.out.println("===");
            }
        }
    }
    public static String toBinaryString(byte b) {
        return Long.toBinaryString((b & 0xFF) + 0x100L).substring(1);
    }
    public static String toBinaryString(byte[] bytes) {
        StringBuilder builder = new StringBuilder();
        for (byte b : bytes) {
            builder.append(Long.toBinaryString((b & 0xFF) + 0x100L).substring(1));
        }
        return builder.toString();
    }
    public static byte[] hexStringToBytes(String hexString) {
        if (hexString == null || "".equals(hexString)) {
            return null;
        }
        String upper = hexString.toUpperCase();
        int length = upper.length() / 2;
        char[] chars = upper.toCharArray();
        byte[] result = new byte[length];
        for (int i = 0; i < length; i++) {
            int pos = i * 2;
            result[i] = (byte) ((charToByte(chars[pos]) << 4) | charToByte(chars[pos + 1]));
        }
        return result;
    }
    public static String bytesToHexStr(byte[] bytes) {
        StringBuilder builder = new StringBuilder(bytes.length * 2);
        for (byte b : bytes) {
            builder.append(String.format("%02x", b & 0xFF));
        }
        return builder.toString();
    }
    private static byte charToByte(char c) {
        return (byte) "0123456789ABCDEF".indexOf(c);
    }
    public static String bytesToStr(byte[] bytes) {
        return bytesToStr(bytes, Charset.forName("gbk"));
    }
    public static String bytesToStr(byte[] bytes, Charset charset) {
        return new String(bytes, charset).trim().toUpperCase();
    }
    public static byte[] strToBytes(String str) throws UnsupportedEncodingException {
        return str.getBytes("gbk");
    }
    public static byte[] longToBytes(long value) {
        long tmp = value;
        byte[] bytes = new byte[8];
        for (int i = 0; i < bytes.length; i++) {
            bytes[i] = Long.valueOf(tmp & 0xFF).byteValue();
            tmp = tmp >> 8;
        }
        return bytes;
    }
    public static long bytesToLong(byte[] bytes) {
        long result = 0L;
        long b0 = bytes[0] & 0xFFL;
        long b1 = (bytes[1] & 0xFFL) << 8;
        long b2 = (bytes[2] & 0xFFL) << 16;
        long b3 = (bytes[3] & 0xFFL) << 24;
        long b4 = (bytes[4] & 0xFFL) << 32;
        long b5 = (bytes[5] & 0xFFL) << 40;
        long b6 = (bytes[6] & 0xFFL) << 48;
        long b7 = (bytes[7] & 0xFFL) << 56;
        result = b0 | b1 | b2 | b3 | b4 | b5 | b6 | b7;
        return result;
    }
    public static byte[] intToBytes(int value) {
        int tmp = value;
        byte[] bytes = new byte[4];
        for (int i = 0; i < bytes.length; i++) {
            bytes[i] = Integer.valueOf(tmp & 0xFF).byteValue();
            tmp = tmp >> 8;
        }
        return bytes;
    }
    public static int bytesToInt(byte[] bytes) {
        int result;
        int b0 = bytes[0] & 0xFF;
        int b1 = (bytes[1] & 0xFF) << 8;
        int b2 = (bytes[2] & 0xFF) << 16;
        int b3 = (bytes[3] & 0xFF) << 24;
        result = b0 | b1 | b2 | b3;
        return result;
    }
    public static short byteToShort(byte[] bytes) {
        short result;
        short b0 = (short) (bytes[0] & 0xFF);
        short b1 = (short) ((bytes[1] & 0xFF) << 8);
        result = (short) (b0 | b1);
        return result;
    }
    public static byte[] shortToByte(short value) {
        int tmp = value;
        byte[] bytes = new byte[2];
        for (int i = 0; i < bytes.length; i++) {
            bytes[i] = Integer.valueOf(tmp & 0xFF).byteValue();
            tmp = tmp >> 8;
        }
        return bytes;
    }
}
src/main/java/com/core/common/SnowflakeIdWorker.java
New file
@@ -0,0 +1,78 @@
package com.core.common;
public class SnowflakeIdWorker {
    private final long twepoch = 1420041600000L;
    private final long sequenceBits = 12L;
    private final long workerIdBits = 5L;
    private final long datacenterIdBits = 5L;
    private final long workerIdLeftShift = 12L;
    private final long datacenterIdLeftShift = 17L;
    private final long timestampLeftShift = 22L;
    private final long maxWorkerId = 31L;
    private final long maxDatacenterId = 31L;
    private final long sequenceMask = 4095L;
    private long workerId;
    private long datacenterId;
    private long sequence = 0L;
    private long lastTimestamp = -1L;
    public SnowflakeIdWorker(long workerId, long datacenterId) {
        if (workerId > maxWorkerId || workerId < 0) {
            throw new IllegalArgumentException(String.format("worker Id can't be greater than %d or less than 0", maxWorkerId));
        }
        if (datacenterId > maxDatacenterId || datacenterId < 0) {
            throw new IllegalArgumentException(String.format("datacenter Id can't be greater than %d or less than 0", maxDatacenterId));
        }
        this.workerId = workerId;
        this.datacenterId = datacenterId;
    }
    public SnowflakeIdWorker() {
        this(0L, 0L);
    }
    public synchronized long nextId() {
        long timestamp = timeGen();
        if (timestamp < lastTimestamp) {
            throw new RuntimeException(String.format(
                    "Clock moved backwards.  Refusing to generate id for %d milliseconds",
                    lastTimestamp - timestamp));
        }
        if (lastTimestamp == timestamp) {
            sequence = (sequence + 1) & sequenceMask;
            if (sequence == 0) {
                timestamp = tilNextMillis(lastTimestamp);
            }
        } else {
            sequence = 0L;
        }
        lastTimestamp = timestamp;
        return ((timestamp - twepoch) << timestampLeftShift)
                | (datacenterId << datacenterIdLeftShift)
                | (workerId << workerIdLeftShift)
                | sequence;
    }
    protected long tilNextMillis(long lastTimestamp) {
        long timestamp = timeGen();
        while (timestamp <= lastTimestamp) {
            timestamp = timeGen();
        }
        return timestamp;
    }
    protected long timeGen() {
        return System.currentTimeMillis();
    }
    public static void main(String[] args) {
        SnowflakeIdWorker idWorker = new SnowflakeIdWorker(0L, 0L);
        for (int i = 0; i < 1000; i++) {
            long id = idWorker.nextId();
            System.out.println(Long.toBinaryString(id));
            System.out.println(id);
        }
    }
}
src/main/java/com/core/common/SpringUtils.java
New file
@@ -0,0 +1,35 @@
package com.core.common;
import com.core.exception.CoolException;
import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
public class SpringUtils implements ApplicationContextAware {
    private static ApplicationContext application;
    public static void init(ApplicationContext applicationContext) {
        application = applicationContext;
    }
    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        application = applicationContext;
    }
    private static ApplicationContext getApplicationContext() {
        if (application == null) {
            throw new CoolException(BaseRes.ERROR);
        }
        return application;
    }
    public static <T> T getBean(Class<T> clazz) {
        return getApplicationContext().getBean(clazz);
    }
    public static Object getBean(String name) {
        return getApplicationContext().getBean(name);
    }
}
src/main/java/com/core/config/CoolBaseConfig.java
New file
@@ -0,0 +1,26 @@
package com.core.config;
import com.baomidou.mybatisplus.plugins.PaginationInterceptor;
import com.core.common.SnowflakeIdWorker;
import com.core.common.SpringUtils;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@Configuration
public class CoolBaseConfig {
    @Bean
    public PaginationInterceptor paginationInterceptor() {
        return new PaginationInterceptor();
    }
    @Bean
    public SpringUtils getSpringUtils() {
        return new SpringUtils();
    }
    @Bean
    public SnowflakeIdWorker snowflakeIdWorker() {
        return new SnowflakeIdWorker();
    }
}
src/main/java/com/core/controller/AbstractBaseController.java
New file
@@ -0,0 +1,74 @@
package com.core.controller;
import com.core.common.BaseRes;
import com.core.common.Cools;
import com.core.exception.CoolException;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public abstract class AbstractBaseController {
    public <T> List exportSupport(List<T> list, List<String> fields) {
        if (Cools.isEmpty(list)) {
            throw new CoolException(BaseRes.EMPTY);
        }
        try {
            List<Object> result = new ArrayList<>();
            Method[] methods = list.get(0).getClass().getMethods();
            for (T item : list) {
                List<Object> row = new ArrayList<>();
                for (String field : fields) {
                    for (Method method : methods) {
                        if (("get" + field).toLowerCase().equals(method.getName().toLowerCase())) {
                            Object value = method.invoke(item);
                            row.add(value);
                            break;
                        }
                    }
                }
                result.add(row);
            }
            return result;
        } catch (Exception e) {
            throw new RuntimeException(e);
        }
    }
    public static Map<String, Object> excludeTrash(Map<String, Object> map) {
        if (Cools.isEmpty(map)) {
            return new HashMap<>();
        }
        Iterator<Map.Entry<String, Object>> iterator = map.entrySet().iterator();
        while (iterator.hasNext()) {
            Map.Entry<String, Object> entry = iterator.next();
            String key = entry.getKey();
            if ("curr".equals(key)
                    || "limit".equals(key)
                    || "orderByField".equals(key)
                    || "orderByType".equals(key)
                    || "condition".equals(key)
                    || Cools.isEmpty(entry.getValue())) {
                iterator.remove();
            }
        }
        return map;
    }
    public static String humpToLine(String str) {
        Pattern pattern = Pattern.compile("[A-Z]");
        Matcher matcher = pattern.matcher(str);
        StringBuffer buffer = new StringBuffer();
        while (matcher.find()) {
            matcher.appendReplacement(buffer, "_" + matcher.group(0).toLowerCase());
        }
        matcher.appendTail(buffer);
        return buffer.toString();
    }
}
src/main/java/com/core/domain/KeyValueVo.java
New file
@@ -0,0 +1,32 @@
package com.core.domain;
public class KeyValueVo {
    private String name;
    private Object value;
    public KeyValueVo() {
    }
    public KeyValueVo(String name, Object value) {
        this.name = name;
        this.value = value;
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public Object getValue() {
        return value;
    }
    public void setValue(Object value) {
        this.value = value;
    }
}
src/main/java/com/core/domain/QueryField.java
New file
@@ -0,0 +1,17 @@
package com.core.domain;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD, ElementType.ANNOTATION_TYPE})
public @interface QueryField {
    String value() default "";
    QueryType type() default QueryType.LIKE;
}
src/main/java/com/core/domain/QueryType.java
New file
@@ -0,0 +1,20 @@
package com.core.domain;
public enum QueryType {
    EQ,
    NE,
    GT,
    GE,
    LT,
    LE,
    LIKE,
    NOT_LIKE,
    LIKE_LEFT,
    LIKE_RIGHT,
    IS_NULL,
    IS_NOT_NULL,
    IN,
    NOT_IN,
    IN_STR,
    NOT_IN_STR
}
src/main/java/com/core/exception/ApplicationException.java
New file
@@ -0,0 +1,14 @@
package com.core.exception;
public class ApplicationException extends RuntimeException {
    private static final long serialVersionUID = 1L;
    public ApplicationException(Throwable cause) {
        super(cause);
    }
    public ApplicationException(String message) {
        super(message);
    }
}
src/main/java/com/core/exception/CoolException.java
New file
@@ -0,0 +1,12 @@
package com.core.exception;
public class CoolException extends RuntimeException {
    public CoolException(Throwable cause) {
        super(cause);
    }
    public CoolException(String message) {
        super(message);
    }
}
src/main/java/com/core/generators/CoolGenerator.java
New file
@@ -0,0 +1,853 @@
package com.core.generators;
import com.core.common.Cools;
import com.core.generators.constant.SqlOsType;
import com.core.generators.domain.Column;
import com.core.generators.utils.GeneratorUtils;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.nio.charset.StandardCharsets;
import java.nio.file.FileAlreadyExistsException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.nio.file.StandardOpenOption;
import java.sql.Connection;
import java.sql.DatabaseMetaData;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.LinkedHashMap;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
public class CoolGenerator {
    private static final String[] ALL_TEMPLATES = {
            "Controller", "Service", "ServiceImpl", "Mapper", "Entity",
            "Xml", "Html", "HtmlDetail", "Js", "Sql"
    };
    private static final Set<String> SYSTEM_MODEL = new LinkedHashSet<>(Arrays.asList("User", "Host"));
    public String url;
    public String username;
    public String password;
    public String table;
    public String packagePath;
    public boolean controller = true;
    public boolean service = true;
    public boolean mapper = true;
    public boolean entity = true;
    public boolean xml = true;
    public boolean html = true;
    public boolean htmlDetail = false;
    public boolean js = true;
    public boolean sql = true;
    public SqlOsType sqlOsType;
    public String backendPrefixPath = "";
    public String frontendPrefixPath = "";
    private List<Column> columns = new ArrayList<>();
    private String fullEntityName;
    private String simpleEntityName;
    private String entityImport;
    private String entityContent;
    private String xmlContent;
    private String htmlSearchContent;
    private String htmlDialogContent;
    private String htmlDetailContent;
    private String jsTableContent;
    private String jsDateContent;
    private String primaryKeyColumn;
    private String primaryKeyType;
    private String majorColumn;
    private String systemPackage;
    public void build() throws Exception {
        init();
        System.out.println("开始生成表[" + table + "]对应代码,实体名[" + fullEntityName + "]");
        for (String templateName : ALL_TEMPLATES) {
            boolean enabled = false;
            String fileDir = "";
            String fileName = "";
            String routeSegment = templateName.toLowerCase();
            if (routeSegment.contains("impl")) {
                routeSegment = routeSegment.substring(0, routeSegment.length() - 4) + "/" + routeSegment.substring(routeSegment.length() - 4);
            }
            switch (templateName) {
                case "Controller":
                    enabled = controller;
                    fileDir = backendPrefixPath + "src/main/java/" + packagePath.replace(".", "/") + "/" + routeSegment + "/";
                    fileName = fullEntityName + "Controller.java";
                    break;
                case "Service":
                    enabled = service;
                    fileDir = backendPrefixPath + "src/main/java/" + packagePath.replace(".", "/") + "/" + routeSegment + "/";
                    fileName = fullEntityName + "Service.java";
                    break;
                case "ServiceImpl":
                    enabled = service;
                    fileDir = backendPrefixPath + "src/main/java/" + packagePath.replace(".", "/") + "/" + routeSegment + "/";
                    fileName = fullEntityName + "ServiceImpl.java";
                    break;
                case "Mapper":
                    enabled = mapper;
                    fileDir = backendPrefixPath + "src/main/java/" + packagePath.replace(".", "/") + "/" + routeSegment + "/";
                    fileName = fullEntityName + "Mapper.java";
                    break;
                case "Entity":
                    enabled = entity;
                    fileDir = backendPrefixPath + "src/main/java/" + packagePath.replace(".", "/") + "/" + routeSegment + "/";
                    fileName = fullEntityName + ".java";
                    break;
                case "Xml":
                    enabled = xml;
                    fileDir = backendPrefixPath + "src/main/resources/mapper/";
                    fileName = fullEntityName + "Mapper.xml";
                    break;
                case "Html":
                    enabled = html;
                    fileDir = frontendPrefixPath + "src/main/webapp//views/" + simpleEntityName + "/";
                    fileName = simpleEntityName + ".html";
                    break;
                case "HtmlDetail":
                    enabled = htmlDetail;
                    fileDir = frontendPrefixPath + "src/main/webapp//views/" + simpleEntityName + "/";
                    fileName = simpleEntityName + "_detail.html";
                    break;
                case "Js":
                    enabled = js;
                    fileDir = frontendPrefixPath + "src/main/webapp/static/js/" + simpleEntityName + "/";
                    fileName = simpleEntityName + ".js";
                    break;
                case "Sql":
                    enabled = sql;
                    fileDir = backendPrefixPath + "version/sql/";
                    fileName = simpleEntityName + ".sql";
                    break;
                default:
                    break;
            }
            if (!enabled) {
                continue;
            }
            try {
                String template = loadTemplate(templateName + ".txt");
                String content = renderTemplate(template);
                writeFile(fileDir, fileName, content, templateName);
            } catch (Exception e) {
                System.out.println(fullEntityName + templateName + " 源文件创建失败:" + e.getMessage());
                throw e;
            }
        }
        System.out.println("表[" + table + "]代码生成结束");
    }
    private void init() throws Exception {
        validate();
        systemPackage = resolveSystemPackage();
        fullEntityName = GeneratorUtils.getNameSpace(table);
        simpleEntityName = GeneratorUtils.firstCharConvert(fullEntityName);
        System.out.println("开始读取表结构:" + table);
        Connection connection = createConnection();
        try {
            switch (sqlOsType) {
                case MYSQL:
                    columns = getMysqlColumns(connection, table, true, sqlOsType);
                    break;
                case SQL_SERVER:
                    columns = getSqlServerColumns(connection, table, true, sqlOsType);
                    break;
                default:
                    throw new IllegalArgumentException("Unsupported sql type: " + sqlOsType);
            }
        } finally {
            connection.close();
        }
        if (Cools.isEmpty(columns)) {
            throw new IllegalStateException("table has no columns: " + table);
        }
        System.out.println("表结构读取完成,共 " + columns.size() + " 个字段");
        primaryKeyColumn = resolvePrimaryKeyColumn();
        primaryKeyType = resolvePrimaryKeyType();
        majorColumn = resolveMajorColumn();
        entityImport = buildEntityImports();
        entityContent = buildEntityContent();
        xmlContent = buildXmlContent();
        htmlSearchContent = buildHtmlSearchContent();
        htmlDialogContent = buildHtmlDialogContent();
        htmlDetailContent = buildHtmlDetailContent();
        jsTableContent = buildJsTableContent();
        jsDateContent = buildJsDateContent();
    }
    private void validate() {
        if (Cools.isEmpty(url, username, password, table, packagePath) || sqlOsType == null) {
            throw new IllegalArgumentException("url/username/password/table/packagePath/sqlOsType are required");
        }
    }
    private String resolveSystemPackage() {
        String[] arr = packagePath.split("\\.");
        if (arr.length <= 2) {
            return packagePath;
        }
        return arr[0] + "." + arr[1];
    }
    private Connection createConnection() throws Exception {
        String jdbcUrl = url;
        switch (sqlOsType) {
            case MYSQL:
                Class.forName("com.mysql.jdbc.Driver");
                if (!jdbcUrl.startsWith("jdbc:mysql://")) {
                    jdbcUrl = "jdbc:mysql://" + jdbcUrl;
                }
                if (!jdbcUrl.contains("?")) {
                    jdbcUrl = jdbcUrl + "?useUnicode=true&characterEncoding=utf-8&useSSL=false&remarksReporting=true";
                } else if (!jdbcUrl.contains("remarksReporting=")) {
                    jdbcUrl = jdbcUrl + "&remarksReporting=true";
                }
                return DriverManager.getConnection(jdbcUrl, username, password);
            case SQL_SERVER:
                Class.forName("com.microsoft.sqlserver.jdbc.SQLServerDriver");
                if (!jdbcUrl.startsWith("jdbc:sqlserver://")) {
                    jdbcUrl = "jdbc:sqlserver://" + jdbcUrl;
                }
                return DriverManager.getConnection(jdbcUrl, username, password);
            default:
                throw new IllegalArgumentException("Unsupported sql type: " + sqlOsType);
        }
    }
    public static List<Column> getMysqlColumns(Connection connection, String table, boolean withForeignKey, SqlOsType sqlOsType) throws Exception {
        return getColumns(connection, table, withForeignKey, sqlOsType);
    }
    public static List<Column> getSqlServerColumns(Connection connection, String table, boolean withForeignKey, SqlOsType sqlOsType) throws Exception {
        return getColumns(connection, table, withForeignKey, sqlOsType);
    }
    private static List<Column> getColumns(Connection connection, String table, boolean withForeignKey, SqlOsType sqlOsType) throws Exception {
        List<Column> columns = new ArrayList<>();
        DatabaseMetaData metaData = connection.getMetaData();
        TableRef tableRef = parseTableRef(table);
        Set<String> primaryKeys = new LinkedHashSet<>();
        ResultSet pkRs = metaData.getPrimaryKeys(tableRef.catalog, tableRef.schema, tableRef.table);
        try {
            while (pkRs.next()) {
                primaryKeys.add(pkRs.getString("COLUMN_NAME"));
            }
        } finally {
            pkRs.close();
        }
        ResultSet columnRs = metaData.getColumns(tableRef.catalog, tableRef.schema, tableRef.table, null);
        try {
            while (columnRs.next()) {
                String columnName = columnRs.getString("COLUMN_NAME");
                int sqlType = columnRs.getInt("DATA_TYPE");
                String type = GeneratorUtils.getType(sqlType);
                if (Cools.isEmpty(type)) {
                    type = "String";
                }
                String remarks = columnRs.getString("REMARKS");
                boolean primaryKey = primaryKeys.contains(columnName);
                boolean mainKey = primaryKey && isAutoIncrement(columnRs);
                boolean notNull = columnRs.getInt("NULLABLE") == DatabaseMetaData.columnNoNulls;
                Integer length = GeneratorUtils.getColumnLength(columnRs.getString("TYPE_NAME"));
                columns.add(new Column(connection, columnName, type, remarks, primaryKey, mainKey, notNull, length,
                        withForeignKey, sqlOsType));
            }
        } finally {
            columnRs.close();
        }
        for (Column column : columns) {
            System.out.println(column.toString());
        }
        return columns;
    }
    private static boolean isAutoIncrement(ResultSet columnRs) {
        try {
            return "YES".equalsIgnoreCase(columnRs.getString("IS_AUTOINCREMENT"));
        } catch (SQLException e) {
            return false;
        }
    }
    private static TableRef parseTableRef(String table) {
        if (table != null && table.contains(".")) {
            String[] arr = table.split("\\.");
            return new TableRef(null, arr[0], arr[arr.length - 1]);
        }
        return new TableRef(null, null, table);
    }
    private String resolvePrimaryKeyColumn() {
        for (Column column : columns) {
            if (column.isPrimaryKey()) {
                return column.getHumpName();
            }
        }
        return columns.get(0).getHumpName();
    }
    private String resolvePrimaryKeyType() {
        for (Column column : columns) {
            if (column.isPrimaryKey()) {
                return column.getType();
            }
        }
        return columns.get(0).getType();
    }
    private String resolveMajorColumn() {
        for (Column column : columns) {
            if (column.isMajor()) {
                return column.getHumpName();
            }
        }
        for (Column column : columns) {
            if (!column.isPrimaryKey()) {
                return column.getHumpName();
            }
        }
        return primaryKeyColumn;
    }
    private String buildEntityImports() {
        Set<String> imports = new LinkedHashSet<>();
        boolean hasTableId = false;
        boolean hasTableField = false;
        boolean hasDate = false;
        boolean needCools = false;
        boolean hasSpringUtils = false;
        boolean hasTableLogic = false;
        for (Column column : columns) {
            if (column.isPrimaryKey()) {
                hasTableId = true;
            } else if (!column.getName().equals(column.getHumpName())) {
                hasTableField = true;
            }
            if ("deleted".equals(column.getName())) {
                hasTableLogic = true;
            }
            if ("Date".equals(column.getType())) {
                hasDate = true;
                needCools = true;
            }
            if (!Cools.isEmpty(column.getEnums()) || !Cools.isEmpty(column.getForeignKey())) {
                needCools = true;
            }
            if (!Cools.isEmpty(column.getForeignKey())) {
                hasSpringUtils = true;
                imports.add("import " + getForeignBasePackage(column.getForeignKey()) + ".service." + column.getForeignKey() + "Service;");
                imports.add("import " + getForeignBasePackage(column.getForeignKey()) + ".entity." + column.getForeignKey() + ";");
            }
        }
        if (needCools) {
            imports.add("import com.core.common.Cools;");
        }
        if (hasSpringUtils) {
            imports.add("import com.core.common.SpringUtils;");
        }
        if (hasTableId) {
            imports.add("import com.baomidou.mybatisplus.annotations.TableId;");
            imports.add("import com.baomidou.mybatisplus.enums.IdType;");
        }
        if (hasTableLogic) {
            imports.add("import com.baomidou.mybatisplus.annotations.TableLogic;");
        }
        if (hasTableField) {
            imports.add("import com.baomidou.mybatisplus.annotations.TableField;");
        }
        if (hasDate) {
            imports.add("import java.text.SimpleDateFormat;");
            imports.add("import java.util.Date;");
            imports.add("import org.springframework.format.annotation.DateTimeFormat;");
        }
        if (imports.isEmpty()) {
            return "";
        }
        StringBuilder builder = new StringBuilder();
        for (String item : imports) {
            builder.append(item).append("\n");
        }
        return builder.toString();
    }
    private String buildEntityContent() {
        StringBuilder builder = new StringBuilder();
        for (Column column : columns) {
            builder.append("    /**\n");
            builder.append("     * ").append(column.getWholeComment()).append("\n");
            builder.append("     */\n");
            builder.append("    @ApiModelProperty(value= \"").append(escapeJava(column.getWholeComment())).append("\")\n");
            if (column.isPrimaryKey()) {
                builder.append("    @TableId(value = \"").append(column.getName()).append("\", type = IdType.")
                        .append(column.isMainKey() ? "AUTO" : "INPUT").append(")\n");
            } else if (!column.getName().equals(column.getHumpName())) {
                builder.append("    @TableField(\"").append(column.getName()).append("\")\n");
            }
            if ("deleted".equals(column.getName())) {
                builder.append("    @TableLogic\n");
            }
            if ("Date".equals(column.getType())) {
                builder.append("    @DateTimeFormat(pattern=\"yyyy-MM-dd HH:mm:ss\")\n");
            }
            builder.append("    private ").append(column.getType()).append(" ").append(column.getHumpName()).append(";\n\n");
        }
        List<Column> constructorColumns = getNonPrimaryColumns();
        builder.append("    public ").append(fullEntityName).append("() {}\n\n");
        if (!constructorColumns.isEmpty()) {
            builder.append("    public ").append(fullEntityName).append("(");
            for (Column column : constructorColumns) {
                builder.append(column.getType()).append(" ").append(column.getHumpName()).append(",");
            }
            builder.deleteCharAt(builder.length() - 1);
            builder.append(") {\n");
            for (Column column : constructorColumns) {
                builder.append("        this.").append(column.getHumpName()).append(" = ").append(column.getHumpName()).append(";\n");
            }
            builder.append("    }\n\n");
            builder.append("//    ").append(fullEntityName).append(" ").append(simpleEntityName)
                    .append(" = new ").append(fullEntityName).append("(\n");
            for (int i = 0; i < constructorColumns.size(); i++) {
                Column column = constructorColumns.get(i);
                builder.append("//            null");
                if (i < constructorColumns.size() - 1) {
                    builder.append(",");
                }
                builder.append("    // ").append(column.getComment());
                if (column.isNotNull()) {
                    builder.append("[非空]");
                }
                if (i < constructorColumns.size() - 1) {
                    builder.append("\n");
                }
            }
            builder.append("\n//    );\n\n");
        }
        List<String> displayGetters = buildDisplayGetters();
        for (String getter : displayGetters) {
            builder.append(getter).append("\n\n");
        }
        return trimTrailingBlankLines(builder.toString());
    }
    private List<String> buildDisplayGetters() {
        List<String> getters = new ArrayList<>();
        for (Column column : columns) {
            String field = column.getHumpName();
            String methodName = GeneratorUtils.firstCharConvert(field, false);
            if ("Date".equals(column.getType())) {
                StringBuilder builder = new StringBuilder();
                builder.append("    public String get").append(methodName).append("$(){\n");
                builder.append("        if (Cools.isEmpty(this.").append(field).append(")){\n");
                builder.append("            return \"\";\n");
                builder.append("        }\n");
                builder.append("        return new SimpleDateFormat(\"yyyy-MM-dd HH:mm:ss\").format(this.").append(field).append(");\n");
                builder.append("    }");
                getters.add(builder.toString());
                continue;
            }
            if (!Cools.isEmpty(column.getEnums())) {
                StringBuilder builder = new StringBuilder();
                builder.append("    public String get").append(methodName).append("$(){\n");
                builder.append("        if (null == this.").append(field).append("){ return null; }\n");
                builder.append("        switch (String.valueOf(this.").append(field).append(")){\n");
                for (Map<String, Object> map : column.getEnums()) {
                    for (Map.Entry<String, Object> entry : map.entrySet()) {
                        builder.append("            case \"").append(escapeJava(entry.getKey())).append("\":\n");
                        builder.append("                return \"").append(escapeJava(String.valueOf(entry.getValue()))).append("\";\n");
                    }
                }
                builder.append("            default:\n");
                builder.append("                return String.valueOf(this.").append(field).append(");\n");
                builder.append("        }\n");
                builder.append("    }");
                getters.add(builder.toString());
                continue;
            }
            if (!Cools.isEmpty(column.getForeignKeyMajor())) {
                StringBuilder builder = new StringBuilder();
                builder.append("    public String get").append(methodName).append("$(){\n");
                builder.append("        ").append(column.getForeignKey()).append("Service service = SpringUtils.getBean(")
                        .append(column.getForeignKey()).append("Service.class);\n");
                builder.append("        ").append(column.getForeignKey()).append(" ")
                        .append(GeneratorUtils.firstCharConvert(column.getForeignKey())).append(" = service.selectById(this.")
                        .append(field).append(");\n");
                builder.append("        if (!Cools.isEmpty(").append(GeneratorUtils.firstCharConvert(column.getForeignKey()))
                        .append(")){\n");
                builder.append("            return String.valueOf(").append(GeneratorUtils.firstCharConvert(column.getForeignKey()))
                        .append(".get").append(column.getForeignKeyMajor()).append("());\n");
                builder.append("        }\n");
                builder.append("        return null;\n");
                builder.append("    }");
                getters.add(builder.toString());
            }
        }
        return getters;
    }
    private String buildXmlContent() {
        StringBuilder builder = new StringBuilder();
        for (Column column : columns) {
            if (column.isPrimaryKey()) {
                builder.append("        <id column=\"").append(column.getName()).append("\" property=\"")
                        .append(column.getHumpName()).append("\" />\n");
            } else {
                builder.append("        <result column=\"").append(column.getName()).append("\" property=\"")
                        .append(column.getHumpName()).append("\" />\n");
            }
        }
        return trimTrailingBlankLines(builder.toString());
    }
    private String buildHtmlSearchContent() {
        StringBuilder builder = new StringBuilder();
        builder.append("                    <div class=\"layui-inline\">\n");
        builder.append("                        <div class=\"layui-input-inline\">\n");
        builder.append("                            <input class=\"layui-input\" type=\"text\" name=\"condition\" placeholder=\"请输入\" autocomplete=\"off\">\n");
        builder.append("                        </div>\n");
        builder.append("                    </div>\n");
        Column rangeColumn = resolveRangeSearchColumn();
        if (rangeColumn != null) {
            builder.append("                    <div class=\"layui-inline\" style=\"width: 300px\">\n");
            builder.append("                        <div class=\"layui-input-inline\">\n");
            builder.append("                            <input class=\"layui-input layui-laydate-range\" name=\"")
                    .append(rangeColumn.getName()).append("\" type=\"text\" placeholder=\"")
                    .append(GeneratorUtils.supportHtmlName(rangeColumn.getComment()))
                    .append("范围\" autocomplete=\"off\" style=\"width: 300px\">\n");
            builder.append("                        </div>\n");
            builder.append("                    </div>\n");
        }
        return trimTrailingBlankLines(builder.toString());
    }
    private String buildHtmlDialogContent() {
        StringBuilder builder = new StringBuilder();
        for (Column column : columns) {
            String field = column.getHumpName();
            if (column.isPrimaryKey()) {
                builder.append("                <input name=\"").append(field).append("\" type=\"hidden\">\n");
                continue;
            }
            builder.append("                <div class=\"layui-form-item\">\n");
            builder.append("                    <label class=\"layui-form-label");
            if (column.isNotNull()) {
                builder.append(" layui-form-required");
            }
            builder.append("\">").append(column.getComment()).append(": </label>\n");
            builder.append("                    <div class=\"layui-input-block");
            if (!Cools.isEmpty(column.getForeignKeyMajor())) {
                builder.append(" cool-auto-complete");
            }
            builder.append("\">\n");
            appendFormField(builder, column, "                        ");
            builder.append("                    </div>\n");
            builder.append("                </div>\n");
        }
        return trimTrailingBlankLines(builder.toString());
    }
    private String buildHtmlDetailContent() {
        StringBuilder builder = new StringBuilder();
        for (Column column : columns) {
            String field = column.getHumpName();
            String label = GeneratorUtils.supportHtmlName(column.getComment());
            if (column.isPrimaryKey()) {
                builder.append("        <div class=\"layui-inline\" style=\"display: none\">\n");
                builder.append("            <label class=\"layui-form-label\">").append(label).append(":</label>\n");
                builder.append("            <div class=\"layui-input-inline\">\n");
                builder.append("                <input id=\"").append(field).append("\" class=\"layui-input\" type=\"text\" placeholder=\"")
                        .append(column.getComment()).append("\">\n");
                builder.append("            </div>\n");
                builder.append("        </div>\n");
                continue;
            }
            builder.append("        <div class=\"layui-inline\">\n");
            builder.append("            <label class=\"layui-form-label\">");
            if (column.isNotNull()) {
                builder.append("<span class=\"not-null\">*</span>");
            }
            builder.append(label).append(":</label>\n");
            builder.append("            <div class=\"layui-input-inline");
            if (!Cools.isEmpty(column.getForeignKeyMajor())) {
                builder.append(" cool-auto-complete");
            }
            builder.append("\">\n");
            appendDetailFormField(builder, column, "                ");
            builder.append("            </div>\n");
            builder.append("        </div>\n");
        }
        return trimTrailingBlankLines(builder.toString());
    }
    private String buildJsTableContent() {
        StringBuilder builder = new StringBuilder();
        for (Column column : columns) {
            String field = resolveDisplayField(column);
            builder.append("            ,{field: '").append(field).append("', align: 'center',title: '")
                    .append(escapeJs(column.getComment())).append("'");
            if (column.isCheckBox()) {
                builder.append(", templet:function(row){\n")
                        .append("                    var html = \"<input value='").append(column.getHumpName())
                        .append("' type='checkbox' lay-skin='primary' lay-filter='tableCheckbox' table-index='\"+row.LAY_TABLE_INDEX+\"'\";\n")
                        .append("                    if(row.").append(column.getHumpName()).append(" === 'Y'){html += \" checked \";}\n")
                        .append("                    html += \">\";\n")
                        .append("                    return html;\n")
                        .append("                }");
            }
            if (column.isPrimaryKey()) {
                builder.append(", sort: true");
            }
            builder.append("}\n");
        }
        return trimTrailingBlankLines(builder.toString());
    }
    private String buildJsDateContent() {
        StringBuilder builder = new StringBuilder();
        for (Column column : columns) {
            if (column.isPrimaryKey()) {
                continue;
            }
            if (!"Date".equals(column.getType())) {
                continue;
            }
            builder.append("            layDate.render({\n");
            builder.append("                elem: '#").append(column.getHumpName()).append("$',\n");
            builder.append("                type: 'datetime',\n");
            builder.append("                value: data!==undefined?data['").append(column.getHumpName()).append("$']:null\n");
            builder.append("            });\n");
        }
        return trimTrailingBlankLines(builder.toString());
    }
    private String resolveDisplayField(Column column) {
        if ("Date".equals(column.getType()) || !Cools.isEmpty(column.getEnums()) || !Cools.isEmpty(column.getForeignKeyMajor())) {
            return column.getHumpName() + "$";
        }
        return column.getHumpName();
    }
    private List<Column> getNonPrimaryColumns() {
        List<Column> result = new ArrayList<>();
        for (Column column : columns) {
            if (!column.isPrimaryKey()) {
                result.add(column);
            }
        }
        return result;
    }
    private Column resolveRangeSearchColumn() {
        for (Column column : columns) {
            if ("Date".equals(column.getType()) && ("create_time".equals(column.getName()) || "createTime".equals(column.getHumpName()))) {
                return column;
            }
        }
        for (Column column : columns) {
            if ("Date".equals(column.getType())) {
                return column;
            }
        }
        return null;
    }
    private String getForeignBasePackage(String foreignKey) {
        if (SYSTEM_MODEL.contains(foreignKey)) {
            return systemPackage + ".system";
        }
        return packagePath;
    }
    private void appendFormField(StringBuilder builder, Column column, String inputIndent) {
        String field = column.getHumpName();
        if (Cools.isEmpty(column.getEnums())) {
            builder.append(inputIndent).append("<input class=\"layui-input\" name=\"").append(field);
            if ("Date".equals(column.getType())) {
                builder.append("\" id=\"").append(field).append("$");
            }
            builder.append("\" placeholder=\"请输入").append(column.getComment()).append("\"");
            if (column.isNotNull()) {
                builder.append(" lay-vertype=\"tips\" lay-verify=\"required\"");
            }
            if (!Cools.isEmpty(column.getForeignKeyMajor())) {
                builder.append(" style=\"display: none\"");
            }
            builder.append(" autocomplete=\"off\">\n");
            if (!Cools.isEmpty(column.getForeignKeyMajor())) {
                String queryKey = GeneratorUtils.firstCharConvert(column.getForeignKey()) + "QueryBy" + field;
                builder.append(inputIndent).append("<input id=\"").append(field).append("$\" name=\"").append(field)
                        .append("$\" class=\"layui-input cool-auto-complete-div\" onclick=\"autoShow(this.id)\" type=\"text\" placeholder=\"请输入")
                        .append(column.getComment()).append("\" onfocus=this.blur() autocomplete=\"off\">\n");
                builder.append(inputIndent).append("<div class=\"cool-auto-complete-window\">\n");
                builder.append(inputIndent).append("    <input class=\"cool-auto-complete-window-input\" data-key=\"")
                        .append(queryKey).append("\" onkeyup=\"autoLoad(this.getAttribute('data-key'))\">\n");
                builder.append(inputIndent).append("    <select class=\"cool-auto-complete-window-select\" data-key=\"")
                        .append(queryKey).append("Select\" onchange=\"confirmed(this.getAttribute('data-key'))\" multiple=\"multiple\">\n");
                builder.append(inputIndent).append("    </select>\n");
                builder.append(inputIndent).append("</div>\n");
            }
            return;
        }
        builder.append(inputIndent).append("<select name=\"").append(field).append("\"");
        if (column.isNotNull()) {
            builder.append(" lay-vertype=\"tips\" lay-verify=\"required\"");
        }
        builder.append(">\n");
        builder.append(inputIndent).append("    <option value=\"\">请选择").append(column.getComment()).append("</option>\n");
        for (Map<String, Object> map : column.getEnums()) {
            for (Map.Entry<String, Object> entry : map.entrySet()) {
                builder.append(inputIndent).append("    <option value=\"").append(entry.getKey()).append("\">")
                        .append(entry.getValue()).append("</option>\n");
            }
        }
        builder.append(inputIndent).append("</select>\n");
    }
    private void appendDetailFormField(StringBuilder builder, Column column, String inputIndent) {
        String field = column.getHumpName();
        if (Cools.isEmpty(column.getEnums())) {
            if (!Cools.isEmpty(column.getForeignKeyMajor())) {
                String queryKey = GeneratorUtils.firstCharConvert(column.getForeignKey()) + "QueryBy" + field;
                builder.append(inputIndent).append("<input id=\"").append(field)
                        .append("\" class=\"layui-input\" type=\"text\" style=\"display: none\">\n");
                builder.append(inputIndent).append("<input id=\"").append(field).append("$\" class=\"layui-input cool-auto-complete-div\" onclick=\"autoShow(this.id)\" type=\"text\" placeholder=\"请输入")
                        .append(column.getComment()).append("\" onfocus=this.blur() autocomplete=\"off\">\n");
                builder.append(inputIndent).append("<div class=\"cool-auto-complete-window\">\n");
                builder.append(inputIndent).append("    <input class=\"cool-auto-complete-window-input\" data-key=\"")
                        .append(queryKey).append("\" onkeyup=\"autoLoad(this.getAttribute('data-key'))\">\n");
                builder.append(inputIndent).append("    <select class=\"cool-auto-complete-window-select\" data-key=\"")
                        .append(queryKey).append("Select\" onchange=\"confirmed(this.getAttribute('data-key'))\" multiple=\"multiple\">\n");
                builder.append(inputIndent).append("    </select>\n");
                builder.append(inputIndent).append("</div>\n");
                return;
            }
            builder.append(inputIndent).append("<input id=\"").append(field);
            if ("Date".equals(column.getType())) {
                builder.append("$");
            }
            builder.append("\" class=\"layui-input\" type=\"text\" placeholder=\"").append(column.getComment())
                    .append("\" autocomplete=\"off\"");
            if (column.isNotNull()) {
                builder.append(" lay-verify=\"required\"");
            }
            builder.append(">\n");
            return;
        }
        builder.append(inputIndent).append("<select id=\"").append(field).append("\"");
        if (column.isNotNull()) {
            builder.append(" lay-verify=\"required\"");
        }
        builder.append(">\n");
        builder.append(inputIndent).append("    <option value=\"\">请选择").append(column.getComment()).append("</option>\n");
        for (Map<String, Object> map : column.getEnums()) {
            for (Map.Entry<String, Object> entry : map.entrySet()) {
                builder.append(inputIndent).append("    <option value=\"").append(entry.getKey()).append("\">")
                        .append(entry.getValue()).append("</option>\n");
            }
        }
        builder.append(inputIndent).append("</select>\n");
    }
    private String renderTemplate(String template) {
        Map<String, String> values = new LinkedHashMap<>();
        values.put("COMPANYNAME", packagePath);
        values.put("SYSTEMPACKAGE", systemPackage);
        values.put("ENTITYNAME", fullEntityName);
        values.put("SIMPLEENTITYNAME", simpleEntityName);
        values.put("TABLENAME", table);
        values.put("ENTITYIMPORT", entityImport);
        values.put("ENTITYCONTENT", entityContent);
        values.put("XMLCONTENT", xmlContent);
        values.put("HTMLSEARCHCONTENT", htmlSearchContent);
        values.put("HTMLDIALOGCONTENT", htmlDialogContent);
        values.put("HTMLDETAILCONTENT", htmlDetailContent);
        values.put("JSTABLECONTENT", jsTableContent);
        values.put("JSDATECONTENT", jsDateContent);
        values.put("PRIMARYKEYCOLUMN", GeneratorUtils.firstCharConvert(primaryKeyColumn, false));
        values.put("PRIMARYKEYCOLUMN0", primaryKeyColumn);
        values.put("PRIMARYKEYTYPE", primaryKeyType);
        values.put("MAJORCOLUMN", GeneratorUtils.humpToLine(majorColumn));
        values.put("UPCASEMARJORCOLUMN", GeneratorUtils.firstCharConvert(majorColumn, false));
        String content = template;
        for (Map.Entry<String, String> entry : values.entrySet()) {
            content = content.replace("@{" + entry.getKey() + "}", entry.getValue() == null ? "" : entry.getValue());
        }
        return content;
    }
    private void writeFile(String dir, String fileName, String content, String templateName) throws IOException {
        Path directory = Paths.get(dir);
        Files.createDirectories(directory);
        Path file = directory.resolve(fileName);
        if (Files.exists(file)) {
            System.out.println(fullEntityName + templateName + " 源文件已经存在创建失败!");
            return;
        }
        try {
            Files.write(file, content.getBytes(StandardCharsets.UTF_8),
                    StandardOpenOption.CREATE_NEW, StandardOpenOption.WRITE);
            System.out.println(fullEntityName + templateName + " 源文件创建成功!");
        } catch (FileAlreadyExistsException e) {
            System.out.println(fullEntityName + templateName + " 源文件已经存在创建失败!");
        }
    }
    private String loadTemplate(String name) throws IOException {
        InputStream inputStream = Thread.currentThread().getContextClassLoader().getResourceAsStream("templates/" + name);
        if (inputStream == null) {
            throw new IOException("template not found: " + name);
        }
        try {
            ByteArrayOutputStream output = new ByteArrayOutputStream();
            byte[] buffer = new byte[1024];
            int len;
            while ((len = inputStream.read(buffer)) != -1) {
                output.write(buffer, 0, len);
            }
            return new String(output.toByteArray(), StandardCharsets.UTF_8);
        } finally {
            inputStream.close();
        }
    }
    private String trimTrailingBlankLines(String text) {
        String trimmed = text;
        while (trimmed.endsWith("\n\n")) {
            trimmed = trimmed.substring(0, trimmed.length() - 1);
        }
        return trimmed;
    }
    private String escapeJava(String text) {
        return text == null ? "" : text.replace("\\", "\\\\").replace("\"", "\\\"");
    }
    private String escapeJs(String text) {
        return escapeJava(text).replace("'", "\\'");
    }
    private static class TableRef {
        private final String catalog;
        private final String schema;
        private final String table;
        private TableRef(String catalog, String schema, String table) {
            this.catalog = catalog;
            this.schema = schema;
            this.table = table;
        }
    }
}
src/main/java/com/core/generators/constant/SqlOsType.java
New file
@@ -0,0 +1,6 @@
package com.core.generators.constant;
public enum SqlOsType {
    MYSQL,
    SQL_SERVER
}
src/main/java/com/core/generators/domain/Column.java
New file
@@ -0,0 +1,265 @@
package com.core.generators.domain;
import com.core.common.Cools;
import com.core.generators.CoolGenerator;
import com.core.generators.constant.SqlOsType;
import com.core.generators.utils.GeneratorUtils;
import java.sql.Connection;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class Column {
    private String name;
    private String type;
    private String comment;
    private String humpName;
    private boolean primaryKey;
    private boolean mainKey;
    private boolean notNull;
    private boolean major;
    private boolean image;
    private boolean checkBox;
    private String foreignKey;
    private String foreignKeyMajor;
    private List<Map<String, Object>> enums;
    private Integer length;
    public Column(Connection connection, String name, String type, String comment, boolean primaryKey,
                  boolean mainKey, boolean notNull, Integer length, boolean withForeignKey, SqlOsType sqlOsType) {
        this.name = name;
        this.type = type;
        this.comment = "";
        if (!Cools.isEmpty(comment)) {
            Pattern enumTitlePattern = Pattern.compile("(.+?)(?=\\{)");
            Matcher enumTitleMatcher = enumTitlePattern.matcher(comment);
            Pattern foreignTitlePattern = Pattern.compile("(.+?)(?=\\[)");
            Matcher foreignTitleMatcher = foreignTitlePattern.matcher(comment);
            if (enumTitleMatcher.find()) {
                this.comment = enumTitleMatcher.group();
                Pattern enumPattern = Pattern.compile("(?<=\\{)(.+?)(?=})");
                Matcher enumMatcher = enumPattern.matcher(comment);
                if (enumMatcher.find()) {
                    String enumText = enumMatcher.group();
                    if (!Cools.isEmpty(enumText)) {
                        String[] enumArr = enumText.split(",");
                        this.enums = new ArrayList<>();
                        for (String item : enumArr) {
                            Map<String, Object> map = new HashMap<>();
                            String[] pair = item.split(":");
                            if (pair.length >= 2) {
                                map.put(pair[0], pair[1]);
                                this.enums.add(map);
                            }
                        }
                    }
                }
            } else if (foreignTitleMatcher.find()) {
                this.comment = foreignTitleMatcher.group();
                Pattern foreignPattern = Pattern.compile("(?<=\\[)(.+?)(?=])");
                Matcher foreignMatcher = foreignPattern.matcher(comment);
                if (foreignMatcher.find()) {
                    String foreignTable = foreignMatcher.group();
                    if (!Cools.isEmpty(foreignTable)) {
                        this.foreignKey = GeneratorUtils.getNameSpace(foreignTable);
                        List<Column> foreignColumns = new ArrayList<>();
                        if (withForeignKey) {
                            try {
                                switch (sqlOsType) {
                                    case MYSQL:
                                        foreignColumns = CoolGenerator.getMysqlColumns(connection, foreignTable, false, sqlOsType);
                                        break;
                                    case SQL_SERVER:
                                        foreignColumns = CoolGenerator.getSqlServerColumns(connection, foreignTable, false, sqlOsType);
                                        break;
                                    default:
                                        break;
                                }
                            } catch (Exception ex) {
                                ex.printStackTrace();
                            }
                        }
                        if (!Cools.isEmpty(foreignColumns)) {
                            for (Column column : foreignColumns) {
                                if (column.isMajor()) {
                                    this.foreignKeyMajor = GeneratorUtils.firstCharConvert(column.getHumpName(), false);
                                }
                            }
                            if (Cools.isEmpty(this.foreignKeyMajor)) {
                                this.foreignKeyMajor = "Id";
                            }
                        }
                    }
                }
            } else {
                this.comment = comment;
            }
            if (comment.endsWith("(*)")) {
                this.comment = comment.substring(0, comment.length() - 3);
                this.major = true;
            }
            if (comment.endsWith("(img)")) {
                this.comment = comment.substring(0, comment.length() - 5);
                this.image = true;
            }
            if (comment.endsWith("(checkbox)")) {
                this.comment = comment.substring(0, comment.length() - 10);
                this.checkBox = true;
            }
        }
        this.primaryKey = primaryKey;
        this.mainKey = mainKey;
        this.notNull = notNull;
        this.length = length;
        this.humpName = GeneratorUtils._convert(name);
    }
    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public String getType() {
        return type;
    }
    public void setType(String type) {
        this.type = type;
    }
    public String getComment() {
        return comment;
    }
    public String getWholeComment() {
        if (!Cools.isEmpty(this.enums)) {
            StringBuilder builder = new StringBuilder("");
            for (Map<String, Object> map : this.enums) {
                for (Map.Entry<String, Object> entry : map.entrySet()) {
                    builder.append(entry.getKey()).append(":").append(entry.getValue()).append("  ");
                }
            }
            return new StringBuilder().append(this.comment).append(builder.toString()).toString();
        }
        return this.comment;
    }
    public void setComment(String comment) {
        this.comment = comment;
    }
    public String getHumpName() {
        return humpName;
    }
    public boolean isPrimaryKey() {
        return primaryKey;
    }
    public boolean isOnly() {
        return primaryKey;
    }
    public void setPrimaryKey(boolean primaryKey) {
        this.primaryKey = primaryKey;
    }
    public boolean isNotNull() {
        return notNull;
    }
    public void setNotNull(boolean notNull) {
        this.notNull = notNull;
    }
    public String getForeignKey() {
        return foreignKey;
    }
    public void setForeignKey(String foreignKey) {
        this.foreignKey = foreignKey;
    }
    public String getForeignKeyMajor() {
        return foreignKeyMajor;
    }
    public void setForeignKeyMajor(String foreignKeyMajor) {
        this.foreignKeyMajor = foreignKeyMajor;
    }
    public List<Map<String, Object>> getEnums() {
        return enums;
    }
    public void setEnums(List<Map<String, Object>> enums) {
        this.enums = enums;
    }
    public Integer getLength() {
        return length;
    }
    public void setLength(Integer length) {
        this.length = length;
    }
    public boolean isMajor() {
        return major;
    }
    public void setMajor(boolean major) {
        this.major = major;
    }
    public boolean isImage() {
        return image;
    }
    public void setImage(boolean image) {
        this.image = image;
    }
    public boolean isCheckBox() {
        return checkBox;
    }
    public void setCheckBox(boolean checkBox) {
        this.checkBox = checkBox;
    }
    public boolean isMainKey() {
        return mainKey;
    }
    public void setMainKey(boolean mainKey) {
        this.mainKey = mainKey;
    }
    @Override
    public String toString() {
        return new StringBuilder()
                .append("Column{name='").append(name).append('\'')
                .append(", type='").append(type).append('\'')
                .append(", comment='").append(comment).append('\'')
                .append(", humpName='").append(humpName).append('\'')
                .append(", primaryKey=").append(primaryKey)
                .append(", notNull=").append(notNull)
                .append(", major=").append(major)
                .append(", image=").append(image)
                .append(", foreignKey='").append(foreignKey).append('\'')
                .append(", foreignKeyMajor='").append(foreignKeyMajor).append('\'')
                .append(", enums=").append(enums)
                .append(", length=").append(length)
                .append('}')
                .toString();
    }
}
src/main/java/com/core/generators/utils/GeneratorUtils.java
New file
@@ -0,0 +1,134 @@
package com.core.generators.utils;
import com.core.common.Cools;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class GeneratorUtils {
    public static String _convert(String text, boolean keepFirst) {
        String[] arr = text.split("_");
        StringBuilder builder = new StringBuilder();
        for (int i = 0; i < arr.length; i++) {
            if (i == 0 && keepFirst) {
                builder.append(arr[i]);
            } else {
                builder.append(arr[i].substring(0, 1).toUpperCase()).append(arr[i].substring(1));
            }
        }
        return builder.toString();
    }
    public static String _convert(String text) {
        return _convert(text, true);
    }
    public static String getType(int sqlType) {
        switch (sqlType) {
            case -7:
                return "Boolean";
            case -6:
            case 5:
                return "Short";
            case 4:
                return "Integer";
            case -5:
                return "Long";
            case 8:
            case 3:
                return "Double";
            case -15:
            case -9:
            case 1:
            case 12:
            case 2004:
            case -1:
                return "String";
            case 91:
            case 93:
                return "Date";
            default:
                return null;
        }
    }
    public static String getNameSpace(String tableName) {
        String[] arr = tableName.split("_");
        StringBuilder builder = new StringBuilder();
        for (int i = 1; i < arr.length; i++) {
            if (i != 1) {
                builder.append("_");
            }
            builder.append(arr[i]);
        }
        return _convert(builder.toString(), false);
    }
    public static String supportHtmlName(String name) {
        if (Cools.isEmpty(name)) {
            return "";
        }
        if (name.length() == 2) {
            return new StringBuilder()
                    .append(name.charAt(0))
                    .append("  ")
                    .append(name.charAt(1))
                    .toString();
        }
        if (name.length() == 3) {
            return new StringBuilder()
                    .append(name.charAt(0))
                    .append(" ")
                    .append(name.charAt(1))
                    .append(" ")
                    .append(name.charAt(2))
                    .toString();
        }
        return name;
    }
    public static Integer getColumnLength(String typeText) {
        if (Cools.isEmpty(typeText)) {
            return null;
        }
        Pattern pattern = Pattern.compile("(?<=\\()(.+?)(?=\\))");
        Matcher matcher = pattern.matcher(typeText);
        if (matcher.find()) {
            String value = matcher.group();
            if (value.contains(",")) {
                value = value.split(",")[0];
            }
            return Integer.valueOf(Integer.parseInt(value));
        }
        return null;
    }
    public static String firstCharConvert(String text, boolean lower) {
        if (Cools.isEmpty(text)) {
            return "";
        }
        String first = text.substring(0, 1);
        if (lower) {
            first = first.toLowerCase();
        } else {
            first = first.toUpperCase();
        }
        return new StringBuilder().append(first).append(text.substring(1)).toString();
    }
    public static String firstCharConvert(String text) {
        return firstCharConvert(text, true);
    }
    public static String humpToLine(String text) {
        Pattern pattern = Pattern.compile("[A-Z]");
        Matcher matcher = pattern.matcher(text);
        StringBuffer buffer = new StringBuffer();
        while (matcher.find()) {
            matcher.appendReplacement(buffer, "_" + matcher.group(0).toLowerCase());
        }
        matcher.appendTail(buffer);
        return buffer.toString();
    }
}
src/main/java/com/core/utils/Algorithm.java
New file
@@ -0,0 +1,10 @@
package com.core.utils;
/**
 * 算法
 */
public class Algorithm {
    private Algorithm() {
    }
}
src/main/java/com/core/utils/SignUtils.java
New file
@@ -0,0 +1,30 @@
package com.core.utils;
import com.core.common.Cools;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
public class SignUtils {
    public static String sign(Map<String, Object> param, String key) {
        List<String> list = new ArrayList<>();
        for (String mapKey : param.keySet()) {
            Object value = param.get(mapKey);
            if ("sign".equals(mapKey) || value == null) {
                continue;
            }
            list.add(mapKey + "=" + value + "&");
        }
        String[] arr = list.toArray(new String[0]);
        Arrays.sort(arr, String.CASE_INSENSITIVE_ORDER);
        StringBuilder builder = new StringBuilder();
        for (String item : arr) {
            builder.append(item);
        }
        String text = builder.toString() + "key=" + key;
        return Cools.md5(text).toUpperCase();
    }
}
src/main/resources/META-INF/spring.factories
New file
@@ -0,0 +1 @@
org.springframework.boot.autoconfigure.EnableAutoConfiguration=com.core.config.CoolBaseConfig
src/main/resources/templates/Controller.txt
New file
@@ -0,0 +1,139 @@
package @{COMPANYNAME}.controller;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.mapper.EntityWrapper;
import com.baomidou.mybatisplus.mapper.Wrapper;
import com.baomidou.mybatisplus.plugins.Page;
import com.core.common.DateUtils;
import com.core.domain.KeyValueVo;
import @{COMPANYNAME}.entity.@{ENTITYNAME};
import @{COMPANYNAME}.service.@{ENTITYNAME}Service;
import com.core.annotations.ManagerAuth;
import com.core.common.BaseRes;
import com.core.common.Cools;
import com.core.common.R;
import @{SYSTEMPACKAGE}.common.web.BaseController;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.*;
@RestController
public class @{ENTITYNAME}Controller extends BaseController {
    @Autowired
    private @{ENTITYNAME}Service @{SIMPLEENTITYNAME}Service;
    @RequestMapping(value = "/@{SIMPLEENTITYNAME}/{id}/auth")
    @ManagerAuth
    public R get(@PathVariable("id") String id) {
        return R.ok(@{SIMPLEENTITYNAME}Service.selectById(String.valueOf(id)));
    }
    @RequestMapping(value = "/@{SIMPLEENTITYNAME}/list/auth")
    @ManagerAuth
    public R list(@RequestParam(defaultValue = "1")Integer curr,
                  @RequestParam(defaultValue = "10")Integer limit,
                  @RequestParam(required = false)String orderByField,
                  @RequestParam(required = false)String orderByType,
                  @RequestParam(required = false)String condition,
                  @RequestParam Map<String, Object> param){
        EntityWrapper<@{ENTITYNAME}> wrapper = new EntityWrapper<>();
        excludeTrash(param);
        convert(param, wrapper);
        allLike(@{ENTITYNAME}.class, param.keySet(), wrapper, condition);
        if (!Cools.isEmpty(orderByField)){wrapper.orderBy(humpToLine(orderByField), "asc".equals(orderByType));}
        return R.ok(@{SIMPLEENTITYNAME}Service.selectPage(new Page<>(curr, limit), wrapper));
    }
    private <T> void convert(Map<String, Object> map, EntityWrapper<T> wrapper){
        for (Map.Entry<String, Object> entry : map.entrySet()){
            String val = String.valueOf(entry.getValue());
            if (val.contains(RANGE_TIME_LINK)){
                String[] dates = val.split(RANGE_TIME_LINK);
                wrapper.ge(entry.getKey(), DateUtils.convert(dates[0]));
                wrapper.le(entry.getKey(), DateUtils.convert(dates[1]));
            } else {
                wrapper.like(entry.getKey(), val);
            }
        }
    }
    @RequestMapping(value = "/@{SIMPLEENTITYNAME}/add/auth")
    @ManagerAuth
    public R add(@{ENTITYNAME} @{SIMPLEENTITYNAME}) {
        @{SIMPLEENTITYNAME}Service.insert(@{SIMPLEENTITYNAME});
        return R.ok();
    }
    @RequestMapping(value = "/@{SIMPLEENTITYNAME}/update/auth")
    @ManagerAuth
    public R update(@{ENTITYNAME} @{SIMPLEENTITYNAME}){
        if (Cools.isEmpty(@{SIMPLEENTITYNAME}) || null==@{SIMPLEENTITYNAME}.get@{PRIMARYKEYCOLUMN}()){
            return R.error();
        }
        @{SIMPLEENTITYNAME}Service.updateById(@{SIMPLEENTITYNAME});
        return R.ok();
    }
    @RequestMapping(value = "/@{SIMPLEENTITYNAME}/delete/auth")
    @ManagerAuth
    public R delete(@RequestParam(value="ids[]") @{PRIMARYKEYTYPE}[] ids){
         for (@{PRIMARYKEYTYPE} id : ids){
            @{SIMPLEENTITYNAME}Service.deleteById(id);
        }
        return R.ok();
    }
    @RequestMapping(value = "/@{SIMPLEENTITYNAME}/export/auth")
    @ManagerAuth
    public R export(@RequestBody JSONObject param){
        EntityWrapper<@{ENTITYNAME}> wrapper = new EntityWrapper<>();
        List<String> fields = JSONObject.parseArray(param.getJSONArray("fields").toJSONString(), String.class);
        Map<String, Object> map = excludeTrash(param.getJSONObject("@{SIMPLEENTITYNAME}"));
        convert(map, wrapper);
        List<@{ENTITYNAME}> list = @{SIMPLEENTITYNAME}Service.selectList(wrapper);
        return R.ok(exportSupport(list, fields));
    }
    @RequestMapping(value = "/@{SIMPLEENTITYNAME}Query/auth")
    @ManagerAuth
    public R query(String condition) {
        EntityWrapper<@{ENTITYNAME}> wrapper = new EntityWrapper<>();
        wrapper.like("@{MAJORCOLUMN}", condition);
        Page<@{ENTITYNAME}> page = @{SIMPLEENTITYNAME}Service.selectPage(new Page<>(0, 10), wrapper);
        List<Map<String, Object>> result = new ArrayList<>();
        for (@{ENTITYNAME} @{SIMPLEENTITYNAME} : page.getRecords()){
            Map<String, Object> map = new HashMap<>();
            map.put("id", @{SIMPLEENTITYNAME}.get@{PRIMARYKEYCOLUMN}());
            map.put("value", @{SIMPLEENTITYNAME}.get@{UPCASEMARJORCOLUMN}());
            result.add(map);
        }
        return R.ok(result);
    }
    @RequestMapping("/@{SIMPLEENTITYNAME}/all/get/kv")
    @ManagerAuth
    public R getDataKV(@RequestParam(required = false) String condition) {
        List<KeyValueVo> vos = new ArrayList<>();
        EntityWrapper<@{ENTITYNAME}> wrapper = new EntityWrapper<>();
        if (!Cools.isEmpty(condition)) {
            wrapper.like("@{MAJORCOLUMN}", condition);
        }
        @{SIMPLEENTITYNAME}Service.selectPage(new Page<>(1, 30), wrapper).getRecords()
                .forEach(item -> vos.add(new KeyValueVo(String.valueOf(item.get@{UPCASEMARJORCOLUMN}()), item.get@{PRIMARYKEYCOLUMN}())));
        return R.ok().add(vos);
    }
    @RequestMapping(value = "/@{SIMPLEENTITYNAME}/check/column/auth")
    @ManagerAuth
    public R query(@RequestBody JSONObject param) {
        Wrapper<@{ENTITYNAME}> wrapper = new EntityWrapper<@{ENTITYNAME}>().eq(humpToLine(String.valueOf(param.get("key"))), param.get("val"));
        if (null != @{SIMPLEENTITYNAME}Service.selectOne(wrapper)){
            return R.parse(BaseRes.REPEAT).add(getComment(@{ENTITYNAME}.class, String.valueOf(param.get("key"))));
        }
        return R.ok();
    }
}
src/main/resources/templates/Entity.txt
New file
@@ -0,0 +1,16 @@
package @{COMPANYNAME}.entity;
@{ENTITYIMPORT}
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import com.baomidou.mybatisplus.annotations.TableName;
import java.io.Serializable;
@Data
@TableName("@{TABLENAME}")
public class @{ENTITYNAME} implements Serializable {
    private static final long serialVersionUID = 1L;
@{ENTITYCONTENT}
}
src/main/resources/templates/Html.txt
New file
@@ -0,0 +1,70 @@
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <title></title>
    <meta name="renderer" content="webkit">
    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
    <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
    <link rel="stylesheet" href="../../static/layui/css/layui.css" media="all">
    <link rel="stylesheet" href="../../static/css/admin.css?v=318" media="all">
    <link rel="stylesheet" href="../../static/css/cool.css" media="all">
</head>
<body>
<div class="layui-fluid">
    <div class="layui-card">
        <div class="layui-card-body">
            <div class="layui-form toolbar" id="search-box">
                <div class="layui-form-item">
@{HTMLSEARCHCONTENT}
                    <div class="layui-inline">&emsp;
                        <button class="layui-btn icon-btn" lay-filter="search" lay-submit>
                            <i class="layui-icon">&#xe615;</i>搜索
                        </button>
                        <button class="layui-btn icon-btn" lay-filter="reset" lay-submit>
                            <i class="layui-icon">&#xe666;</i>重置
                        </button>
                    </div>
                </div>
            </div>
            <table class="layui-hide" id="@{SIMPLEENTITYNAME}" lay-filter="@{SIMPLEENTITYNAME}"></table>
        </div>
    </div>
</div>
<script type="text/html" id="toolbar">
    <div class="layui-btn-container">
        <button class="layui-btn layui-btn-sm" id="btn-add" lay-event="addData">新增</button>
        <button class="layui-btn layui-btn-sm layui-btn-danger" id="btn-delete" lay-event="deleteData">删除</button>
        <button class="layui-btn layui-btn-primary layui-btn-sm" id="btn-export" lay-event="exportData" style="float: right">导出</button>
    </div>
</script>
<script type="text/html" id="operate">
    <a class="layui-btn layui-btn-primary layui-btn-xs btn-edit" lay-event="edit">修改</a>
    <a class="layui-btn layui-btn-danger layui-btn-xs btn-edit" lay-event="del">删除</a>
</script>
<script type="text/javascript" src="../../static/js/jquery/jquery-3.3.1.min.js"></script>
<script type="text/javascript" src="../../static/layui/layui.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/common.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/cool.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/@{SIMPLEENTITYNAME}/@{SIMPLEENTITYNAME}.js" charset="utf-8"></script>
</body>
<!-- 表单弹窗 -->
<script type="text/html" id="editDialog">
    <form id="detail" lay-filter="detail" class="layui-form admin-form model-form">
        <div class="layui-row">
            <div class="layui-col-md12">
@{HTMLDIALOGCONTENT}
             </div>
        </div>
        <hr class="layui-bg-gray">
        <div class="layui-form-item text-right">
            <button class="layui-btn" lay-filter="editSubmit" lay-submit="">保存</button>
            <button class="layui-btn layui-btn-primary" type="button" ew-event="closeDialog">取消</button>
        </div>
    </form>
</script>
</html>
src/main/resources/templates/HtmlDetail.txt
New file
@@ -0,0 +1,48 @@
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <title></title>
    <meta name="renderer" content="webkit">
    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
    <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1">
    <link rel="stylesheet" href="../../static/layui/css/layui.css" media="all">
    <link rel="stylesheet" href="../../static/css/cool.css" media="all">
    <link rel="stylesheet" href="../../static/css/common.css" media="all">
</head>
<body>
<!-- 详情 -->
<div id="data-detail" class="layer_self_wrap">
    <form id="detail" class="layui-form">
    <!--
        <div class="layui-inline"  style="display: none">
            <label class="layui-form-label"><span class="not-null">*</span>编  号:</label>
            <div class="layui-input-inline">
                <input id="id" class="layui-input" type="text" placeholder="编号">
            </div>
        </div>
    -->
@{HTMLDETAILCONTENT}
        <hr class="layui-bg-gray">
        <div id="data-detail-btn" class="layui-btn-container layui-form-item">
            <div id="data-detail-submit-save" type="button" class="layui-btn layui-btn-normal" lay-submit lay-filter="save">保存</div>
            <div id="data-detail-submit-edit" type="button" class="layui-btn layui-btn-normal" lay-submit lay-filter="edit">修改</div>
            <div id="data-detail-close" type="button" class="layui-btn" lay-submit lay-filter="close">关闭</div>
        </div>
        <div id="prompt">
            温馨提示:请仔细填写相关信息,<span class="extrude"><span class="not-null">*</span> 为必填选项。</span>
        </div>
    </form>
</div>
</body>
<script type="text/javascript" src="../../static/js/jquery/jquery-3.3.1.min.js"></script>
<script type="text/javascript" src="../../static/layui/layui.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/common.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/cool.js" charset="utf-8"></script>
<script type="text/javascript" src="../../static/js/@{SIMPLEENTITYNAME}/@{SIMPLEENTITYNAME}.js" charset="utf-8"></script>
</html>
src/main/resources/templates/Js.txt
New file
@@ -0,0 +1,244 @@
var pageCurr;
layui.config({
    base: baseUrl + "/static/layui/lay/modules/"
}).use(['table','laydate', 'form', 'admin'], function(){
    var table = layui.table;
    var $ = layui.jquery;
    var layer = layui.layer;
    var layDate = layui.laydate;
    var form = layui.form;
    var admin = layui.admin;
    // 数据渲染
    tableIns = table.render({
        elem: '#@{SIMPLEENTITYNAME}',
        headers: {token: localStorage.getItem('token')},
        url: baseUrl+'/@{SIMPLEENTITYNAME}/list/auth',
        page: true,
        limit: 15,
        limits: [15, 30, 50, 100, 200, 500],
        toolbar: '#toolbar',
        cellMinWidth: 50,
        height: 'full-120',
        cols: [[
            {type: 'checkbox'}
@{JSTABLECONTENT}
            ,{fixed: 'right', title:'操作', align: 'center', toolbar: '#operate', width:120}
        ]],
        request: {
            pageName: 'curr',
            pageSize: 'limit'
        },
        parseData: function (res) {
            return {
                'code': res.code,
                'msg': res.msg,
                'count': res.data.total,
                'data': res.data.records
            }
        },
        response: {
            statusCode: 200
        },
        done: function(res, curr, count) {
            if (res.code === 403) {
                top.location.href = baseUrl+"/";
            }
            pageCurr=curr;
            limit();
        }
    });
    // 监听排序事件
    table.on('sort(@{SIMPLEENTITYNAME})', function (obj) {
        var searchData = {};
        $.each($('#search-box [name]').serializeArray(), function() {
            searchData[this.name] = this.value;
        });
        searchData['orderByField'] = obj.field;
        searchData['orderByType'] = obj.type;
        tableIns.reload({
            where: searchData,
            page: {curr: 1}
        });
    });
    // 监听头工具栏事件
    table.on('toolbar(@{SIMPLEENTITYNAME})', function (obj) {
        var checkStatus = table.checkStatus(obj.config.id).data;
        switch(obj.event) {
            case 'addData':
                showEditModel();
                break;
            case 'deleteData':
               if (checkStatus.length === 0) {
                   layer.msg('请选择要删除的数据', {icon: 2});
                   return;
               }
               del(checkStatus.map(function (d) {
                   return d.@{PRIMARYKEYCOLUMN0};
               }));
               break;
            case 'exportData':
                admin.confirm('确定导出Excel吗', {shadeClose: true}, function(){
                    var titles=[];
                    var fields=[];
                    obj.config.cols[0].map(function (col) {
                        if (col.type === 'normal' && col.hide === false && col.toolbar == null) {
                            titles.push(col.title);
                            fields.push(col.field);
                        }
                    });
                    var exportData = {};
                    $.each($('#search-box [name]').serializeArray(), function() {
                        exportData[this.name] = this.value;
                    });
                    var param = {
                        '@{SIMPLEENTITYNAME}': exportData,
                        'fields': fields
                    };
                    $.ajax({
                        url: baseUrl+"/@{SIMPLEENTITYNAME}/export/auth",
                        headers: {'token': localStorage.getItem('token')},
                        data: JSON.stringify(param),
                        dataType:'json',
                        contentType:'application/json;charset=UTF-8',
                        method: 'POST',
                        success: function (res) {
                            layer.closeAll();
                            if (res.code === 200) {
                                table.exportFile(titles,res.data,'xls');
                            } else if (res.code === 403) {
                                top.location.href = baseUrl+"/";
                            } else {
                                layer.msg(res.msg, {icon: 2})
                            }
                        }
                    });
                });
                break;
        }
    });
    // 监听行工具事件
    table.on('tool(@{SIMPLEENTITYNAME})', function(obj){
        var data = obj.data;
        switch (obj.event) {
            case 'edit':
                showEditModel(data);
                break;
            case "del":
                del([data.@{PRIMARYKEYCOLUMN0}]);
                break;
        }
    });
    /* 弹窗 - 新增、修改 */
    function showEditModel(mData) {
        admin.open({
            type: 1,
            area: '600px',
            title: (mData ? '修改' : '添加') + '',
            content: $('#editDialog').html(),
            success: function (layero, dIndex) {
                form.val('detail', mData);
                layDateRender(mData);
                form.on('submit(editSubmit)', function (data) {
                    var loadIndex = layer.load(2);
                    $.ajax({
                        url: baseUrl+"/@{SIMPLEENTITYNAME}/"+(mData?'update':'add')+"/auth",
                        headers: {'token': localStorage.getItem('token')},
                        data: data.field,
                        method: 'POST',
                        success: function (res) {
                            layer.close(loadIndex);
                            if (res.code === 200){
                                layer.close(dIndex);
                                layer.msg(res.msg, {icon: 1});
                                tableReload();
                            } else if (res.code === 403){
                                top.location.href = baseUrl+"/";
                            }else {
                                layer.msg(res.msg, {icon: 2});
                            }
                        }
                    })
                    return false;
                });
                $(layero).children('.layui-layer-content').css('overflow', 'visible');
                layui.form.render('select');
            }
        });
    }
    /* 删除 */
    function del(ids) {
        layer.confirm('确定要删除选中数据吗?', {
            skin: 'layui-layer-admin',
            shade: .1
        }, function (i) {
            layer.close(i);
            var loadIndex = layer.load(2);
            $.ajax({
                url: baseUrl+"/@{SIMPLEENTITYNAME}/delete/auth",
                headers: {'token': localStorage.getItem('token')},
                data: {ids: ids},
                method: 'POST',
                success: function (res) {
                    layer.close(loadIndex);
                    if (res.code === 200){
                        layer.msg(res.msg, {icon: 1});
                        tableReload();
                    } else if (res.code === 403){
                        top.location.href = baseUrl+"/";
                    } else {
                        layer.msg(res.msg, {icon: 2});
                    }
                }
            })
        });
    }
    // 搜索
    form.on('submit(search)', function (data) {
        pageCurr = 1;
        tableReload(false);
    });
    // 重置
    form.on('submit(reset)', function (data) {
        pageCurr = 1;
        clearFormVal($('#search-box'));
        tableReload(false);
    });
    // 时间选择器
    function layDateRender(data) {
        setTimeout(function () {
            layDate.render({
                elem: '.layui-laydate-range'
                ,type: 'datetime'
                ,range: true
            });
@{JSDATECONTENT}
        }, 300);
    }
    layDateRender();
});
// 关闭动作
$(document).on('click','#data-detail-close', function () {
    parent.layer.closeAll();
});
function tableReload(child) {
    var searchData = {};
    $.each($('#search-box [name]').serializeArray(), function() {
        searchData[this.name] = this.value;
    });
    tableIns.reload({
        where: searchData,
        page: {curr: pageCurr}
     });
}
src/main/resources/templates/Mapper.txt
New file
@@ -0,0 +1,12 @@
package @{COMPANYNAME}.mapper;
import @{COMPANYNAME}.entity.@{ENTITYNAME};
import com.baomidou.mybatisplus.mapper.BaseMapper;
import org.apache.ibatis.annotations.Mapper;
import org.springframework.stereotype.Repository;
@Mapper
@Repository
public interface @{ENTITYNAME}Mapper extends BaseMapper<@{ENTITYNAME}> {
}
src/main/resources/templates/Service.txt
New file
@@ -0,0 +1,8 @@
package @{COMPANYNAME}.service;
import @{COMPANYNAME}.entity.@{ENTITYNAME};
import com.baomidou.mybatisplus.service.IService;
public interface @{ENTITYNAME}Service extends IService<@{ENTITYNAME}> {
}
src/main/resources/templates/ServiceImpl.txt
New file
@@ -0,0 +1,12 @@
package @{COMPANYNAME}.service.impl;
import @{COMPANYNAME}.mapper.@{ENTITYNAME}Mapper;
import @{COMPANYNAME}.entity.@{ENTITYNAME};
import @{COMPANYNAME}.service.@{ENTITYNAME}Service;
import com.baomidou.mybatisplus.service.impl.ServiceImpl;
import org.springframework.stereotype.Service;
@Service("@{SIMPLEENTITYNAME}Service")
public class @{ENTITYNAME}ServiceImpl extends ServiceImpl<@{ENTITYNAME}Mapper, @{ENTITYNAME}> implements @{ENTITYNAME}Service {
}
src/main/resources/templates/Sql.txt
New file
@@ -0,0 +1,18 @@
-- save @{SIMPLEENTITYNAME} record
-- mysql
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( '@{SIMPLEENTITYNAME}/@{SIMPLEENTITYNAME}.html', '@{SIMPLEENTITYNAME}管理', null , '2', null , '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( '@{SIMPLEENTITYNAME}#view', '查询', '', '3', '0', '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( '@{SIMPLEENTITYNAME}#btn-add', '新增', '', '3', '1', '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( '@{SIMPLEENTITYNAME}#btn-edit', '编辑', '', '3', '2', '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( '@{SIMPLEENTITYNAME}#btn-delete', '删除', '', '3', '3', '1');
insert into `sys_resource` ( `code`, `name`, `resource_id`, `level`, `sort`, `status`) values ( '@{SIMPLEENTITYNAME}#btn-export', '导出', '', '3', '4', '1');
-- sqlserver
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'@{SIMPLEENTITYNAME}/@{SIMPLEENTITYNAME}.html', N'@{SIMPLEENTITYNAME}管理', null, '2', null, '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'@{SIMPLEENTITYNAME}#view', N'查询', '', '3', '0', '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'@{SIMPLEENTITYNAME}#btn-add', N'新增', '', '3', '1', '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'@{SIMPLEENTITYNAME}#btn-edit', N'编辑', '', '3', '2', '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'@{SIMPLEENTITYNAME}#btn-delete', N'删除', '', '3', '3', '1');
insert [dbo].[sys_resource] ( [code], [name], [resource_id], [level], [sort], [status]) values ( N'@{SIMPLEENTITYNAME}#btn-export', N'导出', '', '3', '4', '1');
src/main/resources/templates/Xml.txt
New file
@@ -0,0 +1,10 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="@{COMPANYNAME}.mapper.@{ENTITYNAME}Mapper">
    <!-- 通用查询映射结果 -->
    <resultMap id="BaseResultMap" type="@{COMPANYNAME}.entity.@{ENTITYNAME}">
@{XMLCONTENT}
    </resultMap>
</mapper>
version/lib/cool-framework-install.txt
File was deleted