|
|
@@ -1,9 +1,16 @@
|
|
|
package com.jzg.commons.config;
|
|
|
|
|
|
import com.alibaba.fastjson.JSONObject;
|
|
|
+import com.baomidou.mybatisplus.extension.plugins.handler.MultiDataPermissionHandler;
|
|
|
import com.baomidou.mybatisplus.extension.plugins.inner.InnerInterceptor;
|
|
|
import com.jzg.commons.core.base.BaseController;
|
|
|
import com.jzg.commons.entity.properties.DataScopeProperties;
|
|
|
+import net.sf.jsqlparser.JSQLParserException;
|
|
|
+import net.sf.jsqlparser.expression.Expression;
|
|
|
+import net.sf.jsqlparser.expression.ExpressionVisitor;
|
|
|
+import net.sf.jsqlparser.parser.CCJSqlParserUtil;
|
|
|
+import net.sf.jsqlparser.parser.SimpleNode;
|
|
|
+import net.sf.jsqlparser.schema.Table;
|
|
|
import org.apache.ibatis.executor.Executor;
|
|
|
import org.apache.ibatis.executor.statement.StatementHandler;
|
|
|
import org.apache.ibatis.mapping.MappedStatement;
|
|
|
@@ -17,23 +24,25 @@ import org.apache.ibatis.session.SqlSessionFactory;
|
|
|
import org.redisson.api.RedissonClient;
|
|
|
import org.springframework.beans.factory.annotation.Autowired;
|
|
|
import org.springframework.beans.factory.annotation.Value;
|
|
|
+import org.springframework.core.annotation.Order;
|
|
|
import org.springframework.stereotype.Component;
|
|
|
|
|
|
import java.lang.reflect.Field;
|
|
|
import java.sql.Connection;
|
|
|
import java.sql.SQLException;
|
|
|
-import java.util.ArrayList;
|
|
|
-import java.util.List;
|
|
|
-import java.util.Properties;
|
|
|
+import java.util.*;
|
|
|
+import java.util.regex.Matcher;
|
|
|
+import java.util.regex.Pattern;
|
|
|
|
|
|
/**
|
|
|
* 数据权限拦截器
|
|
|
*/
|
|
|
+@Order(2)
|
|
|
@Intercepts({
|
|
|
@Signature(type = Executor.class, method = "query", args = {MappedStatement.class, Object.class, RowBounds.class, ResultHandler.class}),
|
|
|
// @Signature(type = Executor.class, method = "update", args = {MappedStatement.class, Object.class})
|
|
|
})
|
|
|
-public class DataPermissionInterceptor implements InnerInterceptor {
|
|
|
+ public class DataPermissionInterceptor implements MultiDataPermissionHandler {
|
|
|
|
|
|
private List<String> ignoredTables;
|
|
|
|
|
|
@@ -52,8 +61,6 @@ public class DataPermissionInterceptor implements InnerInterceptor {
|
|
|
this.dataScopeProperties = dataScopeProperties;
|
|
|
}
|
|
|
|
|
|
-
|
|
|
-
|
|
|
private boolean shouldIgnoreTable(String sql) {
|
|
|
for (String table : dataScopeProperties.getTables()) {
|
|
|
if (sql.toLowerCase().contains(table.toLowerCase())) {
|
|
|
@@ -63,55 +70,73 @@ public class DataPermissionInterceptor implements InnerInterceptor {
|
|
|
return false;
|
|
|
}
|
|
|
|
|
|
+ private String getTableName(Table table){
|
|
|
+ return String.valueOf(table.getAlias() == null ? table.getName() : table.getAlias().getName());
|
|
|
+ }
|
|
|
+
|
|
|
@Override
|
|
|
- public void beforeQuery(Executor executor, MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql) throws SQLException {
|
|
|
-
|
|
|
- try {
|
|
|
- if(shouldIgnoreTable(boundSql.getSql())) {
|
|
|
- String currentUserDeptId = baseController.getUserDeptId();
|
|
|
- String userDataScope = baseController.getUserDataScope();
|
|
|
- JSONObject dataScope = JSONObject.parseObject(userDataScope);
|
|
|
- List<String> deptIds = new ArrayList<>();
|
|
|
- StringBuilder additionalSql = new StringBuilder();
|
|
|
- //如果数据权限为空 并且用户名为admin 则不做数据权限
|
|
|
- if(dataScope.isEmpty() && baseController.getUserName().equals("admin")){
|
|
|
- return;
|
|
|
- }
|
|
|
- if (dataScope.getString("dataMark").equals("2")) {
|
|
|
- additionalSql.append(" AND dept_id in (");
|
|
|
- additionalSql.append("select id from sys_dept where route like '"+currentUserDeptId+"%'");
|
|
|
- additionalSql.append(")");
|
|
|
- }else {
|
|
|
- deptIds = dataScope.getObject("deptIds", List.class);
|
|
|
- additionalSql.append(" AND dept_id in (");
|
|
|
- deptIds.forEach(deptId -> {
|
|
|
- additionalSql.append("'" + deptId + "',");
|
|
|
- });
|
|
|
- additionalSql.deleteCharAt(additionalSql.length() - 1);
|
|
|
- additionalSql.append(")");
|
|
|
- }
|
|
|
-
|
|
|
- // 获取原始 SQL
|
|
|
- String sql = boundSql.getSql();
|
|
|
-
|
|
|
- if (sql.toLowerCase().contains("select")) {
|
|
|
- sql += additionalSql.toString();
|
|
|
- Field field = null;
|
|
|
- try {
|
|
|
- field = BoundSql.class.getDeclaredField("sql");
|
|
|
- } catch (NoSuchFieldException e) {
|
|
|
- throw new RuntimeException(e);
|
|
|
- }
|
|
|
- field.setAccessible(true);
|
|
|
- try {
|
|
|
- field.set(boundSql, sql);
|
|
|
- } catch (IllegalAccessException e) {
|
|
|
- throw new RuntimeException(e);
|
|
|
- }
|
|
|
- }
|
|
|
+ public Expression getSqlSegment(Table table, Expression where, String mappedStatementId) {
|
|
|
+
|
|
|
+ String currentUserDeptId = baseController.getUserDeptId();
|
|
|
+ String userDataScope = baseController.getUserDataScope();
|
|
|
+ JSONObject dataScope = JSONObject.parseObject(userDataScope);
|
|
|
+ //如果用户名为admin 不做数据权限
|
|
|
+
|
|
|
+ if (dataScope == null || (dataScope.isEmpty() && baseController.getUserName().equals("admin"))) {
|
|
|
+ return where;
|
|
|
+ }
|
|
|
+ StringBuilder additionalSql = new StringBuilder();
|
|
|
+ String tableName = getTableName(table);
|
|
|
+ if(!shouldIgnoreTable(table.getName())) {
|
|
|
+ String fieldName = table.getName().equals("sys_dept") ? "id" : "dept_id";
|
|
|
+ List<String> deptIds = new ArrayList<>();
|
|
|
+ if (dataScope.getString("dataMark").equals("2")) {
|
|
|
+ additionalSql.append(tableName).append(".").append(fieldName).append(" in (");
|
|
|
+ additionalSql.append("select id from sys_dept where route like '").append(currentUserDeptId).append("%'");
|
|
|
+ additionalSql.append(")");
|
|
|
+ } else {
|
|
|
+ deptIds = dataScope.getObject("deptIds", List.class);
|
|
|
+ additionalSql.append(tableName).append(".").append(fieldName).append(" in (");
|
|
|
+ deptIds.forEach(deptId -> {
|
|
|
+ additionalSql.append("'" + deptId + "',");
|
|
|
+ });
|
|
|
+ additionalSql.deleteCharAt(additionalSql.length() - 1);
|
|
|
+ additionalSql.append(")");
|
|
|
+ }
|
|
|
+ try {
|
|
|
+ return CCJSqlParserUtil.parseCondExpression(additionalSql.toString());
|
|
|
+ } catch (JSQLParserException e) {
|
|
|
+ throw new RuntimeException(e);
|
|
|
}
|
|
|
- }catch (Exception e){
|
|
|
- System.out.printf(e.getMessage());
|
|
|
+ }
|
|
|
+ return null;
|
|
|
+ }
|
|
|
+
|
|
|
+ private static class SqlExpression implements Expression {
|
|
|
+ private final String sql;
|
|
|
+
|
|
|
+ public SqlExpression(String sql) {
|
|
|
+ this.sql = sql;
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public String toString() {
|
|
|
+ return sql;
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public void accept(ExpressionVisitor expressionVisitor) {
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public SimpleNode getASTNode() {
|
|
|
+ return null;
|
|
|
+ }
|
|
|
+
|
|
|
+ @Override
|
|
|
+ public void setASTNode(SimpleNode node) {
|
|
|
+
|
|
|
}
|
|
|
}
|
|
|
}
|