admin
2024-07-25 47e3087067abd35e6337c011f96d2338c0bb1aae
优化自动化代码
28个文件已修改
1个文件已添加
1233 ■■■■■ 已修改文件
src/main/java/org/yeshi/utils/QRCodeUtil.java 564 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/annotation/MapUtil.java 82 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/GeneraterManager.java 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/GeneraterManagerV2.java 25 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/TestEntity3.java 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/entity/admin/AdminGeneraterInfo.java 16 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/mybatis/ColumnParseUtil.java 21 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/mybatis/MyBatisMapperUtil.java 99 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/util/NameUtil.java 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/vo/admin/controller/AdminControllerInfoVO.java 19 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/vo/admin/page/ListInfoVO.java 5 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/vo/service/ServiceInfoVO.java 6 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/vo/xmlconfig/XmlConfigParseUtil.java 3 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/vo/xmlconfig/admin/AdminControllerData.java 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/generater/vo/xmlconfig/service/ServiceData.java 10 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/mq/TDMQUtil.java 82 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/tencentcloud/COSManager.java 11 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/wx/WXAppLoginUtil.java 19 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/generater/admin/add.ftl 43 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/generater/admin/adminController.template 39 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/generater/admin/adminVO.template 14 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/generater/admin/form/checkBox.ftl 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/generater/admin/form/img.ftl 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/generater/admin/list.ftl 18 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/generater/admin/update.ftl 38 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/schemas/generator.dtd 3 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/test.xml 88 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/test/java/com/generater/GeneratorTest.java 6 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/test/java/com/generater/TestEntity2.java 1 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/org/yeshi/utils/QRCodeUtil.java
@@ -26,327 +26,309 @@
import com.google.zxing.Result;
import com.google.zxing.WriterException;
import com.google.zxing.client.j2se.BufferedImageLuminanceSource;
import com.google.zxing.client.j2se.MatrixToImageWriter;
import com.google.zxing.common.BitMatrix;
import com.google.zxing.common.HybridBinarizer;
import com.google.zxing.qrcode.decoder.ErrorCorrectionLevel;
/**
 * 二维码生成
 *
 * @author Administrator
 *
 * @author Administrator
 */
public class QRCodeUtil {
    private static final String CHARSET = "UTF-8";
    private static final String FORMAT_NAME = "JPG";
    // 二维码尺寸
    int QRCODE_SIZE = 200;
    // LOGO宽度
    int WIDTH = 60;
    // LOGO高度
    int HEIGHT = 60;
    private static final String CHARSET = "UTF-8";
    private static final String FORMAT_NAME = "JPG";
    static QRCodeUtil qrCodeUtil;
    // 二维码尺寸
    int QRCODE_SIZE = 200;
    // LOGO宽度
    int WIDTH = 60;
    // LOGO高度
    int HEIGHT = 60;
    public static QRCodeUtil getInstance(int size) {
        if (qrCodeUtil == null) {
            qrCodeUtil = new QRCodeUtil();
        }
        qrCodeUtil.QRCODE_SIZE = size;
        return qrCodeUtil;
    }
    static QRCodeUtil qrCodeUtil;
    public static QRCodeUtil getInstance(int size, int imgSize) {
        if (qrCodeUtil == null) {
            qrCodeUtil = new QRCodeUtil();
        }
        qrCodeUtil.QRCODE_SIZE = size;
        qrCodeUtil.HEIGHT = imgSize;
        qrCodeUtil.WIDTH = imgSize;
        return qrCodeUtil;
    }
    public static QRCodeUtil getInstance(int size) {
        if (qrCodeUtil == null) {
            qrCodeUtil = new QRCodeUtil();
        }
        qrCodeUtil.QRCODE_SIZE = size;
        return qrCodeUtil;
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:31:29
     *
     * @param content
     *            二维码内容
     * @param logoImgPath
     *            Logo
     * @param needCompress
     *            是否压缩Logo
     * @return 返回二维码图片
     * @throws WriterException
     * @throws IOException
     *             BufferedImage TODO 创建二维码图片
     */
    private BufferedImage createImage(String content, InputStream logoImg, boolean needCompress)
            throws WriterException, IOException {
        Hashtable<EncodeHintType, Object> hints = new Hashtable<EncodeHintType, Object>();
        hints.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H);
        hints.put(EncodeHintType.CHARACTER_SET, CHARSET);
        hints.put(EncodeHintType.MARGIN, 1);
        BitMatrix bitMatrix = new MultiFormatWriter().encode(content, BarcodeFormat.QR_CODE, QRCODE_SIZE, QRCODE_SIZE,
                hints);
        int width = bitMatrix.getWidth();
        int height = bitMatrix.getHeight();
        BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
        for (int x = 0; x < width; x++) {
            for (int y = 0; y < height; y++) {
                image.setRGB(x, y, bitMatrix.get(x, y) ? 0xFF000000 : 0xFFFFFFFF);
            }
        }
        if (logoImg == null) {
            return image;
        }
        // 插入图片
        insertImage(image, logoImg, needCompress);
        return image;
    }
    public static QRCodeUtil getInstance(int size, int imgSize) {
        if (qrCodeUtil == null) {
            qrCodeUtil = new QRCodeUtil();
        }
        qrCodeUtil.QRCODE_SIZE = size;
        qrCodeUtil.HEIGHT = imgSize;
        qrCodeUtil.WIDTH = imgSize;
        return qrCodeUtil;
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:31:29
     *
     * @param content
     *            二维码内容
     * @param logoImgPath
     *            Logo
     * @param needCompress
     *            是否压缩Logo
     * @return 返回二维码图片
     * @throws WriterException
     * @throws IOException
     *             BufferedImage TODO 创建二维码图片
     */
    private BufferedImage createImageDeleteWhite(String content, InputStream logoImg, boolean needCompress)
            throws WriterException, IOException {
        Hashtable<EncodeHintType, Object> hints = new Hashtable<EncodeHintType, Object>();
        hints.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H);
        hints.put(EncodeHintType.CHARACTER_SET, CHARSET);
        hints.put(EncodeHintType.MARGIN, 1);
        BitMatrix bitMatrix = new MultiFormatWriter().encode(content, BarcodeFormat.QR_CODE, QRCODE_SIZE, QRCODE_SIZE,
                hints);
        //调用去除白边方法
    /**
     * user: Rex date: 2016年12月29日 上午12:31:29
     *
     * @param content      二维码内容
     * @param logoImgPath  Logo
     * @param needCompress 是否压缩Logo
     * @return 返回二维码图片
     * @throws WriterException
     * @throws IOException
     */
    private BufferedImage createImage(String content, InputStream logoImg, boolean needCompress)
            throws WriterException, IOException {
        return this.createImage(content, logoImg, 0xFF000000, 0xFFFFFFFF, needCompress);
    }
    public BufferedImage createImage(String content, InputStream logoImg, int color, int bgColor, boolean needCompress)
            throws WriterException, IOException {
        Hashtable<EncodeHintType, Object> hints = new Hashtable<EncodeHintType, Object>();
        hints.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H);
        hints.put(EncodeHintType.CHARACTER_SET, CHARSET);
        hints.put(EncodeHintType.MARGIN, 1);
        BitMatrix bitMatrix = new MultiFormatWriter().encode(content, BarcodeFormat.QR_CODE, QRCODE_SIZE, QRCODE_SIZE,
                hints);
        int width = bitMatrix.getWidth();
        int height = bitMatrix.getHeight();
        BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
        for (int x = 0; x < width; x++) {
            for (int y = 0; y < height; y++) {
                image.setRGB(x, y, bitMatrix.get(x, y) ? color : bgColor);
            }
        }
        if (logoImg == null) {
            return image;
        }
        if (logoImg != null) {
            // 插入图片
            insertImage(image, logoImg, needCompress);
        }
        return image;
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:31:29
     *
     * @param content      二维码内容
     * @param logoImgPath  Logo
     * @param needCompress 是否压缩Logo
     * @return 返回二维码图片
     * @throws WriterException
     * @throws IOException
     */
    private BufferedImage createImageDeleteWhite(String content, InputStream logoImg, boolean needCompress)
            throws WriterException, IOException {
        return createImageDeleteWhite(content, logoImg, 0xFF000000, 0xFFFFFFFF, needCompress);
    }
    public BufferedImage createImageDeleteWhite(String content, InputStream logoImg, int color, int bgColor, boolean needCompress)
            throws WriterException, IOException {
        Hashtable<EncodeHintType, Object> hints = new Hashtable<EncodeHintType, Object>();
        hints.put(EncodeHintType.ERROR_CORRECTION, ErrorCorrectionLevel.H);
        hints.put(EncodeHintType.CHARACTER_SET, CHARSET);
        hints.put(EncodeHintType.MARGIN, 1);
        BitMatrix bitMatrix = new MultiFormatWriter().encode(content, BarcodeFormat.QR_CODE, QRCODE_SIZE, QRCODE_SIZE,
                hints);
        //调用去除白边方法
        bitMatrix = deleteWhite(bitMatrix);
        int width = bitMatrix.getWidth();
        int height = bitMatrix.getHeight();
        BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
        for (int x = 0; x < width; x++) {
            for (int y = 0; y < height; y++) {
                image.setRGB(x, y, bitMatrix.get(x, y) ? 0xFF000000 : 0xFFFFFFFF);
            }
        }
        if (logoImg == null) {
            return image;
        }
        // 插入图片
        insertImage(image, logoImg, needCompress);
        return image;
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:30:09
     *
     * @param source
     *            二维码图片
     * @param logoImgPath
     *            Logo
     * @param needCompress
     *            是否压缩Logo
     * @throws IOException
     *             void TODO 添加Logo
     */
    private void insertImage(BufferedImage source, InputStream logoImg, boolean needCompress) throws IOException {
        Image src = ImageIO.read(logoImg);
        int width = src.getWidth(null);
        int height = src.getHeight(null);
        if (needCompress) { // 压缩LOGO
            if (width > WIDTH) {
                width = WIDTH;
            }
            if (height > HEIGHT) {
                height = HEIGHT;
            }
        int width = bitMatrix.getWidth();
        int height = bitMatrix.getHeight();
        BufferedImage image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
        for (int x = 0; x < width; x++) {
            for (int y = 0; y < height; y++) {
                image.setRGB(x, y, bitMatrix.get(x, y) ? color : bgColor);
            }
        }
        if (logoImg == null) {
            return image;
        }
            Image image = src.getScaledInstance(width, height, Image.SCALE_SMOOTH);
            BufferedImage tag = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
            Graphics g = tag.getGraphics();
            g.drawImage(image, 0, 0, null); // 绘制缩小后的图
            g.dispose();
            src = image;
        }
        // 插入图片
        if (logoImg != null) {
            insertImage(image, logoImg, needCompress);
        }
        return image;
    }
        // 插入LOGO
        Graphics2D graph = source.createGraphics();
        int x = (QRCODE_SIZE - width) / 2;
        int y = (QRCODE_SIZE - height) / 2;
        graph.drawImage(src, x, y, width, height, null);
        Shape shape = new RoundRectangle2D.Float(x, y, width, width, 6, 6);
        graph.setStroke(new BasicStroke(3f));
        graph.draw(shape);
        graph.dispose();
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:30:09
     *
     * @param source       二维码图片
     * @param logoImgPath  Logo
     * @param needCompress 是否压缩Logo
     * @throws IOException void TODO 添加Logo
     */
    private void insertImage(BufferedImage source, InputStream logoImg, boolean needCompress) throws IOException {
        Image src = ImageIO.read(logoImg);
        int width = src.getWidth(null);
        int height = src.getHeight(null);
        if (needCompress) { // 压缩LOGO
            if (width > WIDTH) {
                width = WIDTH;
            }
    /**
     * user: Rex date: 2016年12月29日 上午12:32:32
     *
     * @param content
     *            二维码内容
     * @param logoImgPath
     *            Logo
     * @param destPath
     *            二维码输出路径
     * @param needCompress
     *            是否压缩Logo
     * @throws Exception
     *             void TODO 生成带Logo的二维码
     */
    public void encode(String content, InputStream logoImg, String destPath, boolean needCompress) throws Exception {
        BufferedImage image = createImage(content, logoImg, needCompress);
        ImageIO.write(image, FORMAT_NAME, new File(destPath));
    }
            if (height > HEIGHT) {
                height = HEIGHT;
            }
    /**
     * user: Rex date: 2016年12月29日 上午12:35:44
     *
     * @param content
     *            二维码内容
     * @param destPath
     *            二维码输出路径
     * @throws Exception
     *             void TODO 生成不带Logo的二维码
     */
    public void encode(String content, String destPath) throws Exception {
        encode(content, null, destPath, false);
    }
            Image image = src.getScaledInstance(width, height, Image.SCALE_SMOOTH);
            BufferedImage tag = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
            Graphics g = tag.getGraphics();
            g.drawImage(image, 0, 0, null); // 绘制缩小后的图
            g.dispose();
            src = image;
        }
    public InputStream encode(String content) throws Exception {
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        encode(content, null, out, false);
        return new ByteArrayInputStream(out.toByteArray());
    }
        // 插入LOGO
        Graphics2D graph = source.createGraphics();
        int x = (QRCODE_SIZE - width) / 2;
        int y = (QRCODE_SIZE - height) / 2;
        graph.drawImage(src, x, y, width, height, null);
        Shape shape = new RoundRectangle2D.Float(x, y, width, width, 6, 6);
        graph.setStroke(new BasicStroke(3f));
        graph.draw(shape);
        graph.dispose();
    }
    public InputStream encodeDeleteWhite(String content) throws Exception {
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        encodeDeleteWhite(content, null, out, false);
        return new ByteArrayInputStream(out.toByteArray());
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:36:58
     *
     * @param content
     *            二维码内容
     * @param logoImgPath
     *            Logo
     * @param output
     *            输出流
     * @param needCompress
     *            是否压缩Logo
     * @throws Exception
     *             void TODO 生成带Logo的二维码,并输出到指定的输出流
     */
    public void encode(String content, InputStream logoImg, OutputStream output, boolean needCompress)
            throws Exception {
        BufferedImage image = createImage(content, logoImg, needCompress);
        ImageIO.write(image, FORMAT_NAME, output);
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:32:32
     *
     * @param content      二维码内容
     * @param logoImgPath  Logo
     * @param destPath     二维码输出路径
     * @param needCompress 是否压缩Logo
     * @throws Exception void TODO 生成带Logo的二维码
     */
    public void encode(String content, InputStream logoImg, String destPath, boolean needCompress) throws Exception {
        BufferedImage image = createImage(content, logoImg, needCompress);
        ImageIO.write(image, FORMAT_NAME, new File(destPath));
    }
    /**
     *
     * @param content
     * @param logoImg
     * @param output
     *            二进制输出流
     * @param needCompress
     * @throws Exception
     */
    public void encode(String content, InputStream logoImg, ByteArrayOutputStream output, boolean needCompress)
            throws Exception {
        BufferedImage image = createImage(content, logoImg, needCompress);
        ImageIO.write(image, FORMAT_NAME, output);
    }
    /**
     *
     * @param content
     * @param logoImg
     * @param output
     *            二进制输出流
     * @param needCompress
     * @throws Exception
     */
    public void encodeDeleteWhite(String content, InputStream logoImg, ByteArrayOutputStream output, boolean needCompress)
            throws Exception {
        BufferedImage image = createImageDeleteWhite(content, logoImg, needCompress);
        ImageIO.write(image, FORMAT_NAME, output);
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:35:44
     *
     * @param content  二维码内容
     * @param destPath 二维码输出路径
     * @throws Exception void TODO 生成不带Logo的二维码
     */
    public void encode(String content, String destPath) throws Exception {
        encode(content, null, destPath, false);
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:38:02
     *
     * @param content
     *            二维码内容
     * @param output
     *            输出流
     * @throws Exception
     *             void TODO 生成不带Logo的二维码,并输出到指定的输出流
     */
    public void encode(String content, OutputStream output) throws Exception {
        encode(content, null, output, false);
    }
    public InputStream encode(String content) throws Exception {
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        encode(content, null, out, false);
        return new ByteArrayInputStream(out.toByteArray());
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:39:10
     *
     * @param file
     *            二维码
     * @return 返回解析得到的二维码内容
     * @throws Exception
     *             String TODO 二维码解析
     */
    public String decode(File file) throws Exception {
        BufferedImage image;
        image = ImageIO.read(file);
        if (image == null) {
            return null;
        }
        BufferedImageLuminanceSource source = new BufferedImageLuminanceSource(image);
        BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));
        Result result;
        Hashtable<DecodeHintType, Object> hints = new Hashtable<DecodeHintType, Object>();
        hints.put(DecodeHintType.CHARACTER_SET, CHARSET);
        result = new MultiFormatReader().decode(bitmap, hints);
        String resultStr = result.getText();
        return resultStr;
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:39:48
     *
     * @param path
     *            二维码存储位置
     * @return 返回解析得到的二维码内容
     * @throws Exception
     *             String TODO 二维码解析
     */
    public String decode(String path) throws Exception {
        return decode(new File(path));
    }
    public InputStream encodeDeleteWhite(String content) throws Exception {
        ByteArrayOutputStream out = new ByteArrayOutputStream();
        encodeDeleteWhite(content, null, out, false);
        return new ByteArrayInputStream(out.toByteArray());
    }
     private static BitMatrix deleteWhite(BitMatrix matrix) {
    /**
     * user: Rex date: 2016年12月29日 上午12:36:58
     *
     * @param content      二维码内容
     * @param logoImgPath  Logo
     * @param output       输出流
     * @param needCompress 是否压缩Logo
     * @throws Exception void TODO 生成带Logo的二维码,并输出到指定的输出流
     */
    public void encode(String content, InputStream logoImg, OutputStream output, boolean needCompress)
            throws Exception {
        BufferedImage image = createImage(content, logoImg, needCompress);
        ImageIO.write(image, FORMAT_NAME, output);
    }
    /**
     * @param content
     * @param logoImg
     * @param output       二进制输出流
     * @param needCompress
     * @throws Exception
     */
    public void encode(String content, InputStream logoImg, ByteArrayOutputStream output, boolean needCompress)
            throws Exception {
        BufferedImage image = createImage(content, logoImg, needCompress);
        ImageIO.write(image, FORMAT_NAME, output);
    }
    /**
     * @param content
     * @param logoImg
     * @param output       二进制输出流
     * @param needCompress
     * @throws Exception
     */
    public void encodeDeleteWhite(String content, InputStream logoImg, ByteArrayOutputStream output, boolean needCompress)
            throws Exception {
        BufferedImage image = createImageDeleteWhite(content, logoImg, needCompress);
        ImageIO.write(image, FORMAT_NAME, output);
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:38:02
     *
     * @param content 二维码内容
     * @param output  输出流
     * @throws Exception void TODO 生成不带Logo的二维码,并输出到指定的输出流
     */
    public void encode(String content, OutputStream output) throws Exception {
        encode(content, null, output, false);
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:39:10
     *
     * @param file 二维码
     * @return 返回解析得到的二维码内容
     * @throws Exception String TODO 二维码解析
     */
    public String decode(File file) throws Exception {
        BufferedImage image;
        image = ImageIO.read(file);
        if (image == null) {
            return null;
        }
        BufferedImageLuminanceSource source = new BufferedImageLuminanceSource(image);
        BinaryBitmap bitmap = new BinaryBitmap(new HybridBinarizer(source));
        Result result;
        Hashtable<DecodeHintType, Object> hints = new Hashtable<DecodeHintType, Object>();
        hints.put(DecodeHintType.CHARACTER_SET, CHARSET);
        result = new MultiFormatReader().decode(bitmap, hints);
        String resultStr = result.getText();
        return resultStr;
    }
    /**
     * user: Rex date: 2016年12月29日 上午12:39:48
     *
     * @param path 二维码存储位置
     * @return 返回解析得到的二维码内容
     * @throws Exception String TODO 二维码解析
     */
    public String decode(String path) throws Exception {
        return decode(new File(path));
    }
    private static BitMatrix deleteWhite(BitMatrix matrix) {
        int[] rec = matrix.getEnclosingRectangle();
        int resWidth = rec[2] + 1;
        int resHeight = rec[3] + 1;
        BitMatrix resMatrix = new BitMatrix(resWidth, resHeight);
        resMatrix.clear();
        for (int i = 0; i < resWidth; i++) {
src/main/java/org/yeshi/utils/annotation/MapUtil.java
@@ -1,36 +1,66 @@
package org.yeshi.utils.annotation;
import com.google.gson.Gson;
import net.sf.json.JSONObject;
import org.yeshi.utils.StringUtil;
import java.io.UnsupportedEncodingException;
import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.util.Properties;
public class MapUtil {
    public static Object parseMap(Class<?> clazz, Properties ps) {
        System.out.println(clazz.getName());
        Object target = null;
        try {
            Class clz = Class.forName(clazz.getName());
            target = clz.newInstance();
        } catch (Exception e) {
            e.printStackTrace();
        }
        Field[] fields = clazz.getDeclaredFields();
        for (Field fd : fields) {
            fd.setAccessible(true);
            Annotation[] as = fd.getAnnotations();
            for (Annotation a : as) {
                if (a instanceof Map) {
                    Map c = (Map) a;
                    try {
                        fd.set(target, new String(ps.getProperty(c.value()).getBytes("ISO-8859-1"), "UTF-8"));
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            }
        }
        return target;
    }
    public static Object parseMap(Class<?> clazz, Properties ps) {
        System.out.println(clazz.getName());
        Object target = null;
        try {
            Class clz = Class.forName(clazz.getName());
            target = clz.newInstance();
        } catch (Exception e) {
            e.printStackTrace();
        }
        Field[] fields = clazz.getDeclaredFields();
        for (Field fd : fields) {
            fd.setAccessible(true);
            Annotation[] as = fd.getAnnotations();
            for (Annotation a : as) {
                if (a instanceof Map) {
                    Map c = (Map) a;
                    try {
                        fd.set(target, new String(ps.getProperty(c.value()).getBytes("ISO-8859-1"), "UTF-8"));
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }
            }
        }
        return target;
    }
    public static Object parseMapByJson(Class<?> clazz, Properties ps, String encoding) {
        if (StringUtil.isNullOrEmpty(encoding)) {
            encoding = "ISO-8859-1";
        }
        JSONObject json = new JSONObject();
        Field[] fields = clazz.getDeclaredFields();
        for (Field fd : fields) {
            fd.setAccessible(true);
            Annotation[] as = fd.getAnnotations();
            for (Annotation a : as) {
                if (a instanceof Map) {
                    Map c = (Map) a;
                    try {
                        json.put(fd.getName(), new String(ps.getProperty(c.value()).getBytes(encoding), "UTF-8"));
                    } catch (UnsupportedEncodingException e) {
                        e.printStackTrace();
                    }
                }
            }
        }
        return new Gson().fromJson(json.toString(), clazz);
    }
}
src/main/java/org/yeshi/utils/generater/GeneraterManager.java
@@ -317,7 +317,7 @@
     * @date 18:25 2021/10/13
     * @param: entityName
     **/
    private static String getHtmlNameFromEntityName(String entityName) {
    public static String getHtmlNameFromEntityName(String entityName) {
        StringBuffer sb = new StringBuffer();
        StringBuffer buffer = null;
        for (int i = 0; i < entityName.length(); i++) {
src/main/java/org/yeshi/utils/generater/GeneraterManagerV2.java
@@ -101,21 +101,24 @@
    }
    public void createAdminVO() throws Exception {
        if (StringUtil.isNullOrEmpty(config.getService().getAdminVOPackage())) {
            throw new Exception("尚未配置AdminVO");
    public AdminVOVO createAdminVO() throws Exception {
        if (StringUtil.isNullOrEmpty(config.getAdmin().getController().getAdminVOPackage())) {
            return null;
        }
        String name = NameUtil.getDefaultExceptionName(config.getEntity());
        String path = getDirPath(config.getService().getAdminVOPackage());
        String name = NameUtil.getDefaultAdminVOName(config.getEntity());
        String path = getDirPath(config.getAdmin().getController().getAdminVOPackage());
        try {
            AdminVOVO vo = new AdminVOVO.Builder().setEntity(config.getEntity()).setPackageName(config.getService().getAdminVOPackage()).build();
            AdminVOVO vo = new AdminVOVO.Builder().setEntity(config.getEntity()).setPackageName(config.getAdmin().getController().getAdminVOPackage()).build();
            String result = GeneraterUtil.createAdminVO(vo);
            //保存
            saveFile(result, new File(path, name + ".java").getAbsolutePath());
            return vo;
        } catch (Exception e) {
            e.printStackTrace();
        }
        return null;
    }
@@ -247,9 +250,6 @@
            }
        }
        if (config.getService().getAdminVOPackage() != null) {
            createAdminVO();
        }
        QueryVO queryVO = createQuery(config.getService().getQueryPackage());
@@ -315,13 +315,18 @@
            query = new ClassInfo(queryName, config.getService().getQueryPackage() + "." + queryName);
        }
        AdminVOVO adminVOVO = null;
        if (config.getAdmin().getController().getAdminVOPackage() != null) {
            adminVOVO = createAdminVO();
        }
        String path = getDirPath(config.getAdmin().getController().getPkg());
        AdminGeneraterInfo generaterInfo = new AdminGeneraterInfo.Builder().setEntityClass(config.getEntity()).setAdminData(config.getAdmin()).build();
        AdminControllerInfoVO vo = new AdminControllerInfoVO.Builder().setAdminInfo(generaterInfo).setPackageName(generaterInfo.getControllerData().getPkg()).setQueryVO(query).setService(service).build();
        AdminControllerInfoVO vo = new AdminControllerInfoVO.Builder().setAdminVO(adminVOVO == null ? null : new ClassInfo(adminVOVO.getName(), adminVOVO.getPackageName() + "." + adminVOVO.getName())).setAdminInfo(generaterInfo).setPackageName(generaterInfo.getControllerData().getPkg()).setQueryVO(query).setService(service).build();
        String controllerName = vo.getControllerName();
        //生成controller
        String result = GeneraterUtil.createAdminController(vo);
src/main/java/org/yeshi/utils/generater/TestEntity3.java
@@ -15,6 +15,7 @@
@Table("table_test")
public class TestEntity3 {
    @Id
    @Column(name = "id")
    private String id;
    @Column(name = "nick_name")
src/main/java/org/yeshi/utils/generater/entity/admin/AdminGeneraterInfo.java
@@ -315,14 +315,16 @@
                FormComponentImg formComponentImg = (FormComponentImg) component;
                params.put("width", formComponentImg.getWidth() == null ? -1 : formComponentImg.getWidth());
                params.put("height", formComponentImg.getHeight() == null ? -1 : formComponentImg.getHeight());
                params.put("uploadApi", formComponentImg.getApi().getPath());
                if (formComponentImg.getApi().getParams() != null) {
                    List<KeyValue> list = new ArrayList<>();
                    for (Iterator<String> its = formComponentImg.getApi().getParams().keySet().iterator(); its.hasNext(); ) {
                        String key = its.next();
                        list.add(new KeyValue(key, formComponentImg.getApi().getParams().get(key) + ""));
                if( formComponentImg.getApi()!=null) {
                    params.put("uploadApi", formComponentImg.getApi().getPath());
                    if (formComponentImg.getApi().getParams() != null) {
                        List<KeyValue> list = new ArrayList<>();
                        for (Iterator<String> its = formComponentImg.getApi().getParams().keySet().iterator(); its.hasNext(); ) {
                            String key = its.next();
                            list.add(new KeyValue(key, formComponentImg.getApi().getParams().get(key) + ""));
                        }
                        params.put("uploadApiParams", list);
                    }
                    params.put("uploadApiParams", list);
                }
            } else if (component instanceof FormComponentSwitch) {
                rowData.setType(Switch.class.getSimpleName());
src/main/java/org/yeshi/utils/generater/mybatis/ColumnParseUtil.java
@@ -87,4 +87,25 @@
        }
    }
    public static String getMysqlType(String type) {
        if (type.endsWith("java.lang.Long")) {
            return "bigint";
        } else if (type.endsWith("java.lang.Integer")) {
            return "int";
        } else if (type.endsWith("java.lang.String")) {
            return "varchar";
        } else if (type.endsWith("java.lang.Boolean")) {
            return "tinyint";
        } else if (type.endsWith("java.math.BigDecimal")) {
            return "decimal";
        } else if (type.endsWith("java.util.Date")) {
            return "datetime";
        } else if (type.endsWith("java.lang.Double")) {
            return "double";
        } else {
            return "varchar";
        }
    }
}
src/main/java/org/yeshi/utils/generater/mybatis/MyBatisMapperUtil.java
@@ -14,6 +14,7 @@
import org.dom4j.DocumentHelper;
import org.dom4j.io.OutputFormat;
import org.dom4j.io.XMLWriter;
import org.springframework.data.annotation.Id;
import org.yeshi.utils.generater.entity.MybatisColumnData;
public class MyBatisMapperUtil {
@@ -409,6 +410,101 @@
        }
    }
    public static String createSQL(Class<?> clz){
        List<AttributeColumnMap> keysList = new ArrayList<>();
        Field[] fields = clz.getDeclaredFields();
        for (Field fd : fields) {
            Annotation[] as = fd.getAnnotations();
            AttributeColumnMap columnMap=null;
            for (Annotation a : as) {
                if (a instanceof Column) {
                    Column c = (Column) a;
                    columnMap = new AttributeColumnMap(fd.getName(), c.name(), fd.getType().getName());
                    columnMap.length = c.length();
                    break;
                }
            }
            for (Annotation a : as) {
                if(a instanceof Id){
                    // 主键
                    columnMap.mainKey = true;
                    break;
                }
            }
            if(columnMap!=null){
                keysList.add(columnMap);
            }
        }
        String tableName = "";
        Annotation[] as = clz.getAnnotations();
        for (Annotation a : as) {
            if (a instanceof Table) {
                Table t = (Table) a;
                tableName = t.value();
            }
        }
        StringBuffer buffer=new StringBuffer();
        buffer.append("create table `").append(tableName).append("`(\n");
        for(AttributeColumnMap columnMap:keysList){
            String mysqlType = ColumnParseUtil.getMysqlType(columnMap.type);
            buffer.append("\t`").append(columnMap.column).append("`");
            if(columnMap.mainKey) {
                if(mysqlType.equalsIgnoreCase("bigint")) {
                    buffer.append(" bigint(20) ");
                    buffer.append(" unsigned NOT NULL AUTO_INCREMENT ");
                }else if(mysqlType.equalsIgnoreCase("varchar")){
                    buffer.append(" varchar(32) ");
                    buffer.append(" NOT NULL ");
                }
                buffer.append(",\n");
                buffer.append("\tPRIMARY KEY (`"+columnMap.column+"`),\n");
            }else{
                String lengthStr=null;
                int length = columnMap.length;
                switch(mysqlType){
                    case "varchar":
                        if(length<=0){
                            length = 32;
                        }
                        lengthStr="("+length+")";
                        break;
                    case "int":
                        if(length<=0){
                            length = 11;
                        }
                        lengthStr="("+length+")";
                        break;
                    case "datetime":
                        lengthStr="";
                        break;
                    case "decimal":
                        if(length<=0){
                            length = 8;
                        }
                        lengthStr="("+length+",2)";
                        break;
                     default:
                         lengthStr="";
                }
                buffer.append(mysqlType).append(lengthStr).append(" DEFAULT NULL,\n");
            }
        }
        String fs=buffer.toString().trim();
        if(fs.endsWith(",")){
            fs = fs.substring(0,fs.length()-1);
        }
        fs+= "\n) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4";
        return fs;
    }
    private static AttributeColumnMap getAttributeColumnMapByAttribute(String attributeName,
                                                                       List<AttributeColumnMap> list) {
        for (AttributeColumnMap acm : list)
@@ -434,6 +530,8 @@
    String attribute;
    String column;
    String type;
    boolean mainKey;
    int length;
    public AttributeColumnMap(String attribute, String column, String type) {
        this.attribute = attribute;
@@ -441,6 +539,7 @@
        this.type = type;
    }
    public AttributeColumnMap() {
    }
src/main/java/org/yeshi/utils/generater/util/NameUtil.java
@@ -24,6 +24,10 @@
        return entity.getSimpleName() + "Exception";
    }
    public static String getDefaultAdminVOName(Class entity) {
        return entity.getSimpleName() + "AdminVO";
    }
    public static String getDefaultQueryName(Class entity) {
        return entity.getSimpleName() + "Query";
    }
src/main/java/org/yeshi/utils/generater/vo/admin/controller/AdminControllerInfoVO.java
@@ -18,6 +18,7 @@
    private ClassInfo entity;
    private ClassInfo service;
    private ClassInfo query;
    private ClassInfo adminVO;
    private boolean jsonp;
    private boolean responseBody;
@@ -43,6 +44,8 @@
        private boolean responseBody;
        private ClassInfo adminVO;
        public Builder setAdminInfo(AdminGeneraterInfo generaterInfo) {
            this.generaterInfo = generaterInfo;
@@ -61,6 +64,11 @@
        public Builder setService(ClassInfo service) {
            this.service = service;
            return this;
        }
        public Builder setAdminVO(ClassInfo adminVO) {
            this.adminVO = adminVO;
            return this;
        }
@@ -90,8 +98,9 @@
            vo.setPackageName(packageName);
            vo.setQueryVO(query);
            vo.setService(service);
            vo.setAdminVO(adminVO);
            vo.setAdd(generaterInfo.getAddFormRows() != null && generaterInfo.getAddFormRows().size() > 0);
            vo.setUpdate(generaterInfo.getUpdateFormRows() != null && generaterInfo.getUpdateFormRows().size() > 0 );
            vo.setUpdate(generaterInfo.getUpdateFormRows() != null && generaterInfo.getUpdateFormRows().size() > 0);
            vo.setDelete(true);
            vo.setResponseBody(generaterInfo.getControllerData().isResponseBody());
@@ -202,4 +211,12 @@
    public void setResponseBody(boolean responseBody) {
        this.responseBody = responseBody;
    }
    public ClassInfo getAdminVO() {
        return adminVO;
    }
    public void setAdminVO(ClassInfo adminVO) {
        this.adminVO = adminVO;
    }
}
src/main/java/org/yeshi/utils/generater/vo/admin/page/ListInfoVO.java
@@ -1,6 +1,7 @@
package org.yeshi.utils.generater.vo.admin.page;
import org.yeshi.utils.StringUtil;
import org.yeshi.utils.generater.GeneraterManager;
import org.yeshi.utils.generater.annotation.admin.form.Select;
import org.yeshi.utils.generater.annotation.admin.form.Text;
import org.yeshi.utils.generater.annotation.admin.form.TextArea;
@@ -54,11 +55,11 @@
            ListInfoVO vo = new ListInfoVO();
            vo.setListApi(generaterInfo.getControllerData().getMapping() + "/list");
            if (generaterInfo.getAddFormRows() != null && generaterInfo.getAddFormRows().size() > 0) {
                vo.setAddPagePath(ColumnUtil.getColumnFromProperty(generaterInfo.getEntity().getSimpleName()) + "_add.html");
                vo.setAddPagePath(GeneraterManager.getHtmlNameFromEntityName(generaterInfo.getEntity().getSimpleName()) + "_add.html");
            }
            if (generaterInfo.getUpdateFormRows() != null && generaterInfo.getUpdateFormRows().size() > 0) {
                vo.setUpdatePagePath(ColumnUtil.getColumnFromProperty(generaterInfo.getEntity().getSimpleName()) + "_update.html");
                vo.setUpdatePagePath(GeneraterManager.getHtmlNameFromEntityName(generaterInfo.getEntity().getSimpleName()) + "_update.html");
            }
            vo.setSearchFormRows(generaterInfo.getSearchFormRows());
            vo.setShowFileds(generaterInfo.getShowDataList());
src/main/java/org/yeshi/utils/generater/vo/service/ServiceInfoVO.java
@@ -1,6 +1,5 @@
package org.yeshi.utils.generater.vo.service;
import org.springframework.stereotype.Service;
import org.yeshi.utils.StringUtil;
import org.yeshi.utils.bean.BeanUtil;
import org.yeshi.utils.generater.entity.BaseData;
@@ -18,7 +17,7 @@
    private ClassInfo service;
    //方法列表
    private List<ServiceMetodInfoVO> metodInfoList;
    private ClassInfo query;
    private ClassInfo query;;
    public static class Builder {
@@ -27,6 +26,7 @@
        private ClassInfo service;
        private ClassInfo query;
        private ClassInfo exception;
        public Builder setEntity(Class entity) {
@@ -53,6 +53,7 @@
            this.exception = exception;
            return this;
        }
        private String getRemarksLine(String content) {
            return "\t * " + content + "\n";
@@ -210,4 +211,5 @@
    public void setImportList(List<String> importList) {
        this.importList = importList;
    }
}
src/main/java/org/yeshi/utils/generater/vo/xmlconfig/XmlConfigParseUtil.java
@@ -109,7 +109,7 @@
        data.setInterPackage(getNodeAttributeValue(node, "interPackage"));
        data.setImplPackage(getNodeAttributeValue(node, "implPackage"));
        data.setQueryPackage(getNodeAttributeValue(node, "queryPackage"));
        data.setAdminVOPackage(getNodeAttributeValue(node, "adminVOPackage"));
        NodeList nodeList = node.getChildNodes();
        for (int i = 0; i < nodeList.getLength(); i++) {
@@ -208,6 +208,7 @@
                    adminControllerData.setMapping(getNodeAttributeValue(node1, "mapping"));
                    adminControllerData.setName(getNodeAttributeValue(node1, "name"));
                    adminControllerData.setPkg(getNodeAttributeValue(node1, "package"));
                    adminControllerData.setAdminVOPackage(getNodeAttributeValue(node1, "adminVOPackage"));
                    adminControllerData.setResponseBody(Boolean.parseBoolean(getNodeAttributeValue(node1, "responseBody")));
                    adminData.setController(adminControllerData);
                }
src/main/java/org/yeshi/utils/generater/vo/xmlconfig/admin/AdminControllerData.java
@@ -16,6 +16,8 @@
    //接口是否jsonp
    private boolean jsonp;
    private String adminVOPackage;
    public String getPkg() {
        return pkg;
@@ -56,4 +58,12 @@
    public void setJsonp(boolean jsonp) {
        this.jsonp = jsonp;
    }
    public String getAdminVOPackage() {
        return adminVOPackage;
    }
    public void setAdminVOPackage(String adminVOPackage) {
        this.adminVOPackage = adminVOPackage;
    }
}
src/main/java/org/yeshi/utils/generater/vo/xmlconfig/service/ServiceData.java
@@ -12,7 +12,7 @@
    private String queryPackage;
    private ExceptionData exception;
    private String adminVOPackage;
    public String getInterPackage() {
        return interPackage;
@@ -44,13 +44,5 @@
    public void setQueryPackage(String queryPackage) {
        this.queryPackage = queryPackage;
    }
    public String getAdminVOPackage() {
        return adminVOPackage;
    }
    public void setAdminVOPackage(String adminVOPackage) {
        this.adminVOPackage = adminVOPackage;
    }
}
src/main/java/org/yeshi/utils/mq/TDMQUtil.java
@@ -2,6 +2,8 @@
import com.qcloud.cmq.Account;
import com.qcloud.cmq.Message;
import com.qcloud.cmq.Queue;
import com.qcloud.cmq.entity.CmqResponse;
import com.tencentcloudapi.common.Credential;
import com.tencentcloudapi.common.exception.TencentCloudSDKException;
import com.tencentcloudapi.common.profile.ClientProfile;
@@ -10,6 +12,7 @@
import com.tencentcloudapi.tdmq.v20200217.models.*;
import java.util.Arrays;
import java.util.Date;
import java.util.List;
//腾讯CMQ消息
@@ -204,6 +207,21 @@
    public String sendMsg(String queueName, String msg) {
        return this.sendMsg(queueName, msg, 0L);
    }
    // 发送消息
    public List<CmqResponse> batchSendMsg(String queueName, List<String> msgList, long delaySeconds) throws Exception {
        Queue queue = account.getQueue(queueName);
        if (delaySeconds > 0) {
            return queue.batchSend(msgList, (int) delaySeconds);
        } else {
            return queue.batchSend(msgList);
        }
    }
    // 发送消息
    public List<CmqResponse> batchSendMsg(String queueName, List<String> msgList) throws Exception {
        return batchSendMsg(queueName, msgList, 0);
    }
@@ -451,32 +469,32 @@
    public static void main(String[] args) {
        TDMQUtil.getInstance().init("AKIDTlpgJhLjOozvd6QI2XnpfGbgV4NQJk25", "xhCSUHo55oHUQ6XicFcmfIgspX0EEzWo", true);
        String queueName = "test1";
        String topicName = "topic_test";
        //创建
        TDMQUtil.getInstance().createQueue(queueName);
        //发送消息
        TDMQUtil.getInstance().sendMsg(queueName, "测试消息");
        //创建主题
        TDMQUtil.getInstance().createTopic(topicName);
        //创建订阅
        TDMQUtil.getInstance().subscribeTopic(topicName, topicName + queueName, queueName);
        //发送订阅消息
        TDMQUtil.getInstance().publishTopicMessage(topicName, "主题消息");
        String queueName = "makemoney-goldcorn-settle";
//        String topicName = "topic_test";
//
//        //创建
//        TDMQUtil.getInstance().createQueue(queueName);
//
//        //发送消息
//        TDMQUtil.getInstance().sendMsg(queueName, "测试消息");
//
//        //创建主题
//        TDMQUtil.getInstance().createTopic(topicName);
//
//        //创建订阅
//        TDMQUtil.getInstance().subscribeTopic(topicName, topicName + queueName, queueName);
//
//        //发送订阅消息
//        TDMQUtil.getInstance().publishTopicMessage(topicName, "主题消息");
        //消费消息
        try {
            Message message = TDMQUtil.getInstance().recieveMsg(queueName);
            System.out.println("接受到的消息:" + message.msgBody);
            TDMQUtil.getInstance().deleteMsg(queueName, message.receiptHandle);
        } catch (Exception e) {
            e.printStackTrace();
        }
//        try {
//            Message message = TDMQUtil.getInstance().recieveMsg(queueName);
//            System.out.println("接受到的消息:" + message.msgBody);
//            TDMQUtil.getInstance().deleteMsg(queueName, message.receiptHandle);
//        } catch (Exception e) {
//            e.printStackTrace();
//        }
        try {
            List<Message> messages = TDMQUtil.getInstance().recieveMsg(10, queueName);
@@ -489,14 +507,14 @@
        }
        //删除订阅
        TDMQUtil.getInstance().deleteSubscribeTopic(topicName, topicName + queueName);
        //删除主题
        TDMQUtil.getInstance().deleteTopic(topicName);
        //删除队列
        TDMQUtil.getInstance().deleteQueue(queueName);
//        //删除订阅
//        TDMQUtil.getInstance().deleteSubscribeTopic(topicName, topicName + queueName);
//
//        //删除主题
//        TDMQUtil.getInstance().deleteTopic(topicName);
//
//        //删除队列
//        TDMQUtil.getInstance().deleteQueue(queueName);
    }
src/main/java/org/yeshi/utils/tencentcloud/COSManager.java
@@ -172,7 +172,7 @@
        return false;
    }
    public boolean deleteFile(String url) {
    public boolean deleteFileByUrl(String url) {
        String key = url.replace(String.format("https://%s.file.myqcloud.com", totalBucketName), "");
        try {
            cosClient.deleteObject(totalBucketName, key);
@@ -182,6 +182,15 @@
        return false;
    }
    public boolean deleteFileByKey(String key) {
        try {
            cosClient.deleteObject(totalBucketName, key);
            return true;
        } catch (Exception e) {
        }
        return false;
    }
    public static String getUploadVideoUrl(String name) {
        if (name != null && !name.startsWith("/"))
            name = "/" + name;
src/main/java/org/yeshi/utils/wx/WXAppLoginUtil.java
@@ -1,7 +1,6 @@
package org.yeshi.utils.wx;
import org.json.JSONException;
import org.json.JSONObject;
import net.sf.json.JSONObject;
import org.yeshi.utils.HttpUtil;
import org.yeshi.utils.StringUtil;
import org.yeshi.utils.entity.wx.WeiXinUser;
@@ -23,12 +22,8 @@
    public static WeiXinUser getWeiXinUser(WeiXinUserParam param) {
        String result = HttpUtil.getAsString(String.format(weiXinUrl2, param.getAccessToken(), param.getOpenId()),
                "ISO-8859-1", "UTF-8");
        JSONObject jsonObject = null;
        try {
            jsonObject = new JSONObject(result);
        } catch (JSONException e) {
            e.printStackTrace();
        }
        JSONObject jsonObject = JSONObject.fromObject(result);
        String nickname = jsonObject.optString("nickname");
        String province = jsonObject.optString("province");
        String city = jsonObject.optString("city");
@@ -64,12 +59,8 @@
    private static WeiXinUserParam parseWeiXinUserParam(String result) {
        WeiXinUserParam weiXinUserParam = new WeiXinUserParam();
        JSONObject jsonObject = null;
        try {
            jsonObject = new JSONObject(result);
        } catch (JSONException e) {
            e.printStackTrace();
        }
        JSONObject jsonObject = JSONObject.fromObject(result);
        String openId = jsonObject.optString("openid");
        if ("".equals(openId)) {
            return null;
src/main/resources/generater/admin/add.ftl
@@ -8,13 +8,16 @@
    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
    <meta name="viewport"
          content="width=device-width,user-scalable=yes, minimum-scale=0.4, initial-scale=0.8,target-densitydpi=low-dpi"/>
    <link rel="stylesheet" href="../css/font.css">
    <link rel="stylesheet" href="../css/xadmin.css">
    <script type="text/javascript" src="../lib/layui/layui.js" charset="utf-8"></script>
    <script type="text/javascript" src="../js/xadmin.js"></script>
    <script src="../js/vue.min.js" type="text/javascript" charset="utf-8"></script>
    <script src="../js/http.js" type="text/javascript" charset="utf-8"></script>
    <script type="text/javascript" src="https://cdn.bootcss.com/jquery/3.2.1/jquery.min.js"></script>
    <link rel="stylesheet" href="/admin/css/font.css">
    <link rel="stylesheet" href="/admin/css/xadmin.css">
    <link rel="stylesheet" href="/admin/css/theme3049.min.css">
    <script src="/admin/lib/layui/layui.js" charset="utf-8"></script>
    <script src="/admin/js/vue.min.js" type="text/javascript" charset="utf-8"></script>
    <script src="/admin/js/xadmin.js" type="text/javascript"></script>
    <script src="/admin/js/http.js" type="text/javascript" charset="utf-8"></script>
    <script src="/admin/js/jquery.min.js" type="text/javascript"></script>
    <script src="/admin/js/utils.js"></script>
    <!-- 让IE8/9支持媒体查询,从而兼容栅格 -->
    <!--[if lt IE 9]>
    <script src="https://cdn.staticfile.org/html5shiv/r29/html5.min.js"></script>
@@ -83,7 +86,7 @@
                auto: false,
                accept: 'images',
                acceptMime: 'image/*',
                field: "file_${value.key}",
                field: "file_url",
                choose: function (obj) {
                    //将每次选择的文件追加到文件队列
                    var files = obj.pushFile();
@@ -106,10 +109,10 @@
                    if (res.code == 0) {
                        //获取链接
                        $("input[name='${value.key}']").val(res.data.url);
                        delete chooseImage["${value.key}"];
                        if (Object.keys(chooseImage).length == 0) {
                        delete uploadTool.chooseImage["${value.key}"];
                        if (Object.keys(uploadTool.chooseImage).length == 0) {
                            //全部上传成功
                            callback();
                            uploadTool.callback(true);
                        }
                    } else {
                        layer.msg(res.msg);
@@ -125,7 +128,7 @@
        },
        upload: function (result) {
            if (this.uploadArray.length > 0) {
            if (this.uploadArray.length > 0 && Object.keys(this.chooseImage).length > 0) {
                this.callback = result;
                //同时上传
                for (var i = 0; i < this.uploadArray.length; i++) {
@@ -159,14 +162,13 @@
        uploadTool.init(upload);
        <#list rowsList as row >
               <#if (row.type=="Text" && (row.params.inputType=="DATE"||row.params.inputType=="DATETIME"))>
            <#if (row.type=="Text" && (row.params.inputType=="DATE"||row.params.inputType=="DATETIME"))>
                    laydate.render({
                          elem: "intput[name=${row.key}]", //指定元素
                          type: ${row.params.inputType?lower_case}
                        elem: "input[name=${row.key}]", //指定元素
                        type: '${row.params.inputType?lower_case}'
                    });
               </#if>
            </#if>
        </#list>
        //监听提交
        form.on('submit(add)',
@@ -185,7 +187,12 @@
                            data.field[onkeys[0]][onkeys[1]] = value;
                        }
                    }
                    uploadTool.upload(function () {
                    uploadTool.upload(function (hasFile) {
                        if (hasFile) {
                            //从新提交表单
                            $("button[lay-filter=add]").click();
                            return;
                        }
                        //发异步,把数据提交给php
                        ksapp.post('${addApi}', data.field, function (res) {
                            if (res.code == 0) {
src/main/resources/generater/admin/adminController.template
@@ -18,6 +18,10 @@
import ${entity.clazz};
import ${service.clazz};
import ${query.clazz};
<#if adminVO??>
import ${adminVO.clazz};
</#if>
<#if responseBody>
<#else>
import java.io.PrintWriter;
@@ -82,7 +86,18 @@
    <#if add>
    ${responseBody?string("@ResponseBody","")}
    @RequestMapping("add")
    public ${responseBody?string("String","void")} add(${entity.name} bean, HttpSession session${jsonp?string(", String callback","")}${responseBody?string("",",PrintWriter out")}) {
     <#if adminVO??>
    public ${responseBody?string("String","void")} add(${adminVO.name} vo,AcceptAdminData acceptAdminData${jsonp?string(", String callback","")}${responseBody?string("",",PrintWriter out")}) {
        try{
            ${serviceObjName}.add(vo.toEntity(acceptAdminData.getSystem()));
            <@print data="JsonUtil.loadTrueResult(\"\")" > </@print>
        }catch(Exception e){
            <@print data="JsonUtil.loadFalseResult(e.getMessage())" > </@print>
        }
    }
     <#else>
    public ${responseBody?string("String","void")} add(${entity.name} bean, AcceptAdminData acceptAdminData${jsonp?string(", String callback","")}${responseBody?string("",",PrintWriter out")}) {
        try{
            ${serviceObjName}.add(bean);
            <@print data="JsonUtil.loadTrueResult(\"\")" > </@print>
@@ -91,10 +106,11 @@
        }
    }
    </#if>
    </#if>
    ${responseBody?string("@ResponseBody","")}
    @RequestMapping("get")
    public ${responseBody?string("String","void")} get(${identifyIdType} id, HttpSession session${jsonp?string(", String callback","")}${responseBody?string("",",PrintWriter out")}) {
    public ${responseBody?string("String","void")} get(${identifyIdType} id, AcceptAdminData acceptAdminData${jsonp?string(", String callback","")}${responseBody?string("",",PrintWriter out")}) {
        ${entity.name} entity = ${serviceObjName}.get(id);
        if (entity !=null){
            <@print data="JsonUtil.loadTrueResult(entity)" > </@print>
@@ -107,7 +123,23 @@
    <#if update>
    ${responseBody?string("@ResponseBody","")}
    @RequestMapping("update")
    public ${responseBody?string("String","void")} update(${entity.name} bean, HttpSession session${jsonp?string(", String callback","")}${responseBody?string("",",PrintWriter out")}) {
    <#if adminVO??>
    public ${responseBody?string("String","void")} update( ${adminVO.name} vo ,AcceptAdminData acceptAdminData${jsonp?string(", String callback","")}${responseBody?string("",",PrintWriter out")}) {
        if (vo.getId() == null) {
           <@print data="JsonUtil.loadFalseResult(\"ID不能为空\")" > </@print>
        }
        try{
            ${serviceObjName}.update(vo.toEntity(null));
        }catch(Exception e){
            <@print data="JsonUtil.loadFalseResult(e.getMessage())" > </@print>
        }
        <@print data="JsonUtil.loadTrueResult(\"\")" > </@print>
    }
    <#else>
    public ${responseBody?string("String","void")} update( ${entity.name} bean , AcceptAdminData acceptAdminData${jsonp?string(", String callback","")}${responseBody?string("",",PrintWriter out")}) {
        if (bean.getId() == null) {
           <@print data="JsonUtil.loadFalseResult(\"ID不能为空\")" > </@print>
        }
@@ -119,6 +151,7 @@
        <@print data="JsonUtil.loadTrueResult(\"\")" > </@print>
    }
    </#if>
    </#if>
}
src/main/resources/generater/admin/adminVO.template
@@ -9,8 +9,6 @@
<#list columns as column >
   <#if column.type=='Date'>
    private String ${column.columnName};
   <#elseif column.type=='Boolean'>
    private String ${column.columnName};
   <#else>
    private ${column.type} ${column.columnName};
   </#if>
@@ -21,8 +19,6 @@
        <#list columns as column >
          <#if column.type=='Date'>
        entity.${column.setColumnMehtodName}(new Date(TimeUtil.convertToTimeTemp(${column.columnName}, "yyyy-MM-dd HH:mm:ss")));
         <#elseif column.type=='Boolean'>
        entity.${column.setColumnMehtodName}("on".equalsIgnoreCase(${column.columnName}) ? true : false);
         <#else>
        entity.${column.setColumnMehtodName}(${column.columnName});
          </#if>
@@ -36,8 +32,6 @@
        <#list columns as column >
         <#if column.type=='Date'>
        vo.${column.setColumnMehtodName}(TimeUtil.getGernalTime(entity.${column.columnMehtod}.getTime(), "yyyy-MM-dd HH:mm:ss"));
         <#elseif column.type=='Boolean'>
        vo.${column.setColumnMehtodName}(entity.${column.columnMehtod} ? "on" : null);
          <#else>
        vo.${column.setColumnMehtodName}(entity.${column.columnMehtod});
          </#if>
@@ -47,14 +41,6 @@
    <#list columns as column >
     <#if column.type=='Date'>
     public String ${column.columnMehtod} {
        return ${column.columnName};
     }
      public void ${column.setColumnMehtodName}(String ${column.columnName}) {
        this.${column.columnName} = ${column.columnName};
      }
      <#elseif column.type=='Boolean'>
     public String ${column.columnMehtod} {
        return ${column.columnName};
     }
src/main/resources/generater/admin/form/checkBox.ftl
@@ -1 +1 @@
                            <input type="checkbox" name="${value.key}" title="${value.value}">
                            <input type="checkbox" name="${value.key}" title="${value.value}" value="true">
src/main/resources/generater/admin/form/img.ftl
@@ -1,5 +1,5 @@
                        <#if value.params.uploadApi??&&value.params.uploadApi!="">
                        <img id="img_${value.key}" style="display: block;margin-bottom: 10px;  <#if value.params.width gt 0 > width:${value.params.width}px;</#if> <#if value.params.height gt 0 > height:${value.params.height}px;</#if> " />
                        <img id="img_${value.key}" style="display: block;margin-bottom: 10px;  <#if value.params.width gt 0 > width:${value.params.width}px;</#if> <#if value.params.height gt 0 > max-height:${value.params.height}px;</#if> " />
                        <button type="button" class="layui-btn" id="upload_${value.key}" style="margin-bottom: 5px">
                            <i class="layui-icon">&#xe67c;</i>上传图片
                        </button>
src/main/resources/generater/admin/list.ftl
@@ -8,14 +8,16 @@
    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
    <meta name="viewport"
          content="width=device-width,user-scalable=yes, minimum-scale=0.4, initial-scale=0.8,target-densitydpi=low-dpi"/>
    <link rel="stylesheet" href="../css/font.css">
    <link rel="stylesheet" href="../css/xadmin.css">
    <script src="../lib/layui/layui.js" charset="utf-8"></script>
    <link rel="stylesheet" href="../css/theme3049.min.css">
    <script src="../js/vue.min.js" type="text/javascript" charset="utf-8"></script>
    <script type="text/javascript" src="../js/xadmin.js"></script>
    <script src="../js/http.js" type="text/javascript" charset="utf-8"></script>
    <script type="text/javascript" src="https://cdn.bootcss.com/jquery/3.2.1/jquery.min.js"></script>
    <link rel="stylesheet" href="/admin/css/font.css">
    <link rel="stylesheet" href="/admin/css/xadmin.css">
    <link rel="stylesheet" href="/admin/css/theme3049.min.css">
    <script src="/admin/lib/layui/layui.js" charset="utf-8"></script>
    <script src="/admin/js/vue.min.js" type="text/javascript" charset="utf-8"></script>
    <script src="/admin/js/xadmin.js" type="text/javascript"></script>
    <script src="/admin/js/http.js" type="text/javascript" charset="utf-8"></script>
    <script src="/admin/js/jquery.min.js" type="text/javascript"></script>
    <script src="/admin/js/utils.js"></script>
    <!--[if lt IE 9]>
    <script src="https://cdn.staticfile.org/html5shiv/r29/html5.min.js"></script>
    <script src="https://cdn.staticfile.org/respond.js/1.4.2/respond.min.js"></script>
src/main/resources/generater/admin/update.ftl
@@ -8,13 +8,16 @@
    <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
    <meta name="viewport"
          content="width=device-width,user-scalable=yes, minimum-scale=0.4, initial-scale=0.8,target-densitydpi=low-dpi"/>
    <link rel="stylesheet" href="../css/font.css">
    <link rel="stylesheet" href="../css/xadmin.css">
    <script type="text/javascript" src="../lib/layui/layui.js" charset="utf-8"></script>
    <script type="text/javascript" src="../js/xadmin.js"></script>
    <script src="../js/vue.min.js" type="text/javascript" charset="utf-8"></script>
    <script src="../js/http.js" type="text/javascript" charset="utf-8"></script>
    <script type="text/javascript" src="https://cdn.bootcss.com/jquery/3.2.1/jquery.min.js"></script>
    <link rel="stylesheet" href="/admin/css/font.css">
    <link rel="stylesheet" href="/admin/css/xadmin.css">
    <link rel="stylesheet" href="/admin/css/theme3049.min.css">
    <script src="/admin/lib/layui/layui.js" charset="utf-8"></script>
    <script src="/admin/js/vue.min.js" type="text/javascript" charset="utf-8"></script>
    <script src="/admin/js/xadmin.js" type="text/javascript"></script>
    <script src="/admin/js/http.js" type="text/javascript" charset="utf-8"></script>
    <script src="/admin/js/jquery.min.js" type="text/javascript"></script>
    <script src="/admin/js/utils.js"></script>
    <!-- 让IE8/9支持媒体查询,从而兼容栅格 -->
    <!--[if lt IE 9]>
    <script src="https://cdn.staticfile.org/html5shiv/r29/html5.min.js"></script>
@@ -83,7 +86,7 @@
                auto: false,
                accept: 'images',
                acceptMime: 'image/*',
                field: "file_${value.key}",
                field: "file_url",
                choose: function (obj) {
                    //将每次选择的文件追加到文件队列
                    var files = obj.pushFile();
@@ -106,10 +109,10 @@
                    if (res.code == 0) {
                        //获取链接
                        $("input[name='${value.key}']").val(res.data.url);
                        delete chooseImage["${value.key}"];
                        if (Object.keys(chooseImage).length == 0) {
                        delete uploadTool.chooseImage["${value.key}"];
                        if (Object.keys(uploadTool.chooseImage).length == 0) {
                            //全部上传成功
                            callback();
                            uploadTool.callback(true);
                        }
                    } else {
                        layer.msg(res.msg);
@@ -125,7 +128,7 @@
        },
        upload: function (result) {
            if (this.uploadArray.length > 0) {
            if (this.uploadArray.length > 0&&Object.keys(this.chooseImage).length>0) {
                this.callback = result;
                //同时上传
                for (var i = 0; i < this.uploadArray.length; i++) {
@@ -180,8 +183,8 @@
        <#list rowsList as row >
            <#if (row.type=="Text" && (row.params.inputType=="DATE"||row.params.inputType=="DATETIME"))>
                    laydate.render({
                        elem: "intput[name=${row.key}]", //指定元素
                        type: ${row.params.inputType?lower_case}
                        elem: "input[name=${row.key}]", //指定元素
                        type: '${row.params.inputType?lower_case}'
                    });
            </#if>
        </#list>
@@ -211,7 +214,12 @@
                            data.field[onkeys[0]][onkeys[1]] = value;
                        }
                    }
                    uploadTool.upload(function () {
                    uploadTool.upload(function (hasFile) {
                        if (hasFile) {
                            //从新提交表单
                            $("button[lay-filter=update]").click();
                            return;
                        }
                        //发异步,把数据提交给php
                        var params = data.field;
                        params.id = ksapp.getQueryParam("id");
src/main/resources/schemas/generator.dtd
@@ -19,7 +19,7 @@
        <!ATTLIST service interPackage CDATA #REQUIRED>
        <!ATTLIST service implPackage CDATA #REQUIRED>
        <!ATTLIST service queryPackage CDATA #REQUIRED>
        <!ATTLIST service adminVOPackage CDATA #IMPLIED>
        <!ELEMENT exception  EMPTY>
@@ -37,6 +37,7 @@
        <!ATTLIST controller mapping CDATA #REQUIRED>
        <!ATTLIST controller responseBody (true|false) "true">
        <!ATTLIST controller jsonp (true|false) "true">
        <!ATTLIST controller adminVOPackage CDATA #IMPLIED>
        <!ELEMENT pages  (list?,add?,update?)>
src/main/resources/test.xml
New file
@@ -0,0 +1,88 @@
<?xml version='1.0' encoding='UTF-8'?>
<!DOCTYPE generator-config  PUBLIC "-//yeshitv.com//DTD generator_code 1.0//EN"
        "http://192.168.3.122:8848/buwan-web/dtd/generator.dtd">
<generator-config class="org.yeshi.utils.generater.TestEntity3">
    <dao package="com.generater.test.mapper" mapperDir="D:/workspace/server/utils/src/test/java/mapper">
        <queryList>
            <query name="nickName" type="contains"></query>
        </queryList>
    </dao>
    <service interPackage="com.generater.test.service.inter" implPackage="com.generater.test.service.impl"
             queryPackage="com.generater.test.query">
        <exception package="com.generater.test.exception"></exception>
    </service>
    <admin>
        <controller package="com.generater.test.controller.admin" mapping="/test" />
        <pages title="测试" pageDir="D:/workspace/server/utils/src/test/java/html">
            <list fileName="list.html">
                <searchForm>
                    <columns>
                        <column property="nickName" title="昵称">
                            <text inputType="TEXT" maxLength="100"></text>
                        </column>
                    </columns>
                </searchForm>
                <columns>
                    <column property="id" title="ID" showType="TEXT"></column>
                    <column property="nickName" title="昵称" showType="TEXT"></column>
                    <column property="sex" title="性别" showType="TEXT"></column>
                    <column property="portrait" title="头像" showType="IMG"></column>
                </columns>
            </list>
            <add fileName="add.html">
                <column property="nickName" title="昵称">
                    <text inputType="TEXT" dateFormat="" placeHolder="">
                        <verify type="regex" express="*" require="true" notify=""></verify>
                    </text>
                </column>
                <column property="sex" title="性别">
                    <select>
                        <values>
                            <value key="0">未知</value>
                            <value key="1">男</value>
                            <value key="2">女</value>
                        </values>
                    </select>
                </column>
                <column property="province" title="省份">
                    <select>
                        <api path="api/getCountrys">
                            <params>
                                <value key="cq">重庆</value>
                                <value key="sc">四川</value>
                            </params>
                        </api>
                        <verify type="none" require="true"></verify>
                    </select>
                </column>
                <column property="show" title="是否显示">
                    <switch></switch>
                </column>
                <column property="portrait" title="头像">
                    <img enable="false" editLink="true">
                        <api path="/api/uploadImg">
                            <params>
                                <value key="type">portrait</value>
                            </params>
                        </api>
                    </img>
                </column>
            </add>
            <update fileName="update.html">
                <column property="nickName" title="昵称">
                    <text inputType="TEXT">
                        <verify type="regex" express="*" require="true" notify=""></verify>
                    </text>
                </column>
            </update>
        </pages>
    </admin>
</generator-config>
src/test/java/com/generater/GeneratorTest.java
@@ -4,9 +4,11 @@
import org.yeshi.utils.FileUtil;
import org.yeshi.utils.FreemarkerUtils;
import org.yeshi.utils.generater.GeneraterUtil;
import org.yeshi.utils.generater.TestEntity3;
import org.yeshi.utils.generater.entity.ClassInfo;
import org.yeshi.utils.generater.entity.admin.AdminGeneraterInfo;
import org.yeshi.utils.generater.mybatis.Column;
import org.yeshi.utils.generater.mybatis.MyBatisMapperUtil;
import org.yeshi.utils.generater.mybatis.Table;
import org.yeshi.utils.generater.vo.ExceptionVO;
import org.yeshi.utils.generater.vo.xmlconfig.base.FormComponent;
@@ -49,7 +51,9 @@
        //
//        boolean match = Pattern.matches("^(https://){1}.*(\\.m3u8)$", "https://n1.szjal.cn/20210805/qnDXhXBa/index.m3u8123");
//        System.out.println(match);
        generater();
//        generater();
       String sql =  MyBatisMapperUtil.createSQL(TestEntity3.class);
       System.out.println(sql);
    }
    private static void generateAdminPage() throws Exception {
src/test/java/com/generater/TestEntity2.java
@@ -25,6 +25,7 @@
@Table("table_test")
public class TestEntity2 {
    @Id
    @Column(name="id")
    private String id;
    @Column(name="nick_name")