mirror of
https://github.com/jeecgboot/JeecgBoot.git
synced 2026-01-02 02:25:27 +08:00
JeecgBoot 3.1.0 版本发布,基于代码生成器的企业级低代码平台
This commit is contained in:
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>jeecg-boot-base-api</artifactId>
|
||||
<groupId>org.jeecgframework.boot</groupId>
|
||||
<version>3.0</version>
|
||||
<version>3.1.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
||||
@ -37,8 +37,8 @@ public interface IBpmBaseExtAPI {
|
||||
*/
|
||||
@PostMapping(value = "/act/process/extActProcess/startMutilProcess")
|
||||
Result<String> startMutilProcess(@RequestParam("flowCode") String flowCode, @RequestParam("id") String id,
|
||||
@RequestParam("formUrl") String formUrl, @RequestParam("formUrlMobile") String formUrlMobile,
|
||||
@RequestParam("username") String username, @RequestParam("jsonData") String jsonData) throws Exception;
|
||||
@RequestParam("formUrl") String formUrl, @RequestParam("formUrlMobile") String formUrlMobile,
|
||||
@RequestParam("username") String username, @RequestParam("jsonData") String jsonData) throws Exception;
|
||||
|
||||
/**
|
||||
* 24. 流程提交接口(自定义表单设计器)
|
||||
@ -60,8 +60,8 @@ public interface IBpmBaseExtAPI {
|
||||
*/
|
||||
@PostMapping(value = "/act/process/extActProcess/startDesFormMutilProcess")
|
||||
Result<String> startDesFormMutilProcess(@RequestParam("flowCode") String flowCode, @RequestParam("id") String id,
|
||||
@RequestParam("formUrl") String formUrl, @RequestParam("formUrlMobile") String formUrlMobile,
|
||||
@RequestParam("username") String username, @RequestParam("jsonData") String jsonData) throws Exception;
|
||||
@RequestParam("formUrl") String formUrl, @RequestParam("formUrlMobile") String formUrlMobile,
|
||||
@RequestParam("username") String username, @RequestParam("jsonData") String jsonData) throws Exception;
|
||||
|
||||
/**
|
||||
* 25. 保存流程草稿箱接口(自定义开发表单、online表单)
|
||||
@ -83,7 +83,7 @@ public interface IBpmBaseExtAPI {
|
||||
*/
|
||||
@PostMapping(value = "/act/process/extActProcess/saveMutilProcessDraft")
|
||||
Result<String> saveMutilProcessDraft(@RequestParam("flowCode") String flowCode, @RequestParam("id") String id,
|
||||
@RequestParam("formUrl") String formUrl, @RequestParam("formUrlMobile") String formUrlMobile,
|
||||
@RequestParam("username") String username, @RequestParam("jsonData") String jsonData) throws Exception;
|
||||
@RequestParam("formUrl") String formUrl, @RequestParam("formUrlMobile") String formUrlMobile,
|
||||
@RequestParam("username") String username, @RequestParam("jsonData") String jsonData) throws Exception;
|
||||
|
||||
}
|
||||
|
||||
@ -15,7 +15,8 @@ import java.util.Map;
|
||||
* 【Online】Feign API接口
|
||||
*/
|
||||
@Component
|
||||
@FeignClient(contextId = "onlineBaseRemoteApi", value = ServiceNameConstants.SYSTEM_ONLINE, fallbackFactory = OnlineBaseExtAPIFallbackFactory.class)
|
||||
@FeignClient(contextId = "onlineBaseRemoteApi", value = ServiceNameConstants.SYSTEM_SERVICE, fallbackFactory = OnlineBaseExtAPIFallbackFactory.class)
|
||||
//@FeignClient(contextId = "onlineBaseRemoteApi", value = ServiceNameConstants.SYSTEM_ONLINE, fallbackFactory = OnlineBaseExtAPIFallbackFactory.class)
|
||||
public interface IOnlineBaseExtAPI {
|
||||
|
||||
/**
|
||||
|
||||
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>jeecg-boot-base-api</artifactId>
|
||||
<groupId>org.jeecgframework.boot</groupId>
|
||||
<version>3.0</version>
|
||||
<version>3.1.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
||||
@ -25,7 +25,7 @@ public interface IBpmBaseExtAPI {
|
||||
* @return
|
||||
* @throws Exception
|
||||
*/
|
||||
Result<String> startMutilProcess(String flowCode, String id, String formUrl, String formUrlMobile,String username, String jsonData) throws Exception;
|
||||
Result<String> startMutilProcess(String flowCode, String id, String formUrl, String formUrlMobile, String username, String jsonData) throws Exception;
|
||||
|
||||
/**
|
||||
* 24. 流程提交接口(自定义表单设计器)
|
||||
@ -38,7 +38,7 @@ public interface IBpmBaseExtAPI {
|
||||
* @return
|
||||
* @throws Exception
|
||||
*/
|
||||
Result<String> startDesFormMutilProcess(String flowCode, String id, String formUrl, String formUrlMobile,String username,String jsonData) throws Exception;
|
||||
Result<String> startDesFormMutilProcess(String flowCode, String id, String formUrl, String formUrlMobile, String username, String jsonData) throws Exception;
|
||||
/**
|
||||
* 25. 保存流程草稿箱接口(自定义开发表单、online表单)
|
||||
* @param flowCode 流程业务关联 例如:joa_leave_01
|
||||
@ -50,6 +50,6 @@ public interface IBpmBaseExtAPI {
|
||||
* @return
|
||||
* @throws Exception
|
||||
*/
|
||||
Result<String> saveMutilProcessDraft(String flowCode, String id, String formUrl, String formUrlMobile,String username,String jsonData) throws Exception;
|
||||
Result<String> saveMutilProcessDraft(String flowCode, String id, String formUrl, String formUrlMobile, String username, String jsonData) throws Exception;
|
||||
|
||||
}
|
||||
|
||||
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>jeecg-boot-base</artifactId>
|
||||
<groupId>org.jeecgframework.boot</groupId>
|
||||
<version>3.0</version>
|
||||
<version>3.1.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
||||
@ -4,7 +4,7 @@
|
||||
<parent>
|
||||
<groupId>org.jeecgframework.boot</groupId>
|
||||
<artifactId>jeecg-boot-base</artifactId>
|
||||
<version>3.0</version>
|
||||
<version>3.1.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
||||
@ -71,16 +71,16 @@ public class Result<T> implements Serializable {
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
public static Result<Object> ok() {
|
||||
Result<Object> r = new Result<Object>();
|
||||
public static<T> Result<T> ok() {
|
||||
Result<T> r = new Result<T>();
|
||||
r.setSuccess(true);
|
||||
r.setCode(CommonConstant.SC_OK_200);
|
||||
return r;
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
public static Result<Object> ok(String msg) {
|
||||
Result<Object> r = new Result<Object>();
|
||||
public static<T> Result<T> ok(String msg) {
|
||||
Result<T> r = new Result<T>();
|
||||
r.setSuccess(true);
|
||||
r.setCode(CommonConstant.SC_OK_200);
|
||||
r.setMessage(msg);
|
||||
@ -88,8 +88,8 @@ public class Result<T> implements Serializable {
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
public static Result<Object> ok(Object data) {
|
||||
Result<Object> r = new Result<Object>();
|
||||
public static<T> Result<T> ok(T data) {
|
||||
Result<T> r = new Result<T>();
|
||||
r.setSuccess(true);
|
||||
r.setCode(CommonConstant.SC_OK_200);
|
||||
r.setResult(data);
|
||||
@ -103,6 +103,7 @@ public class Result<T> implements Serializable {
|
||||
return r;
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
public static<T> Result<T> OK(String msg) {
|
||||
Result<T> r = new Result<T>();
|
||||
r.setSuccess(true);
|
||||
@ -139,12 +140,12 @@ public class Result<T> implements Serializable {
|
||||
return r;
|
||||
}
|
||||
|
||||
public static Result<Object> error(String msg) {
|
||||
public static<T> Result<T> error(String msg) {
|
||||
return error(CommonConstant.SC_INTERNAL_SERVER_ERROR_500, msg);
|
||||
}
|
||||
|
||||
public static Result<Object> error(int code, String msg) {
|
||||
Result<Object> r = new Result<Object>();
|
||||
public static<T> Result<T> error(int code, String msg) {
|
||||
Result<T> r = new Result<T>();
|
||||
r.setCode(code);
|
||||
r.setMessage(msg);
|
||||
r.setSuccess(false);
|
||||
@ -157,10 +158,11 @@ public class Result<T> implements Serializable {
|
||||
this.success = false;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* 无权限访问返回结果
|
||||
*/
|
||||
public static Result<Object> noauth(String msg) {
|
||||
public static<T> Result<T> noauth(String msg) {
|
||||
return error(CommonConstant.SC_JEECG_NO_AUTHZ, msg);
|
||||
}
|
||||
|
||||
|
||||
@ -88,7 +88,7 @@ public class AutoLogAspect {
|
||||
|
||||
|
||||
//设置操作类型
|
||||
if (dto.getLogType() == CommonConstant.LOG_TYPE_2) {
|
||||
if (CommonConstant.LOG_TYPE_2 == dto.getLogType()) {
|
||||
dto.setOperateType(getOperateType(methodName, syslog.operateType()));
|
||||
}
|
||||
|
||||
|
||||
@ -2,6 +2,7 @@ package org.jeecg.common.aspect;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.alibaba.fastjson.JSONObject;
|
||||
import com.alibaba.fastjson.parser.Feature;
|
||||
import com.baomidou.mybatisplus.core.metadata.IPage;
|
||||
import com.fasterxml.jackson.annotation.JsonFormat;
|
||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||
@ -18,6 +19,7 @@ import org.jeecg.common.constant.CommonConstant;
|
||||
import org.jeecg.common.system.vo.DictModel;
|
||||
import org.jeecg.common.util.oConvertUtils;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Lazy;
|
||||
import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.util.StringUtils;
|
||||
@ -38,14 +40,14 @@ import java.util.stream.Collectors;
|
||||
@Component
|
||||
@Slf4j
|
||||
public class DictAspect {
|
||||
|
||||
@Lazy
|
||||
@Autowired
|
||||
private CommonAPI commonAPI;
|
||||
@Autowired
|
||||
public RedisTemplate redisTemplate;
|
||||
|
||||
// 定义切点Pointcut
|
||||
@Pointcut("execution(public * org.jeecg.modules..*.*Controller.*(..))")
|
||||
@Pointcut("execution(public * org.jeecg.modules..*.*Controller.*(..)) || @annotation(org.jeecg.common.aspect.annotation.AutoDict)")
|
||||
public void excudeService() {
|
||||
}
|
||||
|
||||
@ -103,7 +105,10 @@ public class DictAspect {
|
||||
} catch (JsonProcessingException e) {
|
||||
log.error("json解析失败"+e.getMessage(),e);
|
||||
}
|
||||
JSONObject item = JSONObject.parseObject(json);
|
||||
//update-begin--Author:scott -- Date:20211223 ----for:【issues/3303】restcontroller返回json数据后key顺序错乱 -----
|
||||
JSONObject item = JSONObject.parseObject(json, Feature.OrderedField);
|
||||
//update-end--Author:scott -- Date:20211223 ----for:【issues/3303】restcontroller返回json数据后key顺序错乱 -----
|
||||
|
||||
//update-begin--Author:scott -- Date:20190603 ----for:解决继承实体字段无法翻译问题------
|
||||
//for (Field field : record.getClass().getDeclaredFields()) {
|
||||
// 遍历所有字段,把字典Code取出来,放到 map 里
|
||||
|
||||
@ -8,6 +8,7 @@ import org.aspectj.lang.annotation.Pointcut;
|
||||
import org.aspectj.lang.reflect.MethodSignature;
|
||||
import org.jeecg.common.api.CommonAPI;
|
||||
import org.jeecg.common.aspect.annotation.PermissionData;
|
||||
import org.jeecg.common.constant.CommonConstant;
|
||||
import org.jeecg.common.system.util.JeecgDataAutorUtils;
|
||||
import org.jeecg.common.system.util.JwtUtil;
|
||||
import org.jeecg.common.system.vo.SysPermissionDataRuleModel;
|
||||
@ -15,6 +16,7 @@ import org.jeecg.common.system.vo.SysUserCacheInfo;
|
||||
import org.jeecg.common.util.SpringContextUtils;
|
||||
import org.jeecg.common.util.oConvertUtils;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.annotation.Lazy;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
@ -31,7 +33,7 @@ import java.util.List;
|
||||
@Component
|
||||
@Slf4j
|
||||
public class PermissionDataAspect {
|
||||
|
||||
@Lazy
|
||||
@Autowired
|
||||
private CommonAPI commonAPI;
|
||||
|
||||
@ -47,11 +49,21 @@ public class PermissionDataAspect {
|
||||
Method method = signature.getMethod();
|
||||
PermissionData pd = method.getAnnotation(PermissionData.class);
|
||||
String component = pd.pageComponent();
|
||||
|
||||
String requestMethod = request.getMethod();
|
||||
String requestPath = request.getRequestURI().substring(request.getContextPath().length());
|
||||
requestPath = filterUrl(requestPath);
|
||||
log.debug("拦截请求 >> "+requestPath+";请求类型 >> "+requestMethod);
|
||||
//update-begin-author:taoyan date:20211027 for:JTC-132【online报表权限】online报表带参数的菜单配置数据权限无效
|
||||
//先判断是否online报表请求
|
||||
// TODO 参数顺序调整有隐患
|
||||
if(requestPath.indexOf(UrlMatchEnum.CGREPORT_DATA.getMatch_url())>=0){
|
||||
// 获取地址栏参数
|
||||
String urlParamString = request.getParameter(CommonConstant.ONL_REP_URL_PARAM_STR);
|
||||
if(oConvertUtils.isNotEmpty(urlParamString)){
|
||||
requestPath+="?"+urlParamString;
|
||||
}
|
||||
}
|
||||
//update-end-author:taoyan date:20211027 for:JTC-132【online报表权限】online报表带参数的菜单配置数据权限无效
|
||||
log.info("拦截请求 >> {} ; 请求类型 >> {} . ", requestPath, requestMethod);
|
||||
String username = JwtUtil.getUserNameByToken(request);
|
||||
//查询数据权限信息
|
||||
//TODO 微服务情况下也得支持缓存机制
|
||||
@ -86,6 +98,7 @@ public class PermissionDataAspect {
|
||||
* @param request
|
||||
* @return
|
||||
*/
|
||||
@Deprecated
|
||||
private String getJgAuthRequsetPath(HttpServletRequest request) {
|
||||
String queryString = request.getQueryString();
|
||||
String requestPath = request.getRequestURI();
|
||||
@ -106,6 +119,7 @@ public class PermissionDataAspect {
|
||||
return filterUrl(requestPath);
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
private boolean moHuContain(List<String> list,String key){
|
||||
for(String str : list){
|
||||
if(key.contains(str)){
|
||||
|
||||
@ -10,8 +10,8 @@ public enum UrlMatchEnum {
|
||||
CGFORM_EXCEL_DATA("/online/cgform/api/exportXls/", "/online/cgformList/"),
|
||||
CGFORM_TREE_DATA("/online/cgform/api/getTreeData/", "/online/cgformList/"),
|
||||
CGREPORT_DATA("/online/cgreport/api/getColumnsAndData/", "/online/cgreport/"),
|
||||
CGREPORT_EXCEL_DATA("/online/cgreport/api/exportXls/", "/online/cgreport/");
|
||||
|
||||
CGREPORT_EXCEL_DATA("/online/cgreport/api/exportXls/", "/online/cgreport/"),
|
||||
CGREPORT_EXCEL_DATA2("/online/cgreport/api/exportManySheetXls/", "/online/cgreport/");
|
||||
|
||||
UrlMatchEnum(String url, String match_url) {
|
||||
this.url = url;
|
||||
@ -47,8 +47,10 @@ public enum UrlMatchEnum {
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
// public static void main(String[] args) {
|
||||
public String getMatch_url() {
|
||||
return match_url;
|
||||
}
|
||||
// public static void main(String[] args) {
|
||||
// /**
|
||||
// * 比如request真实请求URL: /online/cgform/api/getData/81fcf7d8922d45069b0d5ba983612d3a
|
||||
// * 转换匹配路由URL后(对应配置的菜单路径):/online/cgformList/81fcf7d8922d45069b0d5ba983612d3a
|
||||
|
||||
@ -0,0 +1,23 @@
|
||||
package org.jeecg.common.aspect.annotation;
|
||||
|
||||
import java.lang.annotation.*;
|
||||
|
||||
/**
|
||||
* 通过此注解声明的接口,自动实现字典翻译
|
||||
*
|
||||
* @Author scott
|
||||
* @email jeecgos@163.com
|
||||
* @Date 2022年01月05日
|
||||
*/
|
||||
@Target(ElementType.METHOD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Documented
|
||||
public @interface AutoDict {
|
||||
|
||||
/**
|
||||
* 暂时无用
|
||||
* @return
|
||||
*/
|
||||
String value() default "";
|
||||
|
||||
}
|
||||
@ -0,0 +1,33 @@
|
||||
package org.jeecg.common.aspect.annotation;
|
||||
|
||||
import java.lang.annotation.*;
|
||||
|
||||
import org.jeecg.common.constant.enums.LowAppAopEnum;
|
||||
|
||||
/**
|
||||
* 自动注入low_app_id
|
||||
*
|
||||
* @Author scott
|
||||
* @email jeecgos@163.com
|
||||
* @Date 2022年01月05日
|
||||
*/
|
||||
@Target(ElementType.METHOD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Documented
|
||||
public @interface AutoLowApp {
|
||||
|
||||
/**
|
||||
* 切面类型(add、delete、db_import等其他操作)
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
LowAppAopEnum action();
|
||||
|
||||
/**
|
||||
* 业务类型(cgform等)
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
String bizType();
|
||||
|
||||
}
|
||||
@ -77,7 +77,13 @@ public interface CommonConstant {
|
||||
public static final String PREFIX_USER_TOKEN = "prefix_user_token_";
|
||||
/** Token缓存时间:3600秒即一小时 */
|
||||
public static final int TOKEN_EXPIRE_TIME = 3600;
|
||||
|
||||
|
||||
/** 登录二维码 */
|
||||
public static final String LOGIN_QRCODE_PRE = "QRCODELOGIN:";
|
||||
public static final String LOGIN_QRCODE = "LQ:";
|
||||
/** 登录二维码token */
|
||||
public static final String LOGIN_QRCODE_TOKEN = "LQT:";
|
||||
|
||||
|
||||
/**
|
||||
* 0:一级菜单
|
||||
@ -91,7 +97,7 @@ public interface CommonConstant {
|
||||
* 2:按钮权限
|
||||
*/
|
||||
public static final Integer MENU_TYPE_2 = 2;
|
||||
|
||||
|
||||
/**通告对象类型(USER:指定用户,ALL:全体用户)*/
|
||||
public static final String MSG_TYPE_UESR = "USER";
|
||||
public static final String MSG_TYPE_ALL = "ALL";
|
||||
@ -229,6 +235,9 @@ public interface CommonConstant {
|
||||
public static final String SQL_INDEX_UNIQ_SYS_USER_WORK_NO = "uniq_sys_user_work_no";
|
||||
/** sys_user 表 phone 唯一键索引 */
|
||||
public static final String SQL_INDEX_UNIQ_SYS_USER_PHONE = "uniq_sys_user_phone";
|
||||
/** 达梦数据库升提示。违反表[SYS_USER]唯一性约束 */
|
||||
public static final String SQL_INDEX_UNIQ_SYS_USER = "唯一性约束";
|
||||
|
||||
/** sys_user 表 email 唯一键索引 */
|
||||
public static final String SQL_INDEX_UNIQ_SYS_USER_EMAIL = "uniq_sys_user_email";
|
||||
/** sys_quartz_job 表 job_class_name 唯一键索引 */
|
||||
@ -239,6 +248,8 @@ public interface CommonConstant {
|
||||
public static final String SQL_INDEX_UNIQ_SYS_ROLE_CODE = "uniq_sys_role_role_code";
|
||||
/** sys_depart 表 code 唯一键索引 */
|
||||
public static final String SQL_INDEX_UNIQ_DEPART_ORG_CODE = "uniq_depart_org_code";
|
||||
/** sys_category 表 code 唯一键索引 */
|
||||
public static final String SQL_INDEX_UNIQ_CATEGORY_CODE = "idx_sc_code";
|
||||
/**
|
||||
* 在线聊天 是否为默认分组
|
||||
*/
|
||||
@ -325,4 +336,7 @@ public interface CommonConstant {
|
||||
/** 系统通告消息状态:2=已撤销 */
|
||||
String ANNOUNCEMENT_SEND_STATUS_2 = "2";
|
||||
|
||||
/**ONLINE 报表权限用 从request中获取地址栏后的参数*/
|
||||
String ONL_REP_URL_PARAM_STR="onlRepUrlParamStr";
|
||||
|
||||
}
|
||||
|
||||
@ -29,7 +29,7 @@ public class ProvinceCityArea {
|
||||
|
||||
public String getCode(String text){
|
||||
this.initAreaList();
|
||||
if(areaList!=null || areaList.size()>0){
|
||||
if(areaList!=null && areaList.size()>0){
|
||||
for(int i=areaList.size()-1;i>=0;i--){
|
||||
if(text.indexOf(areaList.get(i).getText())>=0){
|
||||
return areaList.get(i).getId();
|
||||
@ -39,6 +39,73 @@ public class ProvinceCityArea {
|
||||
return null;
|
||||
}
|
||||
|
||||
// update-begin-author:sunjianlei date:20220121 for:【JTC-704】数据导入错误 省市区组件,文件中为北京市,导入后,导为了山西省
|
||||
/**
|
||||
* 获取省市区code,精准匹配
|
||||
* @param texts 文本数组,省,市,区
|
||||
* @return 返回 省市区的code
|
||||
*/
|
||||
public String[] getCode(String[] texts) {
|
||||
if (texts == null || texts.length == 0) {
|
||||
return null;
|
||||
}
|
||||
this.initAreaList();
|
||||
if (areaList == null || areaList.size() == 0) {
|
||||
return null;
|
||||
}
|
||||
String[] codes = new String[texts.length];
|
||||
String code = null;
|
||||
for (int i = 0; i < texts.length; i++) {
|
||||
String text = texts[i];
|
||||
Area area;
|
||||
if (code == null) {
|
||||
area = getAreaByText(text);
|
||||
} else {
|
||||
area = getAreaByPidAndText(code, text);
|
||||
}
|
||||
if (area != null) {
|
||||
code = area.id;
|
||||
codes[i] = code;
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
return codes;
|
||||
}
|
||||
|
||||
/**
|
||||
* 根据text获取area
|
||||
* @param text
|
||||
* @return
|
||||
*/
|
||||
public Area getAreaByText(String text) {
|
||||
for (Area area : areaList) {
|
||||
if (text.equals(area.getText())) {
|
||||
return area;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* 通过pid获取 area 对象
|
||||
* @param pCode 父级编码
|
||||
* @param text
|
||||
* @return
|
||||
*/
|
||||
public Area getAreaByPidAndText(String pCode, String text) {
|
||||
this.initAreaList();
|
||||
if (this.areaList != null && this.areaList.size() > 0) {
|
||||
for (Area area : this.areaList) {
|
||||
if (area.getPid().equals(pCode) && area.getText().equals(text)) {
|
||||
return area;
|
||||
}
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
// update-end-author:sunjianlei date:20220121 for:【JTC-704】数据导入错误 省市区组件,文件中为北京市,导入后,导为了山西省
|
||||
|
||||
public void getAreaByCode(String code,List<String> ls){
|
||||
for(Area area: areaList){
|
||||
if(area.getId().equals(code)){
|
||||
|
||||
@ -0,0 +1,22 @@
|
||||
package org.jeecg.common.constant.enums;
|
||||
|
||||
/**
|
||||
* LowApp 切面注解枚举
|
||||
* @date 2022-1-5
|
||||
*/
|
||||
public enum LowAppAopEnum {
|
||||
|
||||
/**
|
||||
* 新增方法
|
||||
*/
|
||||
ADD,
|
||||
/**
|
||||
* 删除方法(包含单个和批量删除)
|
||||
*/
|
||||
DELETE,
|
||||
|
||||
/**
|
||||
* Online表单专用:数据库表转Online表单
|
||||
*/
|
||||
CGFORM_DB_IMPORT
|
||||
}
|
||||
@ -1,24 +1,20 @@
|
||||
package org.jeecg.common.constant.enums;
|
||||
|
||||
import org.jeecg.common.util.oConvertUtils;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* 首页自定义
|
||||
* 通过角色编码与首页组件路径配置
|
||||
* 枚举的顺序有权限高低权重作用(也就是配置多个角色,在前面的角色首页,会优先生效)
|
||||
*/
|
||||
public enum RoleIndexConfigEnum {
|
||||
/**
|
||||
* 管理员
|
||||
*/
|
||||
ADMIN("admin1", "dashboard/Analysis2"),
|
||||
/**
|
||||
* 测试
|
||||
*/
|
||||
TEST("test", "dashboard/Analysis"),
|
||||
/**
|
||||
* hr
|
||||
*/
|
||||
HR("hr", "dashboard/Analysis1");
|
||||
|
||||
ADMIN("admin", "dashboard/Analysis"),
|
||||
//TEST("test", "dashboard/IndexChart"),
|
||||
HR("hr", "dashboard/IndexBdc");
|
||||
//DM("dm", "dashboard/IndexTask"),
|
||||
|
||||
/**
|
||||
* 角色编码
|
||||
@ -44,7 +40,7 @@ public enum RoleIndexConfigEnum {
|
||||
* @param roleCode 角色编码
|
||||
* @return
|
||||
*/
|
||||
public static RoleIndexConfigEnum getEnumByCode(String roleCode) {
|
||||
private static RoleIndexConfigEnum getEnumByCode(String roleCode) {
|
||||
for (RoleIndexConfigEnum e : RoleIndexConfigEnum.values()) {
|
||||
if (e.roleCode.equals(roleCode)) {
|
||||
return e;
|
||||
@ -57,7 +53,7 @@ public enum RoleIndexConfigEnum {
|
||||
* @param roleCode 角色编码
|
||||
* @return
|
||||
*/
|
||||
public static String getIndexByCode(String roleCode) {
|
||||
private static String getIndexByCode(String roleCode) {
|
||||
for (RoleIndexConfigEnum e : RoleIndexConfigEnum.values()) {
|
||||
if (e.roleCode.equals(roleCode)) {
|
||||
return e.componentUrl;
|
||||
@ -67,11 +63,10 @@ public enum RoleIndexConfigEnum {
|
||||
}
|
||||
|
||||
public static String getIndexByRoles(List<String> roles) {
|
||||
for (String role : roles) {
|
||||
for (RoleIndexConfigEnum e : RoleIndexConfigEnum.values()) {
|
||||
if (e.roleCode.equals(role)) {
|
||||
return e.componentUrl;
|
||||
}
|
||||
String[] rolesArray = roles.toArray(new String[roles.size()]);
|
||||
for (RoleIndexConfigEnum e : RoleIndexConfigEnum.values()) {
|
||||
if (oConvertUtils.isIn(e.roleCode,rolesArray)){
|
||||
return e.componentUrl;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
|
||||
@ -180,8 +180,15 @@ public class JeecgController<T, S extends IService<T>> {
|
||||
//update-end-author:taoyan date:20190528 for:批量插入数据
|
||||
return Result.ok("文件导入成功!数据行数:" + list.size());
|
||||
} catch (Exception e) {
|
||||
log.error(e.getMessage(), e);
|
||||
return Result.error("文件导入失败:" + e.getMessage());
|
||||
//update-begin-author:taoyan date:20211124 for: 导入数据重复增加提示
|
||||
String msg = e.getMessage();
|
||||
log.error(msg, e);
|
||||
if(msg!=null && msg.indexOf("Duplicate entry")>=0){
|
||||
return Result.error("文件导入失败:有重复数据!");
|
||||
}else{
|
||||
return Result.error("文件导入失败:" + e.getMessage());
|
||||
}
|
||||
//update-end-author:taoyan date:20211124 for: 导入数据重复增加提示
|
||||
} finally {
|
||||
try {
|
||||
file.getInputStream().close();
|
||||
|
||||
@ -25,7 +25,6 @@ import org.jeecg.common.util.oConvertUtils;
|
||||
import org.springframework.util.NumberUtils;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.baomidou.mybatisplus.annotation.DbType;
|
||||
import com.baomidou.mybatisplus.annotation.TableField;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
||||
|
||||
@ -145,20 +144,23 @@ public class QueryGenerator {
|
||||
//区间查询
|
||||
doIntervalQuery(queryWrapper, parameterMap, type, name, column);
|
||||
//判断单值 参数带不同标识字符串 走不同的查询
|
||||
//TODO 这种前后带逗号的支持分割后模糊查询需要否 使多选字段的查询生效
|
||||
//TODO 这种前后带逗号的支持分割后模糊查询(多选字段查询生效) 示例:,1,3,
|
||||
if (null != value && value.toString().startsWith(COMMA) && value.toString().endsWith(COMMA)) {
|
||||
String multiLikeval = value.toString().replace(",,", COMMA);
|
||||
String[] vals = multiLikeval.substring(1, multiLikeval.length()).split(COMMA);
|
||||
final String field = oConvertUtils.camelToUnderline(column);
|
||||
if(vals.length>1) {
|
||||
queryWrapper.and(j -> {
|
||||
log.info("---查询过滤器,Query规则---field:{}, rule:{}, value:{}", field, "like", vals[0]);
|
||||
j = j.like(field,vals[0]);
|
||||
for (int k=1;k<vals.length;k++) {
|
||||
j = j.or().like(field,vals[k]);
|
||||
log.info("---查询过滤器,Query规则 .or()---field:{}, rule:{}, value:{}", field, "like", vals[k]);
|
||||
}
|
||||
//return j;
|
||||
});
|
||||
}else {
|
||||
log.info("---查询过滤器,Query规则---field:{}, rule:{}, value:{}", field, "like", vals[0]);
|
||||
queryWrapper.and(j -> j.like(field,vals[0]));
|
||||
}
|
||||
}else {
|
||||
@ -224,7 +226,7 @@ public class QueryGenerator {
|
||||
if(parameterMap!=null&& parameterMap.containsKey(ORDER_TYPE)) {
|
||||
order = parameterMap.get(ORDER_TYPE)[0];
|
||||
}
|
||||
log.info("排序规则>>列:" + column + ",排序方式:" + order);
|
||||
log.debug("排序规则>>列:" + column + ",排序方式:" + order);
|
||||
if (oConvertUtils.isNotEmpty(column) && oConvertUtils.isNotEmpty(order)) {
|
||||
//字典字段,去掉字典翻译文本后缀
|
||||
if(column.endsWith(CommonConstant.DICT_TEXT_SUFFIX)) {
|
||||
@ -270,10 +272,21 @@ public class QueryGenerator {
|
||||
if (conditions == null || conditions.size() == 0) {
|
||||
return;
|
||||
}
|
||||
log.info("---高级查询参数-->" + conditions.toString());
|
||||
// update-begin-author:sunjianlei date:20220119 for: 【JTC-573】 过滤空条件查询,防止 sql 拼接多余的 and
|
||||
List<QueryCondition> filterConditions = conditions.stream().filter(
|
||||
rule -> oConvertUtils.isNotEmpty(rule.getField())
|
||||
&& oConvertUtils.isNotEmpty(rule.getRule())
|
||||
&& oConvertUtils.isNotEmpty(rule.getVal())
|
||||
).collect(Collectors.toList());
|
||||
if (filterConditions.size() == 0) {
|
||||
return;
|
||||
}
|
||||
// update-end-author:sunjianlei date:20220119 for: 【JTC-573】 过滤空条件查询,防止 sql 拼接多余的 and
|
||||
log.info("---高级查询参数-->" + filterConditions);
|
||||
|
||||
queryWrapper.and(andWrapper -> {
|
||||
for (int i = 0; i < conditions.size(); i++) {
|
||||
QueryCondition rule = conditions.get(i);
|
||||
for (int i = 0; i < filterConditions.size(); i++) {
|
||||
QueryCondition rule = filterConditions.get(i);
|
||||
if (oConvertUtils.isNotEmpty(rule.getField())
|
||||
&& oConvertUtils.isNotEmpty(rule.getRule())
|
||||
&& oConvertUtils.isNotEmpty(rule.getVal())) {
|
||||
@ -324,7 +337,7 @@ public class QueryGenerator {
|
||||
//update-end-author:taoyan date:20201228 for: 【高级查询】 oracle 日期等于查询报错
|
||||
|
||||
// 如果拼接方式是OR,就拼接OR
|
||||
if (MatchTypeEnum.OR == matchType && i < (conditions.size() - 1)) {
|
||||
if (MatchTypeEnum.OR == matchType && i < (filterConditions.size() - 1)) {
|
||||
andWrapper.or();
|
||||
}
|
||||
}
|
||||
@ -457,15 +470,37 @@ public class QueryGenerator {
|
||||
|
||||
private static void addQueryByRule(QueryWrapper<?> queryWrapper,String name,String type,String value,QueryRuleEnum rule) throws ParseException {
|
||||
if(oConvertUtils.isNotEmpty(value)) {
|
||||
Object temp;
|
||||
//update-begin--Author:sunjianlei Date:20220104 for:【JTC-409】修复逗号分割情况下没有转换类型,导致类型严格的数据库查询报错 -------------------
|
||||
// 针对数字类型字段,多值查询
|
||||
if(value.indexOf(COMMA)!=-1){
|
||||
temp = value;
|
||||
if(value.contains(COMMA)){
|
||||
Object[] temp = Arrays.stream(value.split(COMMA)).map(v -> {
|
||||
try {
|
||||
return QueryGenerator.parseByType(v, type, rule);
|
||||
} catch (ParseException e) {
|
||||
e.printStackTrace();
|
||||
return v;
|
||||
}
|
||||
}).toArray();
|
||||
addEasyQuery(queryWrapper, name, rule, temp);
|
||||
return;
|
||||
}
|
||||
Object temp = QueryGenerator.parseByType(value, type, rule);
|
||||
addEasyQuery(queryWrapper, name, rule, temp);
|
||||
//update-end--Author:sunjianlei Date:20220104 for:【JTC-409】修复逗号分割情况下没有转换类型,导致类型严格的数据库查询报错 -------------------
|
||||
}
|
||||
}
|
||||
|
||||
switch (type) {
|
||||
/**
|
||||
* 根据类型转换给定的值
|
||||
* @param value
|
||||
* @param type
|
||||
* @param rule
|
||||
* @return
|
||||
* @throws ParseException
|
||||
*/
|
||||
private static Object parseByType(String value, String type, QueryRuleEnum rule) throws ParseException {
|
||||
Object temp;
|
||||
switch (type) {
|
||||
case "class java.lang.Integer":
|
||||
temp = Integer.parseInt(value);
|
||||
break;
|
||||
@ -490,9 +525,8 @@ public class QueryGenerator {
|
||||
default:
|
||||
temp = value;
|
||||
break;
|
||||
}
|
||||
addEasyQuery(queryWrapper, name, rule, temp);
|
||||
}
|
||||
return temp;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -527,12 +561,12 @@ public class QueryGenerator {
|
||||
* @param rule 查询规则
|
||||
* @param value 查询条件值
|
||||
*/
|
||||
private static void addEasyQuery(QueryWrapper<?> queryWrapper, String name, QueryRuleEnum rule, Object value) {
|
||||
public static void addEasyQuery(QueryWrapper<?> queryWrapper, String name, QueryRuleEnum rule, Object value) {
|
||||
if (value == null || rule == null || oConvertUtils.isEmpty(value)) {
|
||||
return;
|
||||
}
|
||||
name = oConvertUtils.camelToUnderline(name);
|
||||
log.info("--查询规则-->"+name+" "+rule.getValue()+" "+value);
|
||||
log.info("---查询过滤器,Query规则---field:{}, rule:{}, value:{}",name,rule.getValue(),value);
|
||||
switch (rule) {
|
||||
case GT:
|
||||
queryWrapper.gt(name, value);
|
||||
@ -555,7 +589,7 @@ public class QueryGenerator {
|
||||
break;
|
||||
case IN:
|
||||
if(value instanceof String) {
|
||||
queryWrapper.in(name, (Object[])value.toString().split(","));
|
||||
queryWrapper.in(name, (Object[])value.toString().split(COMMA));
|
||||
}else if(value instanceof String[]) {
|
||||
queryWrapper.in(name, (Object[]) value);
|
||||
}
|
||||
|
||||
@ -34,8 +34,8 @@ import org.jeecg.common.util.oConvertUtils;
|
||||
**/
|
||||
public class JwtUtil {
|
||||
|
||||
// Token过期时间30分钟(用户登录过期时间是此时间的两倍,以token在reids缓存时间为准)
|
||||
public static final long EXPIRE_TIME = 30 * 60 * 1000;
|
||||
// Token过期时间2小时(用户登录过期时间是此时间的两倍,以token在reids缓存时间为准)
|
||||
public static final long EXPIRE_TIME = 2 * 60 * 60 * 1000;
|
||||
|
||||
/**
|
||||
*
|
||||
@ -155,7 +155,6 @@ public class JwtUtil {
|
||||
* @param user
|
||||
* @return
|
||||
*/
|
||||
//TODO 急待改造 sckjkdsjsfjdk
|
||||
public static String getUserSystemData(String key,SysUserCacheInfo user) {
|
||||
if(user==null) {
|
||||
user = JeecgDataAutorUtils.loadUserInfo();
|
||||
|
||||
@ -39,5 +39,11 @@ public class DictModel implements Serializable{
|
||||
public String getTitle() {
|
||||
return this.text;
|
||||
}
|
||||
/**
|
||||
* 特殊用途: vue3 Select组件
|
||||
*/
|
||||
public String getLabel() {
|
||||
return this.text;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@ -14,6 +14,7 @@ import org.springframework.jdbc.datasource.DriverManagerDataSource;
|
||||
import org.springframework.util.FileCopyUtils;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.sql.DataSource;
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.File;
|
||||
@ -282,4 +283,39 @@ public class CommonUtils {
|
||||
return DB_TYPE;
|
||||
|
||||
}
|
||||
/**
|
||||
* 获取服务器地址
|
||||
*
|
||||
* @param request
|
||||
* @return
|
||||
*/
|
||||
public static String getBaseUrl(HttpServletRequest request) {
|
||||
//1.【兼容】兼容微服务下的 base path-------
|
||||
String x_gateway_base_path = request.getHeader("X_GATEWAY_BASE_PATH");
|
||||
if(oConvertUtils.isNotEmpty(x_gateway_base_path)){
|
||||
log.info("x_gateway_base_path = "+ x_gateway_base_path);
|
||||
return x_gateway_base_path;
|
||||
}
|
||||
//2.【兼容】SSL认证之后,request.getScheme()获取不到https的问题
|
||||
// https://blog.csdn.net/weixin_34376986/article/details/89767950
|
||||
String scheme = request.getHeader("X-Forwarded-Scheme");
|
||||
if(oConvertUtils.isEmpty(scheme)){
|
||||
scheme = request.getScheme();
|
||||
}
|
||||
|
||||
//3.常规操作
|
||||
String serverName = request.getServerName();
|
||||
int serverPort = request.getServerPort();
|
||||
String contextPath = request.getContextPath();
|
||||
|
||||
//返回 host domain
|
||||
String baseDomainPath = null;
|
||||
if(80 == serverPort){
|
||||
baseDomainPath = scheme + "://" + serverName + contextPath ;
|
||||
}else{
|
||||
baseDomainPath = scheme + "://" + serverName + ":" + serverPort + contextPath ;
|
||||
}
|
||||
log.info("-----Common getBaseUrl----- : " + baseDomainPath);
|
||||
return baseDomainPath;
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,7 @@
|
||||
package org.jeecg.common.util;
|
||||
|
||||
import io.minio.*;
|
||||
import io.minio.http.Method;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.jeecg.common.util.filter.FileTypeFilter;
|
||||
import org.jeecg.common.util.filter.StrAttackFilter;
|
||||
@ -158,9 +159,11 @@ public class MinioUtil {
|
||||
public static String getObjectURL(String bucketName, String objectName, Integer expires) {
|
||||
initMinio(minioUrl, minioName,minioPass);
|
||||
try{
|
||||
//update-begin---author:liusq Date:20220121 for:获取文件外链报错提示method不能为空,导致文件下载和预览失败----
|
||||
GetPresignedObjectUrlArgs objectArgs = GetPresignedObjectUrlArgs.builder().object(objectName)
|
||||
.bucket(bucketName)
|
||||
.expiry(expires).build();
|
||||
.expiry(expires).method(Method.GET).build();
|
||||
//update-begin---author:liusq Date:20220121 for:获取文件外链报错提示method不能为空,导致文件下载和预览失败----
|
||||
String url = minioClient.getPresignedObjectUrl(objectArgs);
|
||||
return URLDecoder.decode(url,"UTF-8");
|
||||
}catch (Exception e){
|
||||
|
||||
@ -17,7 +17,7 @@ public class SqlInjectionUtil {
|
||||
* (上线修改值 20200501,同步修改前端的盐值)
|
||||
*/
|
||||
private final static String TABLE_DICT_SIGN_SALT = "20200501";
|
||||
private final static String xssStr = "'|and |exec |insert |select |delete |update |drop |count |chr |mid |master |truncate |char |declare |;|or |+";
|
||||
private final static String xssStr = "and |exec |insert |select |delete |update |drop |count |chr |mid |master |truncate |char |declare |;|or |+|user()";
|
||||
|
||||
/*
|
||||
* 针对表字典进行额外的sign签名校验(增加安全机制)
|
||||
|
||||
@ -25,7 +25,7 @@ public class DbTypeUtils {
|
||||
dialectMap.put("postgresql", "org.hibernate.dialect.PostgreSQLDialect"); //1 --
|
||||
dialectMap.put("sqlserver2005", "org.hibernate.dialect.SQLServer2005Dialect");
|
||||
dialectMap.put("sqlserver", "org.hibernate.dialect.SQLServerDialect"); //1
|
||||
dialectMap.put("dm", "org.hibernate.dialect.OracleDialect");//达梦数据库 [国产] 1--
|
||||
dialectMap.put("dm", "org.hibernate.dialect.DmDialect");//达梦数据库 [国产] 1--
|
||||
dialectMap.put("xugu", "org.hibernate.dialect.HSQLDialect"); //虚谷数据库
|
||||
dialectMap.put("kingbasees", "org.hibernate.dialect.PostgreSQLDialect"); //人大金仓 [国产] 1
|
||||
dialectMap.put("phoenix", "org.hibernate.dialect.HSQLDialect"); // Phoenix HBase数据库
|
||||
|
||||
@ -258,6 +258,9 @@ public class OssBootUtil {
|
||||
newBucket = bucket;
|
||||
}
|
||||
initOSS(endPoint, accessKeyId, accessKeySecret);
|
||||
//update-begin---author:liusq Date:20220120 for:替换objectName前缀,防止key不一致导致获取不到文件----
|
||||
objectName = OssBootUtil.replacePrefix(objectName,bucket);
|
||||
//update-end---author:liusq Date:20220120 for:替换objectName前缀,防止key不一致导致获取不到文件----
|
||||
OSSObject ossObject = ossClient.getObject(newBucket,objectName);
|
||||
inputStream = new BufferedInputStream(ossObject.getObjectContent());
|
||||
}catch (Exception e){
|
||||
@ -266,14 +269,14 @@ public class OssBootUtil {
|
||||
return inputStream;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取文件流
|
||||
* @param objectName
|
||||
* @return
|
||||
*/
|
||||
public static InputStream getOssFile(String objectName){
|
||||
return getOssFile(objectName,null);
|
||||
}
|
||||
///**
|
||||
// * 获取文件流
|
||||
// * @param objectName
|
||||
// * @return
|
||||
// */
|
||||
//public static InputStream getOssFile(String objectName){
|
||||
// return getOssFile(objectName,null);
|
||||
//}
|
||||
|
||||
/**
|
||||
* 获取文件外链
|
||||
@ -285,6 +288,9 @@ public class OssBootUtil {
|
||||
public static String getObjectURL(String bucketName, String objectName, Date expires) {
|
||||
initOSS(endPoint, accessKeyId, accessKeySecret);
|
||||
try{
|
||||
//update-begin---author:liusq Date:20220120 for:替换objectName前缀,防止key不一致导致获取不到文件----
|
||||
objectName = OssBootUtil.replacePrefix(objectName,bucketName);
|
||||
//update-end---author:liusq Date:20220120 for:替换objectName前缀,防止key不一致导致获取不到文件----
|
||||
if(ossClient.doesObjectExist(bucketName,objectName)){
|
||||
URL url = ossClient.generatePresignedUrl(bucketName,objectName,expires);
|
||||
return URLDecoder.decode(url.toString(),"UTF-8");
|
||||
@ -334,5 +340,27 @@ public class OssBootUtil {
|
||||
return FILE_URL;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 替换前缀,防止key不一致导致获取不到文件
|
||||
* @param objectName 文件上传路径 key
|
||||
* @param customBucket 自定义桶
|
||||
* @date 2022-01-20
|
||||
* @author lsq
|
||||
* @return
|
||||
*/
|
||||
private static String replacePrefix(String objectName,String customBucket){
|
||||
log.info("------replacePrefix---替换前---objectName:{}",objectName);
|
||||
if(oConvertUtils.isNotEmpty(staticDomain)){
|
||||
objectName= objectName.replace(staticDomain+"/","");
|
||||
}else{
|
||||
String newBucket = bucketName;
|
||||
if(oConvertUtils.isNotEmpty(customBucket)){
|
||||
newBucket = customBucket;
|
||||
}
|
||||
String path ="https://" + newBucket + "." + endPoint + "/";
|
||||
objectName = objectName.replace(path,"");
|
||||
}
|
||||
log.info("------replacePrefix---替换后---objectName:{}",objectName);
|
||||
return objectName;
|
||||
}
|
||||
}
|
||||
@ -1,6 +1,10 @@
|
||||
package org.jeecg.config;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
|
||||
import org.jeecg.common.api.CommonAPI;
|
||||
import org.jeecg.common.system.vo.DictModel;
|
||||
import org.jeecg.common.util.oConvertUtils;
|
||||
@ -8,9 +12,7 @@ import org.jeecgframework.dict.service.AutoPoiDictServiceI;
|
||||
import org.springframework.context.annotation.Lazy;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
|
||||
/**
|
||||
* 描述:AutoPoi Excel注解支持字典参数设置
|
||||
@ -25,6 +27,9 @@ import java.util.List;
|
||||
@Slf4j
|
||||
@Service
|
||||
public class AutoPoiDictConfig implements AutoPoiDictServiceI {
|
||||
final static String EXCEL_SPLIT_TAG = "_";
|
||||
final static String TEMP_EXCEL_SPLIT_TAG = "---";
|
||||
|
||||
@Lazy
|
||||
@Resource
|
||||
private CommonAPI commonAPI;
|
||||
@ -53,7 +58,14 @@ public class AutoPoiDictConfig implements AutoPoiDictServiceI {
|
||||
}
|
||||
for (DictModel t : dictList) {
|
||||
if(t!=null){
|
||||
dictReplaces.add(t.getText() + "_" + t.getValue());
|
||||
//update-begin---author:scott Date:20211220 for:[issues/I4MBB3]@Excel dicText字段的值有下划线时,导入功能不能正确解析---
|
||||
if(t.getValue().contains(EXCEL_SPLIT_TAG)){
|
||||
String val = t.getValue().replace(EXCEL_SPLIT_TAG,TEMP_EXCEL_SPLIT_TAG);
|
||||
dictReplaces.add(t.getText() + EXCEL_SPLIT_TAG + val);
|
||||
}else{
|
||||
dictReplaces.add(t.getText() + EXCEL_SPLIT_TAG + t.getValue());
|
||||
}
|
||||
//update-end---author:20211220 Date:20211220 for:[issues/I4MBB3]@Excel dicText字段的值有下划线时,导入功能不能正确解析---
|
||||
}
|
||||
}
|
||||
if (dictReplaces != null && dictReplaces.size() != 0) {
|
||||
|
||||
@ -1,5 +1,6 @@
|
||||
package org.jeecg.config;
|
||||
|
||||
import org.jeecg.config.vo.Shiro;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@ -14,6 +15,15 @@ public class JeeccgBaseConfig {
|
||||
* 是否启用安全模式
|
||||
*/
|
||||
private Boolean safeMode = false;
|
||||
/**
|
||||
* shiro拦截排除
|
||||
*/
|
||||
private Shiro shiro;
|
||||
/**
|
||||
* 签名密钥串(字典等敏感接口)
|
||||
* @TODO 降低使用成本加的默认值,实际以 yml配置 为准
|
||||
*/
|
||||
private String signatureSecret = "dd05f1c54d63749eda95f9fa6d49v442a";
|
||||
|
||||
public Boolean getSafeMode() {
|
||||
return safeMode;
|
||||
@ -22,4 +32,20 @@ public class JeeccgBaseConfig {
|
||||
public void setSafeMode(Boolean safeMode) {
|
||||
this.safeMode = safeMode;
|
||||
}
|
||||
|
||||
public String getSignatureSecret() {
|
||||
return signatureSecret;
|
||||
}
|
||||
|
||||
public void setSignatureSecret(String signatureSecret) {
|
||||
this.signatureSecret = signatureSecret;
|
||||
}
|
||||
|
||||
public Shiro getShiro() {
|
||||
return shiro;
|
||||
}
|
||||
|
||||
public void setShiro(Shiro shiro) {
|
||||
this.shiro = shiro;
|
||||
}
|
||||
}
|
||||
|
||||
@ -20,11 +20,11 @@ public class StaticConfig {
|
||||
@Value(value = "${spring.mail.username}")
|
||||
private String emailFrom;
|
||||
|
||||
/**
|
||||
* 签名密钥串
|
||||
*/
|
||||
@Value(value = "${jeecg.signatureSecret}")
|
||||
private String signatureSecret;
|
||||
// /**
|
||||
// * 签名密钥串
|
||||
// */
|
||||
// @Value(value = "${jeecg.signatureSecret}")
|
||||
// private String signatureSecret;
|
||||
|
||||
|
||||
/*@Bean
|
||||
|
||||
@ -1,3 +1,4 @@
|
||||
|
||||
package org.jeecg.config.shiro;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
@ -15,6 +16,7 @@ import org.crazycake.shiro.RedisClusterManager;
|
||||
import org.crazycake.shiro.RedisManager;
|
||||
import org.jeecg.common.constant.CommonConstant;
|
||||
import org.jeecg.common.util.oConvertUtils;
|
||||
import org.jeecg.config.JeeccgBaseConfig;
|
||||
import org.jeecg.config.shiro.filters.CustomShiroFilterFactoryBean;
|
||||
import org.jeecg.config.shiro.filters.JwtFilter;
|
||||
import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;
|
||||
@ -43,13 +45,12 @@ import java.util.*;
|
||||
@Configuration
|
||||
public class ShiroConfig {
|
||||
|
||||
@Value("${jeecg.shiro.excludeUrls}")
|
||||
private String excludeUrls;
|
||||
@Resource
|
||||
LettuceConnectionFactory lettuceConnectionFactory;
|
||||
@Autowired
|
||||
private Environment env;
|
||||
|
||||
@Autowired
|
||||
JeeccgBaseConfig jeeccgBaseConfig;
|
||||
|
||||
/**
|
||||
* Filter Chain定义说明
|
||||
@ -64,8 +65,9 @@ public class ShiroConfig {
|
||||
shiroFilterFactoryBean.setSecurityManager(securityManager);
|
||||
// 拦截器
|
||||
Map<String, String> filterChainDefinitionMap = new LinkedHashMap<String, String>();
|
||||
if(oConvertUtils.isNotEmpty(excludeUrls)){
|
||||
String[] permissionUrl = excludeUrls.split(",");
|
||||
String shiroExcludeUrls = jeeccgBaseConfig.getShiro().getExcludeUrls();
|
||||
if(oConvertUtils.isNotEmpty(shiroExcludeUrls)){
|
||||
String[] permissionUrl = shiroExcludeUrls.split(",");
|
||||
for(String url : permissionUrl){
|
||||
filterChainDefinitionMap.put(url,"anon");
|
||||
}
|
||||
@ -89,6 +91,12 @@ public class ShiroConfig {
|
||||
filterChainDefinitionMap.put("/sys/common/static/**", "anon");//图片预览 &下载文件不限制token
|
||||
filterChainDefinitionMap.put("/sys/common/pdf/**", "anon");//pdf预览
|
||||
filterChainDefinitionMap.put("/generic/**", "anon");//pdf预览需要文件
|
||||
|
||||
filterChainDefinitionMap.put("/sys/getLoginQrcode/**", "anon"); //登录二维码
|
||||
filterChainDefinitionMap.put("/sys/getQrcodeToken/**", "anon"); //监听扫码
|
||||
filterChainDefinitionMap.put("/sys/checkAuth", "anon"); //授权接口排除
|
||||
|
||||
|
||||
filterChainDefinitionMap.put("/", "anon");
|
||||
filterChainDefinitionMap.put("/doc.html", "anon");
|
||||
filterChainDefinitionMap.put("/**/*.js", "anon");
|
||||
@ -130,6 +138,9 @@ public class ShiroConfig {
|
||||
filterChainDefinitionMap.put("/newsWebsocket/**", "anon");//CMS模块
|
||||
filterChainDefinitionMap.put("/vxeSocket/**", "anon");//JVxeTable无痕刷新示例
|
||||
|
||||
//wps
|
||||
filterChainDefinitionMap.put("/v1/**","anon");
|
||||
|
||||
//性能监控 TODO 存在安全漏洞泄露TOEKN(durid连接池也有)
|
||||
filterChainDefinitionMap.put("/actuator/**", "anon");
|
||||
|
||||
|
||||
@ -137,9 +137,12 @@ public class ShiroRealm extends AuthorizingRealm {
|
||||
if(oConvertUtils.isNotEmpty(userTenantIds)){
|
||||
String contextTenantId = TenantContext.getTenant();
|
||||
if(oConvertUtils.isNotEmpty(contextTenantId) && !"0".equals(contextTenantId)){
|
||||
if(String.join(",",userTenantIds).indexOf(contextTenantId)<0){
|
||||
//update-begin-author:taoyan date:20211227 for: /issues/I4O14W 用户租户信息变更判断漏洞
|
||||
String[] arr = userTenantIds.split(",");
|
||||
if(!oConvertUtils.isIn(contextTenantId, arr)){
|
||||
throw new AuthenticationException("用户租户信息变更,请重新登陆!");
|
||||
}
|
||||
//update-end-author:taoyan date:20211227 for: /issues/I4O14W 用户租户信息变更判断漏洞
|
||||
}
|
||||
}
|
||||
//update-end-author:taoyan date:20210609 for:校验用户的tenant_id和前端传过来的是否一致
|
||||
|
||||
@ -5,7 +5,7 @@ import lombok.extern.slf4j.Slf4j;
|
||||
import org.jeecg.common.exception.JeecgBootException;
|
||||
import org.jeecg.common.util.SpringContextUtils;
|
||||
import org.jeecg.common.util.oConvertUtils;
|
||||
import org.jeecg.config.StaticConfig;
|
||||
import org.jeecg.config.JeeccgBaseConfig;
|
||||
import org.springframework.util.DigestUtils;
|
||||
import org.springframework.util.StringUtils;
|
||||
|
||||
@ -46,8 +46,9 @@ public class SignUtil {
|
||||
params.remove("_t");
|
||||
String paramsJsonStr = JSONObject.toJSONString(params);
|
||||
log.info("Param paramsJsonStr : {}", paramsJsonStr);
|
||||
StaticConfig staticConfig = SpringContextUtils.getBean(StaticConfig.class);
|
||||
String signatureSecret = staticConfig.getSignatureSecret();
|
||||
//设置签名秘钥
|
||||
JeeccgBaseConfig jeeccgBaseConfig = SpringContextUtils.getBean(JeeccgBaseConfig.class);
|
||||
String signatureSecret = jeeccgBaseConfig.getSignatureSecret();
|
||||
if(oConvertUtils.isEmpty(signatureSecret) || signatureSecret.contains("${")){
|
||||
throw new JeecgBootException("签名密钥 ${jeecg.signatureSecret} 缺少配置 !!");
|
||||
}
|
||||
|
||||
@ -0,0 +1,18 @@
|
||||
package org.jeecg.config.vo;
|
||||
|
||||
/**
|
||||
* @Description: TODO
|
||||
* @author: scott
|
||||
* @date: 2022年01月21日 14:23
|
||||
*/
|
||||
public class Shiro {
|
||||
private String excludeUrls = "";
|
||||
|
||||
public String getExcludeUrls() {
|
||||
return excludeUrls;
|
||||
}
|
||||
|
||||
public void setExcludeUrls(String excludeUrls) {
|
||||
this.excludeUrls = excludeUrls;
|
||||
}
|
||||
}
|
||||
@ -4,7 +4,7 @@
|
||||
<parent>
|
||||
<groupId>org.jeecgframework.boot</groupId>
|
||||
<artifactId>jeecg-boot-base</artifactId>
|
||||
<version>3.0</version>
|
||||
<version>3.1.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
<description>公共模块</description>
|
||||
|
||||
@ -96,4 +96,8 @@ public interface CacheConstant {
|
||||
* online图表
|
||||
*/
|
||||
public static final String ONLINE_GRAPH = "sys:cache:online:graph";
|
||||
/**
|
||||
* 拖拽页面信息缓存
|
||||
*/
|
||||
public static final String DRAG_PAGE_CACHE = "drag:cache:page";
|
||||
}
|
||||
|
||||
@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<artifactId>jeecg-boot-parent</artifactId>
|
||||
<groupId>org.jeecgframework.boot</groupId>
|
||||
<version>3.0</version>
|
||||
<version>3.1.0</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
|
||||
Reference in New Issue
Block a user