use of org.sagacity.sqltoy.callback.ReflectPropsHandler in project sagacity-sqltoy by chenrenfei.
the class DialectUtils method getUpdateReflectHandler.
/**
* @todo 构造修改记录参数反射赋值处理器
* @param preHandler
* @param forceUpdateProps
* @param unifyFieldsHandler
* @return
*/
public static ReflectPropsHandler getUpdateReflectHandler(final ReflectPropsHandler preHandler, String[] forceUpdateProps, IUnifyFieldsHandler unifyFieldsHandler) {
if (unifyFieldsHandler == null) {
return preHandler;
}
final Map<String, Object> keyValues = unifyFieldsHandler.updateUnifyFields();
if (keyValues == null || keyValues.isEmpty()) {
return preHandler;
}
// update操作强制更新字段优先
final Set<String> forceSet = new HashSet<String>();
if (forceUpdateProps != null && forceUpdateProps.length > 0) {
for (String field : forceUpdateProps) {
forceSet.add(field.toLowerCase().replace("_", ""));
}
}
// 强制修改字段赋值
IgnoreCaseSet tmpSet = unifyFieldsHandler.forceUpdateFields();
final IgnoreCaseSet forceUpdateFields = (tmpSet == null) ? new IgnoreCaseSet() : tmpSet;
ReflectPropsHandler handler = new ReflectPropsHandler() {
@Override
public void process() {
if (preHandler != null) {
preHandler.setPropertyIndexMap(this.getPropertyIndexMap());
preHandler.setRowIndex(this.getRowIndex());
preHandler.setRowData(this.getRowData());
preHandler.process();
}
// 修改操作
for (Map.Entry<String, Object> entry : keyValues.entrySet()) {
// 统一修改字段不在强制更新字段范围内
if (!forceSet.contains(entry.getKey().toLowerCase())) {
if (StringUtil.isBlank(this.getValue(entry.getKey())) || forceUpdateFields.contains(entry.getKey())) {
this.setValue(entry.getKey(), entry.getValue());
}
}
}
}
};
return handler;
}
use of org.sagacity.sqltoy.callback.ReflectPropsHandler in project sagacity-sqltoy by chenrenfei.
the class SqlServerDialectUtils method update.
/**
* @todo 单个对象修改,包含级联修改
* @param sqlToyContext
* @param entity
* @param forceUpdateFields
* @param cascade
* @param emptyCascadeClasses
* @param subTableForceUpdateProps
* @param conn
* @param dbType
* @param tableName
* @return
* @throws Exception
*/
public static Long update(SqlToyContext sqlToyContext, Serializable entity, String[] forceUpdateFields, final boolean cascade, final Class[] emptyCascadeClasses, final HashMap<Class, String[]> subTableForceUpdateProps, Connection conn, final Integer dbType, final String tableName) throws Exception {
EntityMeta entityMeta = sqlToyContext.getEntityMeta(entity.getClass());
String realTable = entityMeta.getSchemaTable(tableName, dbType);
Long updateCount = DialectUtils.update(sqlToyContext, entity, entityMeta, "isnull", forceUpdateFields, conn, dbType, realTable);
// 级联修改
if (cascade && !entityMeta.getCascadeModels().isEmpty()) {
HashMap<Type, String> typeMap = new HashMap<Type, String>();
if (emptyCascadeClasses != null) {
for (Type type : emptyCascadeClasses) {
typeMap.put(type, "");
}
}
// 级联子表数据
List subTableData = null;
String[] forceUpdateProps = null;
EntityMeta subTableEntityMeta;
for (TableCascadeModel cascadeModel : entityMeta.getCascadeModels()) {
final Object[] mainFieldValues = BeanUtil.reflectBeanToAry(entity, cascadeModel.getFields());
subTableEntityMeta = sqlToyContext.getEntityMeta(cascadeModel.getMappedType());
forceUpdateProps = (subTableForceUpdateProps == null) ? null : subTableForceUpdateProps.get(cascadeModel.getMappedType());
if (cascadeModel.getCascadeType() == 1) {
subTableData = (List) BeanUtil.getProperty(entity, cascadeModel.getProperty());
} else {
subTableData = new ArrayList();
Object item = BeanUtil.getProperty(entity, cascadeModel.getProperty());
if (item != null) {
subTableData.add(item);
}
}
final String[] mappedFields = cascadeModel.getMappedFields();
// 针对存量子表数据,调用级联修改的语句,分delete 和update两种操作 1、删除存量数据;2、设置存量数据状态为停用
if (cascadeModel.getCascadeUpdateSql() != null && ((subTableData != null && !subTableData.isEmpty()) || typeMap.containsKey(cascadeModel.getMappedType()))) {
SqlExecuteStat.debug("执行子表级联更新前的存量数据更新", null);
SqlToyResult sqlToyResult = SqlConfigParseUtils.processSql(cascadeModel.getCascadeUpdateSql(), mappedFields, mainFieldValues, null);
SqlUtil.executeSql(sqlToyContext.getTypeHandler(), sqlToyResult.getSql(), sqlToyResult.getParamsValue(), null, conn, dbType, null, true);
}
// 子表数据不为空,采取saveOrUpdateAll操作
if (subTableData != null && !subTableData.isEmpty()) {
logger.info("执行update主表:{} 对应级联子表: {} 更新操作!", tableName, subTableEntityMeta.getTableName());
SqlExecuteStat.debug("执行子表级联更新操作", null);
saveOrUpdateAll(sqlToyContext, subTableData, sqlToyContext.getBatchSize(), // 设置关联外键字段的属性值(来自主表的主键)
new ReflectPropsHandler() {
public void process() {
for (int i = 0; i < mappedFields.length; i++) {
this.setValue(mappedFields[i], mainFieldValues[i]);
}
}
}, forceUpdateProps, conn, dbType, null, null);
} else {
logger.info("未执行update主表:{} 对应级联子表: {} 更新操作,子表数据为空!", tableName, subTableEntityMeta.getTableName());
}
}
}
return updateCount;
}
use of org.sagacity.sqltoy.callback.ReflectPropsHandler in project sagacity-sqltoy by chenrenfei.
the class SqlServerDialectUtils method saveAll.
/**
* @todo 保存批量对象数据
* @param sqlToyContext
* @param entityMeta
* @param pkStrategy
* @param isAssignPK
* @param insertSql
* @param entities
* @param reflectPropsHandler
* @param conn
* @param dbType
* @param autoCommit
* @return
* @throws Exception
*/
private static Long saveAll(SqlToyContext sqlToyContext, EntityMeta entityMeta, PKStrategy pkStrategy, boolean isAssignPK, String insertSql, List<?> entities, ReflectPropsHandler reflectPropsHandler, Connection conn, final Integer dbType, final Boolean autoCommit) throws Exception {
boolean isIdentity = pkStrategy != null && pkStrategy.equals(PKStrategy.IDENTITY);
boolean isSequence = pkStrategy != null && pkStrategy.equals(PKStrategy.SEQUENCE);
String[] reflectColumns;
if ((isIdentity && !isAssignPK) || (isSequence && !isAssignPK)) {
reflectColumns = entityMeta.getRejectIdFieldArray();
} else {
reflectColumns = entityMeta.getFieldsArray();
}
ReflectPropsHandler handler = DialectUtils.getAddReflectHandler(reflectPropsHandler, sqlToyContext.getUnifyFieldsHandler());
handler = DialectUtils.getSecureReflectHandler(handler, sqlToyContext.getFieldsSecureProvider(), sqlToyContext.getDesensitizeProvider(), entityMeta.getSecureFields());
List<Object[]> paramValues = BeanUtil.reflectBeansToInnerAry(entities, reflectColumns, null, handler);
int pkIndex = entityMeta.getIdIndex();
// 是否存在业务ID
boolean hasBizId = (entityMeta.getBusinessIdGenerator() == null) ? false : true;
int bizIdColIndex = hasBizId ? entityMeta.getFieldIndex(entityMeta.getBusinessIdField()) : 0;
// 标识符
String signature = entityMeta.getBizIdSignature();
Integer[] relatedColumn = entityMeta.getBizIdRelatedColIndex();
// 无主键值以及多主键以及assign或通过generator方式产生主键策略
if (pkStrategy != null && null != entityMeta.getIdGenerator()) {
int idLength = entityMeta.getIdLength();
int bizIdLength = entityMeta.getBizIdLength();
Object[] rowData;
boolean isAssigned = true;
List<Object[]> idSet = new ArrayList<Object[]>();
String idJdbcType = entityMeta.getIdType();
Object[] relatedColValue = null;
String businessIdType = hasBizId ? entityMeta.getColumnJavaType(entityMeta.getBusinessIdField()) : "";
for (int i = 0, s = paramValues.size(); i < s; i++) {
rowData = (Object[]) paramValues.get(i);
if (relatedColumn != null) {
relatedColValue = new Object[relatedColumn.length];
for (int meter = 0; meter < relatedColumn.length; meter++) {
relatedColValue[meter] = rowData[relatedColumn[meter]];
if (relatedColValue[meter] == null) {
throw new IllegalArgumentException("对象:" + entityMeta.getEntityClass().getName() + " 生成业务主键依赖的关联字段:" + relatedColumn[meter] + " 值为null!");
}
}
}
if (StringUtil.isBlank(rowData[pkIndex])) {
isAssigned = false;
rowData[pkIndex] = entityMeta.getIdGenerator().getId(entityMeta.getTableName(), signature, entityMeta.getBizIdRelatedColumns(), relatedColValue, null, idJdbcType, idLength, entityMeta.getBizIdSequenceSize());
}
if (hasBizId && StringUtil.isBlank(rowData[bizIdColIndex])) {
rowData[bizIdColIndex] = entityMeta.getBusinessIdGenerator().getId(entityMeta.getTableName(), signature, entityMeta.getBizIdRelatedColumns(), relatedColValue, null, businessIdType, bizIdLength, entityMeta.getBizIdSequenceSize());
// 回写业务主键值
BeanUtil.setProperty(entities.get(i), entityMeta.getBusinessIdField(), rowData[bizIdColIndex]);
}
idSet.add(new Object[] { rowData[pkIndex] });
}
// 批量反向设置最终得到的主键值
if (!isAssigned) {
BeanUtil.mappingSetProperties(entities, entityMeta.getIdArray(), idSet, new int[] { 0 }, true);
}
}
SqlExecuteStat.showSql("mssql批量保存", insertSql, null);
return batchUpdateByJdbc(sqlToyContext.getTypeHandler(), insertSql, paramValues, sqlToyContext.getBatchSize(), entityMeta.getFieldsTypeArray(), autoCommit, conn, dbType);
}
use of org.sagacity.sqltoy.callback.ReflectPropsHandler in project sagacity-sqltoy by chenrenfei.
the class DefaultDialectUtils method processFieldValues.
/**
* @TODO 反射实体对象的属性值到数组,并调用主键策略产生主键值并写回到entity中
* @param sqlToyContext
* @param entityMeta
* @param entity
* @return
* @throws Exception
*/
private static Object[] processFieldValues(final SqlToyContext sqlToyContext, EntityMeta entityMeta, Serializable entity) throws Exception {
// 构造全新的新增记录参数赋值反射(覆盖之前的)
ReflectPropsHandler handler = DialectUtils.getAddReflectHandler(null, sqlToyContext.getUnifyFieldsHandler());
handler = DialectUtils.getSecureReflectHandler(handler, sqlToyContext.getFieldsSecureProvider(), sqlToyContext.getDesensitizeProvider(), entityMeta.getSecureFields());
// 这里不体现defaultValue 值,产生的insert sql语句中已经处理了default值问题
Object[] fullParamValues = BeanUtil.reflectBeanToAry(entity, entityMeta.getFieldsArray(), null, handler);
// 主键采用assign方式赋予,则调用generator产生id并赋予其值
if (entityMeta.getIdStrategy() != null && null != entityMeta.getIdGenerator()) {
int bizIdLength = entityMeta.getBizIdLength();
int idLength = entityMeta.getIdLength();
int pkIndex = entityMeta.getIdIndex();
// 是否存在业务ID
boolean hasBizId = (entityMeta.getBusinessIdGenerator() == null) ? false : true;
int bizIdColIndex = hasBizId ? entityMeta.getFieldIndex(entityMeta.getBusinessIdField()) : 0;
// 标识符
String signature = entityMeta.getBizIdSignature();
Integer[] relatedColumn = entityMeta.getBizIdRelatedColIndex();
String[] relatedColumnNames = entityMeta.getBizIdRelatedColumns();
int relatedColumnSize = (relatedColumn == null) ? 0 : relatedColumn.length;
Object[] relatedColValue = null;
String businessIdType = hasBizId ? entityMeta.getColumnJavaType(entityMeta.getBusinessIdField()) : "";
if (StringUtil.isBlank(fullParamValues[pkIndex]) || StringUtil.isBlank(fullParamValues[bizIdColIndex])) {
if (relatedColumn != null) {
relatedColValue = new Object[relatedColumnSize];
for (int meter = 0; meter < relatedColumnSize; meter++) {
relatedColValue[meter] = fullParamValues[relatedColumn[meter]];
if (StringUtil.isBlank(relatedColValue[meter])) {
throw new IllegalArgumentException("对象:" + entityMeta.getEntityClass().getName() + " 生成业务主键依赖的关联字段:" + relatedColumnNames[meter] + " 值为null!");
}
}
}
}
if (StringUtil.isBlank(fullParamValues[pkIndex])) {
// id通过generator机制产生,设置generator产生的值
fullParamValues[pkIndex] = entityMeta.getIdGenerator().getId(entityMeta.getTableName(), signature, entityMeta.getBizIdRelatedColumns(), relatedColValue, null, entityMeta.getIdType(), idLength, entityMeta.getBizIdSequenceSize());
// 回写主键值
BeanUtil.setProperty(entity, entityMeta.getIdArray()[0], fullParamValues[pkIndex]);
}
if (hasBizId && StringUtil.isBlank(fullParamValues[bizIdColIndex])) {
fullParamValues[bizIdColIndex] = entityMeta.getBusinessIdGenerator().getId(entityMeta.getTableName(), signature, entityMeta.getBizIdRelatedColumns(), relatedColValue, null, businessIdType, bizIdLength, entityMeta.getBizIdSequenceSize());
// 回写业务主键值
BeanUtil.setProperty(entity, entityMeta.getBusinessIdField(), fullParamValues[bizIdColIndex]);
}
}
return fullParamValues;
}
use of org.sagacity.sqltoy.callback.ReflectPropsHandler in project sagacity-sqltoy by chenrenfei.
the class ClickHouseDialectUtils method update.
public static Long update(SqlToyContext sqlToyContext, Serializable entity, String nullFunction, String[] forceUpdateFields, Connection conn, final Integer dbType, String tableName) throws Exception {
EntityMeta entityMeta = sqlToyContext.getEntityMeta(entity.getClass());
String realTable = entityMeta.getSchemaTable(tableName, dbType);
// 无主键
if (entityMeta.getIdArray() == null) {
throw new IllegalArgumentException("表:" + realTable + " 无主键,不符合update/updateAll规则,请检查表设计是否合理!");
}
// 全部是主键则无需update
if (entityMeta.getRejectIdFieldArray() == null) {
logger.warn("表:" + realTable + " 字段全部是主键不存在更新字段,无需执行更新操作!");
return 0L;
}
// 构造全新的修改记录参数赋值反射(覆盖之前的)
ReflectPropsHandler handler = DialectUtils.getUpdateReflectHandler(null, forceUpdateFields, sqlToyContext.getUnifyFieldsHandler());
handler = DialectUtils.getSecureReflectHandler(handler, sqlToyContext.getFieldsSecureProvider(), sqlToyContext.getDesensitizeProvider(), entityMeta.getSecureFields());
// 排除分区字段
String[] fields = entityMeta.getFieldsNotPartitionKey();
Object[] fieldsValues = BeanUtil.reflectBeanToAry(entity, fields, null, handler);
// 判断主键是否为空
int end = fields.length;
int pkIndex = end - entityMeta.getIdArray().length;
for (int i = pkIndex; i < end; i++) {
if (StringUtil.isBlank(fieldsValues[i])) {
throw new IllegalArgumentException("通过对象对表:" + realTable + " 进行update操作,主键字段必须要赋值!");
}
}
// 构建update语句
String updateSql = generateUpdateSql(dbType, entityMeta, nullFunction, forceUpdateFields, realTable);
if (updateSql == null) {
throw new IllegalArgumentException("update sql is null,引起问题的原因是没有设置需要修改的字段!");
}
Long updateCnt = SqlUtil.executeSql(sqlToyContext.getTypeHandler(), updateSql, fieldsValues, entityMeta.getFieldsTypeArray(), conn, dbType, null, false);
return updateCnt;
}
Aggregations