You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

56 lines
2.7 KiB

package com.project.base.config;
import com.baomidou.mybatisplus.core.injector.AbstractMethod;
import com.baomidou.mybatisplus.core.metadata.TableInfo;
import com.baomidou.mybatisplus.core.metadata.TableFieldInfo;
import org.apache.ibatis.executor.keygen.NoKeyGenerator;
import org.apache.ibatis.mapping.MappedStatement;
import org.apache.ibatis.mapping.SqlSource;
import java.util.stream.Collectors;
/**
* 自定义选装件MySQL 批量 Upsert
*/
public class InsertBatchOnDuplicateKeyUpdate extends AbstractMethod {
protected InsertBatchOnDuplicateKeyUpdate() {
super("batchUpsert"); // 方法名
}
@Override
public MappedStatement injectMappedStatement(Class<?> mapperClass, Class<?> modelClass, TableInfo tableInfo) {
final String methodName = "batchUpsert";
// 1. 准备 INSERT 字段
String columnScript = "(" + tableInfo.getKeyColumn() + "," +
tableInfo.getFieldList().stream()
.map(TableFieldInfo::getColumn)
.collect(Collectors.joining(",")) + ")";
// 2. 准备 VALUES 部分 (修复重点!)
String valuesScript = "(#{item." + tableInfo.getKeyProperty() + "}," +
tableInfo.getFieldList().stream()
.map(i -> {
// 【核心修复】检查该字段是否有 TypeHandler (如 JacksonTypeHandler)
if (i.getTypeHandler() != null) {
// 生成格式如:#{item.depIdPath,typeHandler=com.baomidou.mybatisplus.extension.handlers.JacksonTypeHandler}
return "#{item." + i.getProperty() + ",typeHandler=" + i.getTypeHandler().getName() + "}";
}
return "#{item." + i.getProperty() + "}";
})
.collect(Collectors.joining(",")) + ")";
// 3. 准备 ON DUPLICATE KEY UPDATE 部分
String updateScript = tableInfo.getFieldList().stream()
.filter(i -> !i.getColumn().equals("create_time"))
.map(i -> i.getColumn() + " = VALUES(" + i.getColumn() + ")")
.collect(Collectors.joining(",")) + ", update_time = NOW()";
String sql = String.format("<script>INSERT INTO %s %s VALUES <foreach collection=\"list\" item=\"item\" separator=\",\">%s</foreach> ON DUPLICATE KEY UPDATE %s</script>",
tableInfo.getTableName(), columnScript, valuesScript, updateScript);
SqlSource sqlSource = languageDriver.createSqlSource(configuration, sql, modelClass);
return this.addInsertMappedStatement(mapperClass, modelClass, methodName, sqlSource, new NoKeyGenerator(), null, null);
}
}