Commit 80b2cbf5 authored by litengwei's avatar litengwei

SQL Injection: MyBatis Mapper(SQL注入:MyBatis Mapper)

parent 9ca3358c
package com.yeejoin.amos.boot.module.common.api.interceptor;
import org.apache.ibatis.cache.CacheKey;
import org.apache.ibatis.executor.Executor;
import org.apache.ibatis.mapping.BoundSql;
import org.apache.ibatis.mapping.MappedStatement;
import org.apache.ibatis.plugin.*;
import org.apache.ibatis.session.ResultHandler;
import org.apache.ibatis.session.RowBounds;
import org.springframework.stereotype.Component;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.Properties;
@Component
// 标志该类是一个拦截器
// {@Signature(type = StatementHandler.class, method = "prepare", args = {Connection.class, Integer.class})}
@Intercepts({
@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class}),
@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class, CacheKey.class, BoundSql.class}),
}
)
public class PluginInterceptor implements Interceptor {
/**
* 进行拦截的时候要执行的方法
* @param invocation
* @return
* @throws Throwable
*/
public Object intercept(Invocation invocation) throws Throwable {
System.out.println("====intercept======");
Object[] args = invocation.getArgs();
MappedStatement mappedStatement = (MappedStatement) args[0];
Object parameter = args[1];
RowBounds rowBounds = (RowBounds) args[2];
ResultHandler resultHandler = (ResultHandler) args[3];
Executor executor = (Executor) invocation.getTarget();
CacheKey cacheKey;
BoundSql boundSql;
//由于逻辑关系,只会进入一次
if (args.length == 4) {
//4 个参数时
boundSql = mappedStatement.getBoundSql(parameter);
cacheKey = executor.createCacheKey(mappedStatement, parameter, rowBounds, boundSql);
} else {
//6 个参数时
cacheKey = (CacheKey) args[4];
boundSql = (BoundSql) args[5];
}
//id为执行的mapper方法的全路径名,如com.metro.dao.UserMapper.insertUser
String id = mappedStatement.getId();
//获取到原始sql语句
String sql = boundSql.getSql();
if("com.yeejoin.amos.boot.module.common.api.mapper.OrgUsrMapper.selectPersonListCount".equals(id) ||
"com.yeejoin.amos.boot.module.common.api.mapper.OrgUsrMapper.selectPersonList".equals(id)) {
HashMap par = new HashMap();
if(parameter instanceof HashMap) {
par = (HashMap)((HashMap<?, ?>) parameter).get("map");
}
LinkedHashMap<String,String> fieldsValue = (LinkedHashMap<String, String>) par.get("fieldsValue");
Iterator<String> iterator = fieldsValue.keySet().stream().iterator();
while (iterator.hasNext()) {
String next = iterator.next();
sql = sql.replaceFirst("item",next).replaceFirst("ietmValue", new StringBuffer().append("'").append(fieldsValue.get(next)).append("'").toString());
}
//通过反射修改sql语句
Field field = boundSql.getClass().getDeclaredField("sql");
field.setAccessible(true);
field.set(boundSql, sql);
return executor.query(mappedStatement, parameter, rowBounds, resultHandler, cacheKey, boundSql);
} else {
return invocation.proceed();
}
}
public Object plugin(Object target) {
System.out.println("-----------------------------plugin-------------------------");
return Plugin.wrap(target, this);
}
public void setProperties(Properties properties) {
System.out.println("====setProperties======");
}
}
\ No newline at end of file
......@@ -290,9 +290,15 @@ select * from (
where cd.group_code =#{groupCode} and cds.instance_id is not null and
cd.is_delete=0
group by cd.instance_id
) result
<if test="groupByName != null and groupByName!='' ">
group by ${groupByName}
) result
<if test="groupByName != null and groupByName!='' and groupByName=='result.carId'">
group by result.carId
</if>
<if test="groupByName != null and groupByName!='' and groupByName=='result.fireFightingId'">
group by result.fireFightingId
</if>
<if test="groupByName != null and groupByName!='' and groupByName=='result.firstAidId'">
group by result.firstAidId
</if>
</select>
......@@ -334,8 +340,8 @@ select * from (
cd.is_delete=0
group by cd.instance_id
) result
<if test="groupByName != null and groupByName!='' ">
group by ${groupByName}
<if test="groupByName != null and groupByName!='' and groupByName=='result.deptId'">
group by result.deptId
</if>
</select>
......
......@@ -110,10 +110,8 @@
<foreach collection="map.fieldsValue.keys" item="item">
<if test="item != 'bizOrgName'">
AND a.${item} = #{map.fieldsValue[#{item}]}
AND a.item = ietmValue
</if>
</foreach>
</if>
</select>
......@@ -218,7 +216,7 @@
<if test="map.fieldsValue != null">
<foreach collection="map.fieldsValue.keys" item="item">
<if test="item != 'bizOrgName'">
AND a.${item} = #{map.fieldsValue[#{item}]}
AND a.item = ietmValue
</if>
</foreach>
</if>
......@@ -251,7 +249,7 @@
u.biz_org_code bizOrgCode,
<if test="fields != null">
<foreach collection="fields" item="item" separator=",">MAX(case f.field_code when #{item} then IFNULL(v.field_value_label, v.field_value)
end) ${item}
end) as #{item}
</foreach>
</if>
FROM
......
package com.yeejoin.equipmanage.common.interceptor;
import org.apache.ibatis.cache.CacheKey;
import org.apache.ibatis.executor.Executor;
import org.apache.ibatis.mapping.BoundSql;
import org.apache.ibatis.mapping.MappedStatement;
import org.apache.ibatis.plugin.*;
import org.apache.ibatis.session.ResultHandler;
import org.apache.ibatis.session.RowBounds;
import org.springframework.stereotype.Component;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.Properties;
@Component
// 标志该类是一个拦截器
// {@Signature(type = StatementHandler.class, method = "prepare", args = {Connection.class, Integer.class})}
@Intercepts({
@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class}),
@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class, CacheKey.class, BoundSql.class}),
}
)
public class PluginInterceptor implements Interceptor {
/**
* 进行拦截的时候要执行的方法
* @param invocation
* @return
* @throws Throwable
*/
public Object intercept(Invocation invocation) throws Throwable {
System.out.println("====intercept======");
Object[] args = invocation.getArgs();
MappedStatement mappedStatement = (MappedStatement) args[0];
Object parameter = args[1];
RowBounds rowBounds = (RowBounds) args[2];
ResultHandler resultHandler = (ResultHandler) args[3];
Executor executor = (Executor) invocation.getTarget();
CacheKey cacheKey;
BoundSql boundSql;
//由于逻辑关系,只会进入一次
if (args.length == 4) {
//4 个参数时
boundSql = mappedStatement.getBoundSql(parameter);
cacheKey = executor.createCacheKey(mappedStatement, parameter, rowBounds, boundSql);
} else {
//6 个参数时
cacheKey = (CacheKey) args[4];
boundSql = (BoundSql) args[5];
}
//id为执行的mapper方法的全路径名,如com.metro.dao.UserMapper.insertUser
String id = mappedStatement.getId();
//获取到原始sql语句
String sql = boundSql.getSql();
if("com.yeejoin.equipmanage.mapper.FormInstanceMapper.queryForMapList".equals(id)) {
//执行结果
HashMap<String,String> par = new LinkedHashMap<>();
if(parameter instanceof HashMap) {
par = (HashMap<String, String>)((HashMap<?, ?>) parameter).get("params");
}
Iterator<String> iterator = par.keySet().stream().iterator();
while (iterator.hasNext()) {
String next = iterator.next();
sql = sql.replace("item",next);
}
//通过反射修改sql语句
Field field = boundSql.getClass().getDeclaredField("sql");
field.setAccessible(true);
field.set(boundSql, sql);
return executor.query(mappedStatement, parameter, rowBounds, resultHandler, cacheKey, boundSql);
} else {
return invocation.proceed();
}
}
public Object plugin(Object target) {
System.out.println("-----------------------------plugin-------------------------");
return Plugin.wrap(target, this);
}
public void setProperties(Properties properties) {
System.out.println("====setProperties======");
}
}
\ No newline at end of file
......@@ -17,15 +17,15 @@ import java.util.Map;
*/
public interface IFormInstanceService extends IService<FormInstance> {
/**
* 分页查询
*
* @param groupCode 分组编号
* @param current 当前页
* @param size 页面大小
* @return Page
*/
Page<Map<String, Object>> queryForInstancePage(String groupCode, long current, long size);
// /**
// * 分页查询
// *
// * @param groupCode 分组编号
// * @param current 当前页
// * @param size 页面大小
// * @return Page
// */
// Page<Map<String, Object>> queryForInstancePage(String groupCode, long current, long size);
/**
* 创建
......
......@@ -361,37 +361,37 @@ public class FormInstanceServiceImpl extends ServiceImpl<FormInstanceMapper, For
return formInstanceMapper.getFormInstanceById(instanceId);
}
@Override
public Page queryForInstancePage(String groupCode, long current, long size) {
List<FormGroupColumn> optionList = iFormGroupColumnService.queryByGroup(groupCode);
Map<String, String[]> parameterMap = request.getParameterMap();
//说明:parameterMap 为静态map 不可修改,所以需要深拷贝
Map<String, String[]> localMap = new HashMap<>();
localMap.putAll(parameterMap);
localMap.remove("current");
localMap.remove("size");
Map<String, String> params = new HashMap<>();
if (!ValidationUtil.isEmpty(localMap)) {
for (String key : localMap.keySet()) {
if (!ValidationUtil.isEmpty(localMap.get(key))) {
params.put(key, localMap.get(key)[0]);
}
}
}
Page page = new Page();
page.setCurrent(current);
page.setSize(size);
Map<String, Object> fieldNames = Bean.listToMap(optionList, "fieldName", "queryStrategy", FormGroupColumn.class);
Page<Map<String, Object>> resultList = this.getBaseMapper().queryInstancePage(page, groupCode, fieldNames, params);
if (!ValidationUtil.isEmpty(resultList)) {
for (FormGroupColumn optionModel : optionList) {
for (Map<String, Object> instanceMap : resultList.getRecords()) {
instanceMap.put(optionModel.getFieldName(), this.dataTypeProcess(optionModel.getFieldName(), instanceMap.get(optionModel.getFieldName()), optionModel.getDataType(), instanceMap));
}
}
}
return resultList;
}
// @Override
// public Page queryForInstancePage(String groupCode, long current, long size) {
// List<FormGroupColumn> optionList = iFormGroupColumnService.queryByGroup(groupCode);
// Map<String, String[]> parameterMap = request.getParameterMap();
// //说明:parameterMap 为静态map 不可修改,所以需要深拷贝
// Map<String, String[]> localMap = new HashMap<>();
// localMap.putAll(parameterMap);
// localMap.remove("current");
// localMap.remove("size");
// Map<String, String> params = new HashMap<>();
// if (!ValidationUtil.isEmpty(localMap)) {
// for (String key : localMap.keySet()) {
// if (!ValidationUtil.isEmpty(localMap.get(key))) {
// params.put(key, localMap.get(key)[0]);
// }
// }
// }
// Page page = new Page();
// page.setCurrent(current);
// page.setSize(size);
// Map<String, Object> fieldNames = Bean.listToMap(optionList, "fieldName", "queryStrategy", FormGroupColumn.class);
// Page<Map<String, Object>> resultList = this.getBaseMapper().queryInstancePage(page, groupCode, fieldNames, params);
// if (!ValidationUtil.isEmpty(resultList)) {
// for (FormGroupColumn optionModel : optionList) {
// for (Map<String, Object> instanceMap : resultList.getRecords()) {
// instanceMap.put(optionModel.getFieldName(), this.dataTypeProcess(optionModel.getFieldName(), instanceMap.get(optionModel.getFieldName()), optionModel.getDataType(), instanceMap));
// }
// }
// }
// return resultList;
// }
@Override
public List<Map<String, Object>> queryForMapList(String groupCode, Map<String, String> params) {
......
package com.yeejoin.amos.knowledgebase.interceptor;
import org.apache.ibatis.cache.CacheKey;
import org.apache.ibatis.executor.Executor;
import org.apache.ibatis.mapping.BoundSql;
import org.apache.ibatis.mapping.MappedStatement;
import org.apache.ibatis.plugin.*;
import org.apache.ibatis.session.ResultHandler;
import org.apache.ibatis.session.RowBounds;
import org.springframework.stereotype.Component;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.Properties;
@Component
// 标志该类是一个拦截器
// {@Signature(type = StatementHandler.class, method = "prepare", args = {Connection.class, Integer.class})}
@Intercepts({
@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class}),
@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class, CacheKey.class, BoundSql.class}),
}
)
public class PluginInterceptor implements Interceptor {
/**
* 进行拦截的时候要执行的方法
* @param invocation
* @return
* @throws Throwable
*/
public Object intercept(Invocation invocation) throws Throwable {
System.out.println("====intercept======");
Object[] args = invocation.getArgs();
MappedStatement mappedStatement = (MappedStatement) args[0];
Object parameter = args[1];
RowBounds rowBounds = (RowBounds) args[2];
ResultHandler resultHandler = (ResultHandler) args[3];
Executor executor = (Executor) invocation.getTarget();
CacheKey cacheKey;
BoundSql boundSql;
//由于逻辑关系,只会进入一次
if (args.length == 4) {
//4 个参数时
boundSql = mappedStatement.getBoundSql(parameter);
cacheKey = executor.createCacheKey(mappedStatement, parameter, rowBounds, boundSql);
} else {
//6 个参数时
cacheKey = (CacheKey) args[4];
boundSql = (BoundSql) args[5];
}
//id为执行的mapper方法的全路径名,如com.metro.dao.UserMapper.insertUser
String id = mappedStatement.getId();
//获取到原始sql语句
String sql = boundSql.getSql();
if("com.yeejoin.amos.knowledgebase.face.orm.dao.DocContentMapper.queryDocBaseInfoList".equals(id)) {
//执行结果
HashMap<String,Object> par = new LinkedHashMap<>();
if(parameter instanceof HashMap) {
par = (HashMap<String, Object>)((HashMap<?, ?>) parameter).get("paramMap");
}
LinkedHashMap<String,String> fieldsValue = (LinkedHashMap<String, String>) par.get("extraFields");
Iterator<String> iterator = fieldsValue.keySet().stream().iterator();
LinkedHashMap<String,String> fieldsValue2 = (LinkedHashMap<String, String>) par.get("extraStrFilters");
Iterator<String> iterator1 = fieldsValue2.keySet().stream().iterator();
while (iterator.hasNext()) {
String next = iterator.next();
sql = sql.replaceFirst("_field",next);
}
while (iterator1.hasNext()) {
String next = iterator1.next();
sql = sql.replaceFirst("_str",next);
}
//通过反射修改sql语句
Field field = boundSql.getClass().getDeclaredField("sql");
field.setAccessible(true);
field.set(boundSql, sql);
return executor.query(mappedStatement, parameter, rowBounds, resultHandler, cacheKey, boundSql);
} else {
return invocation.proceed();
}
}
public Object plugin(Object target) {
System.out.println("-----------------------------plugin-------------------------");
return Plugin.wrap(target, this);
}
public void setProperties(Properties properties) {
System.out.println("====setProperties======");
}
}
\ No newline at end of file
......@@ -6,38 +6,38 @@
<result column="fieldValue" property="fieldValue"/>
<result column="groupType" property="groupType"/>
</resultMap>
<select id="queryInstancePage" resultType="map">
select
d.*
from
(
select
i.INSTANCE_ID instanceId,
i.GROUP_CODE groupCode,
<foreach collection="fieldNames" item="value" index="key" separator=",">
MAX(CASE WHEN i.FIELD_NAME = #{key} THEN i.FIELD_VALUE END) as #{key}
</foreach>
from
wl_form_instance i
where i.GROUP_CODE = #{groupCode}
GROUP by
i.INSTANCE_ID)d
<if test="params != null and params.size() > 0">
where
1=1
<foreach collection="params" index="key" item="value" separator="">
<choose>
<when test="fieldNames[key] == 'like' and value !=null and value !=''">
and d.${key} like concat('%',#{value},'%')
</when>
<when test="fieldNames[key] == 'eq' and value !=null and value !=''">
and d.${key} = #{value}
</when>
</choose>
</foreach>
</if>
order by instanceId desc
</select>
<!-- <select id="queryInstancePage" resultType="map">-->
<!-- select-->
<!-- d.*-->
<!-- from-->
<!-- (-->
<!-- select-->
<!-- i.INSTANCE_ID instanceId,-->
<!-- i.GROUP_CODE groupCode,-->
<!-- <foreach collection="fieldNames" item="value" index="key" separator=",">-->
<!-- MAX(CASE WHEN i.FIELD_NAME = #{key} THEN i.FIELD_VALUE END) as #{key}-->
<!-- </foreach>-->
<!-- from-->
<!-- wl_form_instance i-->
<!-- where i.GROUP_CODE = #{groupCode}-->
<!-- GROUP by-->
<!-- i.INSTANCE_ID)d-->
<!-- <if test="params != null and params.size() > 0">-->
<!-- where-->
<!-- 1=1-->
<!-- <foreach collection="params" index="key" item="value" separator="">-->
<!-- <choose>-->
<!-- <when test="fieldNames[key] == 'like' and value !=null and value !=''">-->
<!-- and d.item like concat('%',#{value},'%')-->
<!-- </when>-->
<!-- <when test="fieldNames[key] == 'eq' and value !=null and value !=''">-->
<!-- and d.item = #{value}-->
<!-- </when>-->
<!-- </choose>-->
<!-- </foreach>-->
<!-- </if>-->
<!-- order by instanceId desc-->
<!-- </select>-->
<select id="getChildListdate" resultType="map">
SELECT getChildListdate ( #{id} ) ids
......@@ -80,10 +80,10 @@
<foreach collection="params" index="key" item="value" separator="">
<choose>
<when test="fieldNames[key] == 'like' and value !=null and value !=''">
AND d.${key} like concat('%',#{value},'%')
AND d.item like concat('%',#{value},'%')
</when>
<when test="fieldNames[key] == 'eq' and value !=null and value !=''">
AND d.${key} = #{value}
AND d.item = #{value}
</when>
</choose>
......
......@@ -84,7 +84,7 @@
(SELECT kdc.CATEGORY_NAME FROM knowledge_doc_category kdc WHERE kdc.SEQUENCE_NBR = DIRECTORY_ID) directoryName,
<if test="extraFields != null and extraFields.size > 0">
<foreach collection="extraFields" item="_field" >
${_field},
_field,
</foreach>
</if>
IFNULL(collectNum, 0) collectNum, IFNULL(quoteNum, 0) quoteNum, IFNULL(collect, "UNCOLLECT") collect
......@@ -157,7 +157,7 @@
ORG_CODE LIKE CONCAT(#{permissionFilters.orgCode}, "%")
AND AUDIT_STATUS IN
<foreach collection="permissionFilters.auditStatusList" item="auditStatus" open="(" close=")" separator=", ">
${auditStatus}
#{auditStatus}
</foreach>
)
</if>
......@@ -166,7 +166,7 @@
</if>
<if test="extraStrFilters != null and extraStrFilters.size > 0">
<foreach collection="extraStrFilters" item="str">
AND ${str}
AND _str
</foreach>
</if>
</where>
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment