Merge branch 'feature/REQ-2545' into 'master'

Feature/req 2545

See merge request universal/infrastructure/backend/tyr!74
This commit is contained in:
李龙 2024-07-22 02:41:03 +00:00
commit 08834424bc
130 changed files with 6874 additions and 651 deletions

View File

@ -22,7 +22,7 @@ public enum AttrPermissionEnum {
UNIT_COOPERATE_SUBORDINATE(7, "本单位及下级协同(直属+合作)单位数据"),
UNIT_ALL_SUBORDINATE(8, "本单位及以下协同(直属+合作)单位数据"),
WORKSPACE(9, "本项目数据"),
WORKSPACE(9, "本项目数据"),
EQUAL_TO_ROW(10, "同行级数据权限"),
;
private final Integer value;

View File

@ -25,6 +25,8 @@ public enum FeatureResourceType {
COMPONENT(4, "组件"),
ROOT(5, "ROOT"),
GROUP(6, "分组"),
// 用户pc端菜单直接的分割分组线
MENU_PARTITION_GROUP(7, "菜单分割分组"),
;
private static final Map<Integer, FeatureResourceType> MAPPING = new HashMap<>();

View File

@ -0,0 +1,28 @@
package cn.axzo.tyr.client.common.enums;
import com.baomidou.mybatisplus.annotation.EnumValue;
import lombok.AllArgsConstructor;
import lombok.Getter;
/**
* @author likunpeng
* @date 2024/7/2
*/
@Getter
@AllArgsConstructor
public enum PageElementFeatureResourceRelationTypeEnum {
/**
* 默认类型
*/
DEFAULT(0, "默认类型"),
/**
* 页面路由
*/
PAGE_ROUTE(1, "页面路由"),
;
@EnumValue
private final Integer value;
private final String desc;
}

View File

@ -0,0 +1,23 @@
package cn.axzo.tyr.client.common.enums;
import lombok.AllArgsConstructor;
import lombok.Getter;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/18
*/
@Getter
@AllArgsConstructor
public enum PageElementTypeEnum {
PAGE("PAGE", "页面"),
COMPONENT("COMPONENT", "组件"),
;
private final String code;
private final String desc;
}

View File

@ -25,7 +25,7 @@ public enum RowPermissionEnum {
UNIT_COOPERATE_SUBORDINATE(7, "本单位及下级协同(直属+合作)单位数据"),
UNIT_ALL_SUBORDINATE(8, "本单位及以下协同(直属+合作)单位数据"),
WORKSPACE(9, "本项目数据"),
WORKSPACE(9, "本项目数据"),
;

View File

@ -1,12 +1,13 @@
package cn.axzo.tyr.client.feign;
import cn.axzo.framework.domain.web.result.ApiResult;
import cn.axzo.tyr.client.model.req.DeleteFeatureResourceReq;
import cn.axzo.tyr.client.model.req.FeatureResourceTreeSaveReq;
import cn.axzo.tyr.client.model.req.GetFeatureResourceTreeReq;
import cn.axzo.tyr.client.model.req.ResourceSyncReq;
import cn.axzo.tyr.client.model.req.FeatureResourceTreeSaveReq;
import cn.axzo.tyr.client.model.res.FeatureResourceDetailResp;
import cn.axzo.tyr.client.model.res.FeatureResourceTreeNode;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
@ -14,6 +15,7 @@ import org.springframework.web.bind.annotation.RequestParam;
import javax.validation.Valid;
import java.util.List;
import java.util.Map;
/**
* 功能资源API接口
@ -44,7 +46,7 @@ public interface FeatureResourceApi {
/** 删除菜单/页面/组件 **/
@PostMapping("/api/featureResource/delete")
ApiResult<Void> deleteFeatureResource(@RequestParam Long featureId, @RequestParam Long operatorId);
ApiResult<Void> deleteFeatureResource(@Validated @RequestBody DeleteFeatureResourceReq req);
/** 重排序菜单/页面/组件 **/
@ -58,4 +60,8 @@ public interface FeatureResourceApi {
/** 从基准环境查询功能资源树 **/
@PostMapping("/api/featureResource/getBaseTree")
ApiResult<List<FeatureResourceTreeNode>> getBaseTree(@RequestBody @Valid GetFeatureResourceTreeReq req);
/** 通过featureResourceIds查询对应的featureCode **/
@PostMapping("/api/featureResource/listFeatureCodeByFeatureResourceIds")
ApiResult<Map<Long, String>> listFeatureCodeByFeatureResourceIds(@RequestParam List<Long> featureResourceIds);
}

View File

@ -0,0 +1,44 @@
package cn.axzo.tyr.client.feign;
import cn.axzo.framework.domain.web.result.ApiPageResult;
import cn.axzo.framework.domain.web.result.ApiResult;
import cn.axzo.tyr.client.model.req.*;
import cn.axzo.tyr.client.model.res.GetUserHasPermissionPageElementResp;
import cn.axzo.tyr.client.model.res.PageElementResp;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import javax.validation.Valid;
import java.util.List;
/**
* 页面及元素相关接口
*
* @author likunpeng
* @version 1.0
* @date 2024/6/18
*/
@FeignClient(name = "tyr", url = "${axzo.service.tyr:http://tyr:8080}")
public interface PageElementApi {
/** 页面及元素上报 **/
@PostMapping("/api/pageElement/report")
ApiResult<Void> report(@RequestBody @Valid PageElementReportReq req);
/** 查询页面资源 **/
@PostMapping("/api/pageElement/getPageElement")
ApiResult<List<PageElementResp>> getPageElement(@RequestBody @Valid GetPageElementReq req);
/** 编辑页面、页面组件的元素 **/
@PostMapping("/api/pageElement/modifyPageElementRelation")
ApiResult<Void> modifyPageElementRelation(@RequestBody @Valid ModifyPageElementRelationDTO req);
/** 分页查询页面资源 **/
@PostMapping("/api/pageElement/page")
ApiPageResult<PageElementResp> page(@RequestBody @Valid PageQueryElementReq req);
/** 根据用户传入的页面code查询用户有权限的元素code **/
@PostMapping("/api/pageElement/getUserHasPermissionPageElement")
ApiResult<GetUserHasPermissionPageElementResp> getUserHasPermissionPageElement(@RequestBody @Valid GetUserHasPermissionPageElementReq req);
}

View File

@ -5,10 +5,12 @@ import cn.axzo.tyr.client.model.req.NavTreeReq;
import cn.axzo.tyr.client.model.req.PagePermissionReq;
import cn.axzo.tyr.client.model.req.PagePermissionResp;
import cn.axzo.tyr.client.model.req.PermissionCheckReq;
import cn.axzo.tyr.client.model.req.TreePermissionReq;
import cn.axzo.tyr.client.model.req.TreeProductFeatureResourceReq;
import cn.axzo.tyr.client.model.res.FeatureResourceDTO;
import cn.axzo.tyr.client.model.res.NavTreeResp;
import cn.axzo.tyr.client.model.res.ProductFeatureResourceResp;
import cn.axzo.tyr.client.model.res.TreePermissionResp;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.PostMapping;
@ -29,6 +31,7 @@ public interface PermissionQueryApi {
/** 返回有权限的导航菜单页面 **/
@PostMapping(value = "/api/v3/permission/query/getNavTree")
@Deprecated
ApiResult<List<NavTreeResp>> getNavTree(@RequestBody @Valid NavTreeReq req);
/** 页面权限详情:页面自身及所有下级 **/
@ -54,4 +57,14 @@ public interface PermissionQueryApi {
*/
@PostMapping(value = "/api/v3/productPermission/list")
ApiResult<List<FeatureResourceDTO>> listFeatureResource(@RequestBody @Validated TreeProductFeatureResourceReq request);
/**
* 查询用户有权限的菜单资源树
* getNavTree已经废弃不在原方法上改的原因OMS端现在没有保存角色的菜单权限且不通用不能传入指定类型的节点和树种某个节点下的子节点
* 待oms端把菜单的权限点保存且使用前端的页面元素后就可以切换这个接口
* @param req
* @return
*/
@PostMapping(value = "/api/v3/permission/featureResource/tree")
ApiResult<List<TreePermissionResp>> treePermission(@RequestBody @Validated TreePermissionReq req);
}

View File

@ -2,14 +2,7 @@ package cn.axzo.tyr.client.feign;
import cn.axzo.framework.domain.web.result.ApiPageResult;
import cn.axzo.framework.domain.web.result.ApiResult;
import cn.axzo.tyr.client.model.product.ProductAddReq;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationSearchReq;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationUpdateReq;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationVO;
import cn.axzo.tyr.client.model.product.ProductSearchListReq;
import cn.axzo.tyr.client.model.product.ProductSearchPageReq;
import cn.axzo.tyr.client.model.product.ProductUpdateReq;
import cn.axzo.tyr.client.model.product.ProductVO;
import cn.axzo.tyr.client.model.product.*;
import cn.axzo.tyr.client.model.req.ProductSaveReq;
import cn.axzo.tyr.client.model.req.UpdateProductStatusReq;
import cn.axzo.tyr.client.model.res.GovernmentTerminalResp;
@ -155,4 +148,10 @@ public interface ProductApi {
*/
@GetMapping("api/auth/product/getWorkspaceProduct")
ApiResult<WorkspaceProductResp> getWorkspaceProduct(@RequestParam @NotNull(message = "workspaceType不能为空") String workspaceType);
/**
* 获取指定ID的产品详细信息
*/
@PostMapping("api/auth/product/getDetail")
ApiResult<ProductVO> getDetail(@Validated @RequestBody ProductDetailReq req);
}

View File

@ -5,6 +5,8 @@ import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.SuperBuilder;
import java.util.List;
@Data
@SuperBuilder
@NoArgsConstructor
@ -25,7 +27,7 @@ public class BaseFeatureResourceDO {
private Integer featureType;
/** 资源编码 **/
private String featureCode;
private String uniCode;
/** 状态 0-隐藏 1-显示 **/
private Integer status;
@ -38,4 +40,10 @@ public class BaseFeatureResourceDO {
/** 组件类型 **/
private Integer componentType;
/** 组件元素的code列表 */
private List<String> pageElementCodes;
/** 图片资源对象 **/
private FeatureResourceExtraDO extra;
}

View File

@ -0,0 +1,30 @@
package cn.axzo.tyr.client.model.base;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.Serializable;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/24
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class FeatureResourceExtraDO implements Serializable {
/**
* 选中的图标
*/
private String activeIcon;
/**
* 更多图标
*/
private String moreIcon;
}

View File

@ -15,7 +15,7 @@ public class AttributePermissionBO {
private Integer sort; // 序号
private String attrName; //字段名
private String attrCode; // 字段code
private Integer visibilityScope; // 字段值查看范围 1:仅本人数据 2:本人及下属数据 3:仅本部门数据 4:本部门及以下数据 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据 10:同行级数据权限
private Integer visibilityScope; // 字段值查看范围 1:仅本人数据 2:本人及下属数据 3:仅本部门数据 4:本部门及以下数据 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据 10:同行级数据权限
private Integer isUnmaskable; // 是否可脱敏 1-不可操作脱敏 2-可操作脱敏
private Integer isEditable; // 是否可编辑 1-不可编辑 2-可编辑
}

View File

@ -42,7 +42,7 @@ public class DataObjectRuleBO {
/**
* 行级数据权限单选 1:仅本人数据 2:本人及下属数据 3:仅本部门数据 4:本部门及以下数据
* 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据
* 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据
*/
private Integer rowPermission;
/**

View File

@ -33,7 +33,7 @@ public class DefaultDataObjectRuleBO {
/**
* 行级数据权限单选 1:仅本人数据 2:本人及下属数据 3:仅本部门数据 4:本部门及以下数据
* 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据
* 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据
*/
private Integer rowPermission;
/**

View File

@ -23,9 +23,9 @@ public enum DictWorkSpaceTypeEnum {
ENT("ent", "企业工作台", 7,1, "单位租户"),
/**
* 项目工作台
* 项目工作台
*/
PROJ("proj", "项目工作台",1,2, "项目租户"),
PROJ("proj", "项目工作台",1,2, "项目租户"),
GOVERNMENT("gov", "政务监管平台",3,3, "政务监管平台"),

View File

@ -9,7 +9,7 @@ import java.util.Map;
@Getter
@AllArgsConstructor
public enum PermissionScopeType {
WORKSPACE("workspace", "项目"),
WORKSPACE("workspace", "项目"),
OU ("ou", "单位"),
;

View File

@ -0,0 +1,34 @@
package cn.axzo.tyr.client.model.product;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import javax.validation.constraints.Min;
import javax.validation.constraints.NotNull;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/20
*/
@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
public class ProductDetailReq {
/**
* 产品ID
*/
@NotNull(message = "产品ID不能为空")
@Min(value = 1, message = "")
private Long productId;
/**
* 是否查询功能权限点
*/
@Builder.Default
private Boolean queryFeatureScope = Boolean.FALSE;
}

View File

@ -34,4 +34,8 @@ public class ProductFeatureRelationSearchReq {
*/
private String dictCode;
/**
* 关系类型
*/
private Integer type;
}

View File

@ -40,4 +40,9 @@ public class ProductFeatureRelationVO {
* 权限点 ID
*/
private Long featureId;
/**
* 关联类型0saas_feature,1:saas_feature_resource
*/
private Integer type;
}

View File

@ -8,6 +8,7 @@ import lombok.experimental.Accessors;
import java.util.Date;
import java.util.List;
import java.util.Set;
/**
* 产品模型
@ -144,6 +145,16 @@ public class ProductVO {
*/
private List<FeatureScope> featureScopes;
/**
* 新老产品标记前端确认查询权限树的接口0旧权限1新权限树
*/
private Integer relationType;
/**
* 功能范围非政务产品
*/
private List<ProductFeatureRelation> relations;
@Data
@Builder
@NoArgsConstructor
@ -209,4 +220,26 @@ public class ProductVO {
*/
private String featureResourceName;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class ProductFeatureRelation {
/**
* 单位类型
*/
private Long dictCodeId;
/**
* 总数
*/
private Integer totalCount;
/**
* 勾选的最末级 feature ID 集合
*/
private List<Long> featureIds;
}
}

View File

@ -0,0 +1,21 @@
package cn.axzo.tyr.client.model.req;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import javax.validation.constraints.NotNull;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class DeleteFeatureResourceReq {
@NotNull(message = "featureId不能为空")
private Long featureId;
@NotNull(message = "operatorId不能为空")
private Long operatorId;
}

View File

@ -0,0 +1,22 @@
package cn.axzo.tyr.client.model.req;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.Set;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class FeatureIdPair {
/**
* 区分新老菜单资源树
*/
private Integer type;
private Set<Long> featureIds;
}

View File

@ -29,10 +29,17 @@ public class FeatureRoleRelationReq {
/** 功能Id **/
private Long featureId;
/**
* 菜单资源的类型
*/
private Integer featureType;
/** 应用的角色Id列表 **/
private List<Long> roleIds;
/** 授权类型 0-全部角色 1-指定角色 **/
private Integer authType;
private String terminal;
}
}

View File

@ -27,4 +27,16 @@ public class GetFeatureResourceTreeReq {
/** feature类型列表 **/
private List<Integer> featureTypes;
/**
* 应用范围(原租户类型)1:企业租户 2;项目租户
* 只有页面和应用会配置应用范围
*/
private Long workspaceType;
/**
* 是否过滤掉空菜单没有子页面和组件的菜单过滤不返回
*/
@Builder.Default
private Boolean needFilterBlankMenu = Boolean.FALSE;
}

View File

@ -0,0 +1,43 @@
package cn.axzo.tyr.client.model.req;
import com.google.common.collect.Lists;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import javax.validation.constraints.Min;
import javax.validation.constraints.NotNull;
import java.util.List;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/14
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class GetPageElementReq {
/**
* 页面的featureResourceId
*/
@NotNull(message = "页面的featureResourceId不能为空")
@Min(value = 1, message = "页面的featureResourceId有误")
private Long featureResourceId;
/**
* 是否只查询组件已选择的元素
*/
@Builder.Default
private Boolean querySelectedOnly = Boolean.FALSE;
/**
* 查询的关联类型默认全查
* 如果要过滤页面路由的relationTypes传[0]
*/
@Builder.Default
private List<Integer> relationTypes = Lists.newArrayList(0, 1);
}

View File

@ -0,0 +1,45 @@
package cn.axzo.tyr.client.model.req;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import javax.validation.constraints.Min;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/17
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class GetUserHasPermissionPageElementReq {
/** 页面的元素 **/
@NotBlank(message = "页面的元素不能为空")
private String pageElementCode;
/** 登录端 **/
@NotBlank(message = "登录端不能为空")
private String terminal;
/** 人员ID **/
@NotNull(message = "人员ID不能为空")
@Min(value = 1, message = "人员ID有误")
private Long personId;
/** 单位ID **/
@NotNull(message = "单位ID不能为空")
@Min(value = 1, message = "单位ID有误")
private Long ouId;
/** 租户ID **/
@NotNull(message = "租户ID不能为空")
@Min(value = 1, message = "租户ID有误")
private Long workspaceId;
}

View File

@ -1,8 +1,6 @@
package cn.axzo.tyr.client.model.req;
import cn.axzo.framework.auth.domain.TerminalInfo;
import cn.axzo.tyr.client.common.enums.WorkspaceJoinType;
import cn.axzo.tyr.client.model.enums.FeatureType;
import cn.axzo.tyr.client.model.enums.IdentityType;
import cn.axzo.tyr.client.model.res.IdentityAuthRes;
import cn.hutool.core.collection.CollectionUtil;
@ -14,18 +12,11 @@ import lombok.NoArgsConstructor;
import javax.validation.Valid;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.stream.Collectors;
import static cn.axzo.tyr.client.common.enums.WorkspaceJoinType.ENT_GROUP;
import static cn.axzo.tyr.client.common.enums.WorkspaceJoinType.ENT_TEAM;
import static cn.axzo.tyr.client.common.enums.WorkspaceJoinType.PROJ_GROUP;
import static cn.axzo.tyr.client.common.enums.WorkspaceJoinType.PROJ_TEAM;
/**
* @author tanjie@axzo.cn
* @date 2023/10/13 15:23
@ -74,6 +65,12 @@ public class IdentityAuthReq {
@Builder.Default
private boolean useCache = true;
/**
* 权限点类型0saas_feature,1:saas_feature_resource
* 为了兼容第三方调用查询用户的权限点会把新旧权限点都查询出来灰度端历史版本由使用方传入版本
*/
private Integer type;
public IdentityAuthRes toEmpty() {
IdentityAuthRes result = new IdentityAuthRes();
result.setIdentity(this.getIdentityId());
@ -91,7 +88,6 @@ public class IdentityAuthReq {
return result;
}
public void distinctOUWorkspacePair() {
if (CollectionUtil.isEmpty(this.workspaceOusPairs)) {
return;

View File

@ -0,0 +1,46 @@
package cn.axzo.tyr.client.model.req;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/19
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class ModifyPageElementRelationDTO {
/**
* 操作人ID
*/
private Long operatorId;
/**
* 组件所属端
*/
private String terminal;
/**
* 组件code
*/
private String featureResourceUniCode;
/**
* 页面元素编码列表
*/
private List<String> pageElementCodes;
/**
* 绑定关系
*/
@Builder.Default
private Integer relationType = 0;
}

View File

@ -0,0 +1,40 @@
package cn.axzo.tyr.client.model.req;
import cn.axzo.foundation.dao.support.wrapper.CriteriaField;
import cn.axzo.foundation.dao.support.wrapper.Operator;
import cn.axzo.foundation.page.IPageReq;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
import java.util.Set;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class PageElementFeatureResourceRelationReq implements IPageReq {
@CriteriaField(ignore = true)
Integer page;
@CriteriaField(ignore = true)
Integer pageSize;
/**
* 排序使用示例createTime__DESC
*/
@CriteriaField(ignore = true)
List<String> sort;
@CriteriaField(field = "featureResourceUniCode", operator = Operator.IN)
private List<String> featureResourceUniCodes;
@CriteriaField(field = "pageElementCode", operator = Operator.IN)
private Set<String> pageElementCodes;
@CriteriaField(field = "terminal", operator = Operator.EQ)
private String terminal;
}

View File

@ -0,0 +1,66 @@
package cn.axzo.tyr.client.model.req;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotEmpty;
import java.util.List;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/14
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class PageElementReportReq {
/**
*
*/
@NotBlank(message = "端信息不能为空")
private String terminal;
/**
* 页面元素列表
*/
@NotEmpty(message = "页面元素不能为空")
private List<PageElement> pageElements;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class PageElement {
/**
* 元素编码
*/
private String code;
/**
* 元素名称
*/
private String name;
/**
* 元素类型PAGE:页面COMPONENT:页面里的组件
*/
private String type;
/**
* 路由地址
*/
private String linkUrl;
/**
* 子元素只包含一级
*/
private List<PageElement> children;
}
}

View File

@ -0,0 +1,61 @@
package cn.axzo.tyr.client.model.req;
import cn.axzo.foundation.dao.support.wrapper.CriteriaField;
import cn.axzo.foundation.dao.support.wrapper.Operator;
import cn.axzo.foundation.page.IPageReq;
import cn.axzo.tyr.client.common.enums.FeatureResourceType;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class PagePgroupPermissionRelationReq implements IPageReq {
@CriteriaField(ignore = true)
Integer page;
@CriteriaField(ignore = true)
Integer pageSize;
/**
* 排序使用示例createTime__DESC
*/
@CriteriaField(ignore = true)
List<String> sort;
@CriteriaField(field = "id", operator = Operator.IN)
private List<Long> ids;
@CriteriaField(field = "groupId", operator = Operator.IN)
private List<Long> groupIds;
@CriteriaField(field = "featureId", operator = Operator.IN)
private List<Long> featureIds;
@CriteriaField(field = "type", operator = Operator.EQ)
private Integer type;
/**
* 查询菜单树节点类型
*/
@CriteriaField(ignore = true)
private List<FeatureResourceType> featureResourceTypes;
/**
* 查询权限点时会根据端过滤增加效率目前只有CMS端的新版本才冗余了端
*/
@CriteriaField(ignore = true)
private String terminal;
/**
* 新老版本两个情况可以配对查询
*/
@CriteriaField(ignore = true)
private List<FeatureIdPair> featureIdPairs;
}

View File

@ -0,0 +1,33 @@
package cn.axzo.tyr.client.model.req;
import cn.axzo.foundation.dao.support.wrapper.CriteriaField;
import cn.axzo.foundation.dao.support.wrapper.Operator;
import cn.axzo.foundation.page.IPageReq;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class PageProductFeatureRelationReq implements IPageReq {
@CriteriaField(ignore = true)
Integer page;
@CriteriaField(ignore = true)
Integer pageSize;
/**
* 排序使用示例createTime__DESC
*/
@CriteriaField(ignore = true)
List<String> sort;
@CriteriaField(field = "id", operator = Operator.IN)
private List<Long> ids;
}

View File

@ -0,0 +1,49 @@
package cn.axzo.tyr.client.model.req;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import javax.validation.constraints.NotBlank;
import java.util.List;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/14
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class PageQueryElementReq {
/**
*
*/
@NotBlank(message = "端不能为空")
private String terminal;
/**
* 页面元素组件类型
*/
private List<String> elementTypes;
/**
* 搜索条件
*/
private String searchKey;
/**
* 页码
*/
@Builder.Default
private Long page = 1L;
/**
* 每页大小
*/
@Builder.Default
private Long pageSize = 100L;
}

View File

@ -0,0 +1,81 @@
package cn.axzo.tyr.client.model.req;
import cn.axzo.foundation.dao.support.wrapper.CriteriaField;
import cn.axzo.foundation.dao.support.wrapper.Operator;
import cn.axzo.foundation.page.IPageReq;
import cn.axzo.foundation.page.PageResp;
import cn.axzo.tyr.client.common.enums.FeatureResourceType;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.Collections;
import java.util.List;
import java.util.Set;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class PageSaasFeatureResourceReq implements IPageReq {
@CriteriaField(ignore = true)
Integer page;
@CriteriaField(ignore = true)
Integer pageSize;
/**
* 排序使用示例createTime__DESC
*/
@CriteriaField(ignore = true)
List<String> sort;
@CriteriaField(field = "id", operator = Operator.IN)
private List<Long> ids;
/**
* 授权类型0-全部角色 1-指定角色
* FeatureResourceAuthType.ALL_ROLE
*/
@CriteriaField(field = "authType", operator = Operator.EQ)
private Integer authType;
/**
* 资源所属端
*/
@CriteriaField(field = "terminal", operator = Operator.EQ)
private String terminal;
@CriteriaField(ignore = true)
private Long parentId;
@CriteriaField(field = "featureType", operator = Operator.IN)
private List<Integer> featureResourceTypes;
@CriteriaField(field = "path", operator = Operator.SW)
private String path;
/**
* CMS端saas_feature_resource.feature_codes已经废弃后续其他端也会这样迁移
* 新的存在saas_page_element_feature_resource_relation
*/
@CriteriaField(ignore = true)
private Boolean needFeatureCodes;
@CriteriaField(field = "uniCode", operator = Operator.IN)
private Set<String> uniCodes;
@CriteriaField(ignore = true)
private Set<String> paths;
public PageResp toEmpty() {
return PageResp.builder()
.current(this.getPage())
.size(this.getPageSize())
.total(0)
.data(Collections.emptyList())
.build();
}
}

View File

@ -34,6 +34,8 @@ public class PermissionCheckReq {
@NotNull(message = "租户ID不能为空")
private Long workspaceId;
/** 登录端 **/
/**
* 登录端历史的cms和cmpcm端没有给端给了会有问题
*/
private String terminal;
}

View File

@ -11,6 +11,7 @@ import javax.validation.constraints.Min;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;
import java.util.List;
import java.util.Set;
/**
* @author likunpeng
@ -163,5 +164,26 @@ public class ProductSaveReq {
* 政务端featureResourceId
*/
private List<Long> governmentFeatureResourceIds;
/**
* 产品与功能点的关联关系
*/
private List<ProductFeatureRelation> relations;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class ProductFeatureRelation {
/**
* 单位类型
*/
private Long dictCodeId;
/**
* 勾选的最末级 feature ID 集合
*/
private Set<Long> featureIds;
}
}

View File

@ -17,7 +17,7 @@ public class QuerySaasRoleGroupReq {
private List<Long> ids;
/**
* 项目id(不传或者传-1查询的是标准分组)
* 项目id(不传或者传-1查询的是标准分组)
*/
private List<Long> workspaceIds;

View File

@ -0,0 +1,49 @@
package cn.axzo.tyr.client.model.req;
import cn.axzo.tyr.client.common.enums.FeatureResourceType;
import cn.axzo.tyr.client.model.base.WorkspaceOUPair;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
import java.util.List;
@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
public class TreePermissionReq {
@NotNull(message = "人员ID不能为空")
private Long personId;
/**
*
*/
@NotNull(message = "端不能为空")
private String terminal;
/**
* 项目与企业
*/
@NotEmpty(message = "项目与企业对不能为空")
private List<WorkspaceOUPair> workspaceOUPairs;
/**
* 查询菜单树节点类型
*/
private List<FeatureResourceType> featureResourceTypes;
/**
* 菜单节点的uniCode
*/
private String uniCode;
/**
* 是否需要返回权限码
*/
private boolean needFeatureCodes;
}

View File

@ -25,7 +25,7 @@ public class TreeRoleReq {
private Boolean isDisplay;
/**
* 项目id(不传或者传-1查询的是标准分组)
* 项目id(不传或者传-1查询的是标准分组)
*/
private List<Long> workspaceIds;

View File

@ -1,5 +1,6 @@
package cn.axzo.tyr.client.model.res;
import cn.axzo.tyr.client.model.base.FeatureResourceExtraDO;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@ -7,6 +8,7 @@ import lombok.experimental.SuperBuilder;
import java.io.Serializable;
import java.util.Date;
import java.util.List;
/**
* 功能资源DTO
@ -110,7 +112,7 @@ public class FeatureResourceDTO implements Serializable {
/**
* 扩展字段
*/
private String extra;
private FeatureResourceExtraDO extra;
/**
* 授权类型0-全部角色 1-指定角色
@ -151,4 +153,9 @@ public class FeatureResourceDTO implements Serializable {
* 唯一编码用于pre环境菜单同步
*/
private String uniCode;
/**
* 页面元素对象
*/
private List<PageElementBasicDTO> pageElements;
}

View File

@ -0,0 +1,25 @@
package cn.axzo.tyr.client.model.res;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/17
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class GetUserHasPermissionPageElementResp {
/**
* 页面元素的elementCodes
*/
private List<String> pageElementCodes;
}

View File

@ -1,9 +1,11 @@
package cn.axzo.tyr.client.model.res;
import cn.axzo.tyr.client.model.enums.IdentityType;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
import java.util.Set;
/**
@ -66,8 +68,22 @@ public class ListPermissionFromRoleGroupResp {
*/
private Set<Long> simpleFeatureInfos;
/**
* 权限点及是否为新旧权限点
*/
private Set<FeatureInfo> featureInfos;
@Data
@Builder
@AllArgsConstructor
@NoArgsConstructor
public static class FeatureInfo {
private Long featureId;
/** 0saas_feature,1:saas_feature_resource **/
private Integer relationType;
}
}

View File

@ -0,0 +1,44 @@
package cn.axzo.tyr.client.model.res;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/19
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class PageElementBasicDTO {
/**
* 页面元素ID
*/
private Long id;
/**
* 组件编码
*/
private String uniCode;
/**
* 页面元素编码
*/
private String code;
/**
* 页面元素名称
*/
private String name;
/**
* 绑定关系
* @see cn.axzo.tyr.client.common.enums.PageElementFeatureResourceRelationTypeEnum
*/
private Integer relationType;
}

View File

@ -0,0 +1,60 @@
package cn.axzo.tyr.client.model.res;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/14
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class PageElementResp {
/**
* 元素ID
*/
private Long id;
/**
* 元素的组编码
*/
private String groupCode;
/**
* 元素编码
*/
private String code;
/**
* 元素名称
*/
private String name;
/**
* 元素类型
*/
private String type;
/**
* 页面路由地址
*/
private String linkUrl;
/**
* 是否已勾选
*/
private Boolean selected;
/**
* 子元素只包含一级
*/
private List<PageElementResp> children;
}

View File

@ -0,0 +1,146 @@
package cn.axzo.tyr.client.model.res;
import cn.axzo.tyr.client.model.base.FeatureResourceExtraDO;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.extension.handlers.FastjsonTypeHandler;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.Date;
import java.util.Set;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class SaasFeatureResourceResp {
private Long id;
private Date createAt;
private Date updateAt;
/**
* 资源编码-权限码
*/
private Set<String> featureCodes;
/**
* 资源名称
*/
private String featureName;
/**
* 资源类型1-菜单 2-页面 3-应用入口 4-组件;5-root节点
*/
private Integer featureType;
/**
* 资源所属端
*/
private String terminal;
/**
* 组件细分类型 1-跳转子页面 2-跳转公共组件 3-弹出窗口 4-下拉项 5-操作按钮 6-数据卡片 7-站外跳转
*/
private Integer componentType;
/**
* 上级资源ID
*/
private Long parentId;
/**
* 资源ID层级路径 逗号分隔
*/
private String path;
/**
* 展示顺序
*/
private Integer displayOrder;
/**
* 资源状态 0-隐藏 1-展示
*/
private Integer status;
/**
* 资源图标
*/
private String icon;
/**
* 跳转类型 1-站内跳转 2-站外跳转
*/
private Integer redirectType;
/**
* 资源跳转URI
*/
private String linkUrl;
/**
* 路由类型1-PC 2-小程序 3-原生
*/
private Integer linkType;
/**
* APP适配参数
*/
private String linkExt;
/**
* 小程序id
*/
private Integer appItemId;
/**
* 资源同步版本
*/
private Integer syncVersion;
/**
* 扩展字段
*/
@TableField(value = "extra", typeHandler = FastjsonTypeHandler.class)
private FeatureResourceExtraDO extra;
/**
* 授权类型0-全部角色 1-指定角色
*/
private Integer authType;
/**
* 子级鉴权类型 0-不鉴权1-鉴权
*/
private Integer subAuthType;
/**
* 创建人
*/
private Long createBy;
/**
* 更新人
*/
private Long updateBy;
/**
* 应用范围(租户类型)1:企业工作台 2;项目工作台
*/
private Long workspaceType;
/**
* 最低版本序列,主要支持版本灰度策略
*/
private Integer version;
/**
* 唯一编码用于pre环境菜单同步
*/
private String uniCode;
}

View File

@ -0,0 +1,28 @@
package cn.axzo.tyr.client.model.res;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class SaasPermissionRelationRes {
/**
* 菜单资源树节点id
*/
private Long featureId;
/**
* 新旧菜单资源数标识
*/
private Integer type;
/**
* 菜单资源树节点类型
*/
private Integer featureType;
}

View File

@ -17,4 +17,10 @@ public class SaasPermissionRes {
* 资源编码-权限码
*/
private String featureCode;
/**
* 资源所属端
*/
private String terminal;
}

View File

@ -114,6 +114,11 @@ public class SaasRoleRes {
*/
private List<SaasRoleUserV2DTO.SaasRoleUser> saasRoleUsers;
/**
* 角色关联的权限点id信息没有featureCode直接查询的pgPermissionRelation
*/
private List<SaasPermissionRelationRes> permissionRelations;
@Data
@Builder
@NoArgsConstructor

View File

@ -0,0 +1,110 @@
package cn.axzo.tyr.client.model.res;
import cn.axzo.basics.common.model.IBaseTree;
import com.fasterxml.jackson.annotation.JsonIgnore;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
import java.util.Set;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class TreePermissionResp implements IBaseTree<TreePermissionResp, Long> {
/**
* 菜单树节点id
*/
private Long featureId;
/**
* 菜单树节点名字
*/
private String featureName;
/**
* 菜单资源类型1-菜单 2-页面 3-应用入口 4-组件 5-root节点 6-分组
*/
private Integer featureType;
/**
* 跳转类型 1-站内跳转 2-站外跳转
*/
private Integer redirectType;
/**
* 资源跳转URI
*/
private String linkUrl;
/**
* 菜单树节点对应的前端featureCodes
*/
private Set<String> featureCodes;
/** 图标 **/
private String icon;
/**
* 选中的图标
*/
private String activeIcon;
/**
* 更多图标
*/
private String moreIcon;
/**
* 上级资源ID
*/
private Long parentId;
/**
* 资源状态 0-隐藏 1-展示
*/
private Integer status;
/**
* 菜单页面编码端唯一
*/
private String uniCode;
/**
* 展示顺序
*/
private Integer displayOrder;
/**
* 菜单树子节点信息
*/
private List<TreePermissionResp> children;
@JsonIgnore
@Override
public Long getNodeCode() {
return this.getFeatureId();
}
@JsonIgnore
@Override
public Long getParentNodeCode() {
return this.getParentId();
}
@JsonIgnore
@Override
public List<TreePermissionResp> getNodeChildren() {
return this.getChildren();
}
@Override
public void setNodeChildren(List<TreePermissionResp> nodeChildren) {
this.children = nodeChildren;
}
}

View File

@ -1,10 +1,14 @@
package cn.axzo.tyr.client.model.roleuser.dto;
import cn.axzo.tyr.client.model.res.SaasPermissionRelationRes;
import cn.axzo.tyr.client.model.res.SaasPermissionRes;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
@Data
@Builder
@AllArgsConstructor
@ -20,6 +24,8 @@ public class SaasRoleUserV2DTO {
private SaasRoleUser saasRoleUser;
private SaasRole saasRole;
@Data
@Builder
@NoArgsConstructor
@ -35,5 +41,55 @@ public class SaasRoleUserV2DTO {
* 用户名字
*/
private String realName;
/**
* 单位Id
*/
private Long ouId;
/**
* 项目id
*/
private Long workspaceId;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class SaasRole {
private Long id;
/**
* 角色名称
*/
private String name;
/**
* 角色类型
* cn.axzo.tyr.client.common.enums.RoleTypeEnum
*/
private String roleType;
private Long workspaceId;
private Long ownerOuId;
/**
* 产品单位类型
* 1:总包 2:建设单位 3:监理单位 4:劳务分包 5:专业分包 6:OMS通用 7:企业通用 8:企业内班组 9:项目内班组
*/
private Integer productUnitType;
/**
* 角色权限
*/
private List<SaasPermissionRes> saasPermissions;
/**
* 角色关联的权限点id信息没有featureCode直接查询的pgPermissionRelation
*/
private List<SaasPermissionRelationRes> permissionRelations;
}
}

View File

@ -2,8 +2,10 @@ package cn.axzo.tyr.client.model.roleuser.req;
import cn.axzo.foundation.dao.support.wrapper.CriteriaField;
import cn.axzo.foundation.dao.support.wrapper.Operator;
import cn.axzo.tyr.client.common.enums.FeatureResourceType;
import cn.axzo.tyr.client.model.enums.IdentityType;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.SuperBuilder;
@ -33,4 +35,80 @@ public class ListRoleUserRelationParam {
@CriteriaField(ignore = true)
private Boolean needUsers;
/**
* 自然人Id
*/
@CriteriaField(field = "naturalPersonId", operator = Operator.EQ)
private Long personId;
/**
* 身份Id
*/
@CriteriaField(field = "identityId", operator = Operator.EQ)
private Long identityId;
/**
* workspaceId和ouId配对查询
* 例如((workspaceId = ## and ouId = ##) or (workspaceId = ## and ouId = ##))
*/
@CriteriaField(ignore = true)
private List<WorkspaceOuPair> workspaceOuPairs;
@CriteriaField(ignore = true)
private Boolean needRole;
/**
* 从saas_feature中查询权限点
*/
@CriteriaField(ignore = true)
private Boolean needRolePermissionOld;
/**
* 根据权限点id过滤
*/
@CriteriaField(ignore = true)
private List<Long> featureIds;
@CriteriaField(ignore = true)
private Boolean needPermissionRelation;
/**
* 查询菜单树节点类型
*/
@CriteriaField(ignore = true)
private List<FeatureResourceType> featureResourceTypes;
/**
* 新旧权限点needPermissionRelation = true时最好带上因为新旧权限点会有冲突的情况发生
*/
@CriteriaField(ignore = true)
private Integer type;
@CriteriaField(ignore = true)
private String terminal;
/**
* 权限点从saas_feature_resource表查询
*/
@CriteriaField(ignore = true)
private Boolean needPermission;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class WorkspaceOuPair {
/**
* 租户id
*/
private Long workspaceId;
/**
* 单位id
*/
private Long ouId;
}
}

View File

@ -34,7 +34,7 @@ public class SaveOrUpdatePermissionGroupVO {
private String type;
/**
* 已选择的项目
* 已选择的项目
*/
@Valid
private List<PermissionGroupScopeVO> selectedWorkspace;

View File

@ -99,7 +99,7 @@ public class SaveOrUpdateRoleVO {
private Long id;
/**
* 项目类型字典code
* 项目类型字典code
*/
private String workspaceTypeCode;
}

View File

@ -132,6 +132,12 @@
<groupId>cn.axzo.basics</groupId>
<artifactId>basics-profiles-api</artifactId>
</dependency>
<dependency>
<groupId>cn.axzo.platform</groupId>
<artifactId>apisix-plat-api</artifactId>
<version>2.0.0-SNAPSHOT</version>
</dependency>
</dependencies>
<build>
<plugins>

View File

@ -1,6 +1,7 @@
package cn.axzo.tyr.server;
import cn.axzo.pokonyan.config.mybatisplus.EntityMetaObjectHandler;
import cn.axzo.tyr.server.config.RocketMQEventConfiguration;
import cn.axzo.tyr.server.job.CMSRoleJobHandler;
import cn.hutool.extra.spring.SpringUtil;
import lombok.extern.slf4j.Slf4j;
@ -20,6 +21,7 @@ import org.springframework.scheduling.annotation.EnableAsync;
@EnableDiscoveryClient
@MapperScan(value = {"cn.axzo.tyr.server.repository.mapper"})
@SpringBootApplication(scanBasePackages = "cn.axzo")
@Import(RocketMQEventConfiguration.class)
public class TyrApplication {
public static void main(String[] args) {
ConfigurableApplicationContext run = SpringApplication.run(TyrApplication.class, args);

View File

@ -1,10 +1,12 @@
package cn.axzo.tyr.server;
import cn.axzo.tyr.server.config.RocketMQEventConfiguration;
import lombok.extern.log4j.Log4j2;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.openfeign.EnableFeignClients;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Import;
import org.springframework.core.env.Environment;
import org.springframework.scheduling.annotation.EnableAsync;
@ -15,6 +17,7 @@ import org.springframework.scheduling.annotation.EnableAsync;
@EnableFeignClients(basePackages = {"cn.axzo"})
@Log4j2
@EnableAsync
@Import(RocketMQEventConfiguration.class)
public class TyrServerDevApplication {
public static void main(String[] args) throws Exception {

View File

@ -1,10 +1,12 @@
package cn.axzo.tyr.server;
import cn.axzo.tyr.server.config.RocketMQEventConfiguration;
import lombok.extern.log4j.Log4j2;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.openfeign.EnableFeignClients;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Import;
import org.springframework.core.env.Environment;
import org.springframework.scheduling.annotation.EnableAsync;
@ -16,6 +18,7 @@ import org.springframework.scheduling.annotation.EnableAsync;
@EnableFeignClients(basePackages = {"cn.axzo"})
@Log4j2
@EnableAsync
@Import(RocketMQEventConfiguration.class)
public class TyrServerPreApplication {
public static void main(String[] args) throws Exception {
@ -28,6 +31,8 @@ public class TyrServerPreApplication {
System.setProperty("spring.redis.port", "6379");
System.setProperty("spring.redis.host", "172.16.1.76");
System.setProperty("rocketmq.name-server", "172.16.2.82:9876");
SpringApplication application = new SpringApplication(TyrServerPreApplication.class);
ApplicationContext applicationContext = application.run(args);
Environment env = applicationContext.getEnvironment();

View File

@ -1,10 +1,12 @@
package cn.axzo.tyr.server;
import cn.axzo.tyr.server.config.RocketMQEventConfiguration;
import lombok.extern.log4j.Log4j2;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.openfeign.EnableFeignClients;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Import;
import org.springframework.core.env.Environment;
import org.springframework.scheduling.annotation.EnableAsync;
@ -16,6 +18,7 @@ import org.springframework.scheduling.annotation.EnableAsync;
@EnableFeignClients(basePackages = {"cn.axzo"})
@Log4j2
@EnableAsync
@Import(RocketMQEventConfiguration.class)
public class TyrServerTestApplication {
public static void main(String[] args) throws Exception {

View File

@ -37,8 +37,11 @@ public class FeignConfig implements RequestInterceptor, EnvironmentAware {
private String maokaiEnvUrl;
@Value("${pudgeEnvUrl:http://dev-app.axzo.cn/pudge}")
private String pudgeEnvUrl;
private static String POD_NAMESPACE;
@Value("${apisixUrl:http://dev-app.axzo.cn/apisix-plat}")
private String apisixUrl;
private static String POD_NAMESPACE;
static {
Map<String, String> env = System.getenv();
if (env != null) {
@ -59,6 +62,8 @@ public class FeignConfig implements RequestInterceptor, EnvironmentAware {
url = url.replace("http://thrones", thronesEnvUrl);
url = url.replace("http://maokai:8080", maokaiEnvUrl);
url = url.replace("http://pudge:10099", pudgeEnvUrl);
url = url.replace("http://apisix-plat:8080", apisixUrl);
String profile = environment.getProperty("spring.profiles.active");
if(Objects.equals(profile, "test") && url.contains("dev-app.axzo.cn")) {
url = url.replace("dev-app", "test-api");

View File

@ -0,0 +1,90 @@
package cn.axzo.tyr.server.config;
import cn.axzo.framework.rocketmq.BaseListener;
import cn.axzo.framework.rocketmq.DefaultEventConsumer;
import cn.axzo.framework.rocketmq.EventConsumer;
import cn.axzo.framework.rocketmq.EventHandlerRepository;
import cn.axzo.framework.rocketmq.EventProducer;
import cn.axzo.framework.rocketmq.RocketMQEventProducer;
import lombok.extern.slf4j.Slf4j;
import org.apache.rocketmq.common.message.MessageExt;
import org.apache.rocketmq.spring.annotation.ConsumeMode;
import org.apache.rocketmq.spring.annotation.RocketMQMessageListener;
import org.apache.rocketmq.spring.core.RocketMQListener;
import org.apache.rocketmq.spring.core.RocketMQTemplate;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.stereotype.Component;
import java.util.function.Consumer;
/**
* @Author: liyong.tian
* @Date: 2023/7/25 14:43
* @Description:
*/
@Slf4j
public class RocketMQEventConfiguration {
@Value("${spring.application.name}")
private String appName;
@Value("${topic}")
private String topic;
@Bean
public RocketMQTemplate ser(){
return new RocketMQTemplate();
}
@Bean
EventProducer eventProducer(RocketMQTemplate rocketMQTemplate) {
return new RocketMQEventProducer(rocketMQTemplate,
appName,
appName,
EventProducer.Context.<RocketMQEventProducer.RocketMQMessageMeta>builder()
.meta(RocketMQEventProducer.RocketMQMessageMeta.builder()
.topic(topic)
.build())
.build(),
null
);
}
@Bean
EventConsumer eventConsumer(EventHandlerRepository eventHandlerRepository) {
Consumer<EventConsumer.EventWrapper> callback = (eventWrapper) -> {
if (eventWrapper.isHandled()) {
// 只收集被App真正消费的消息.
//String topic = (String) eventWrapper.getExt().get(EVENT_TOPIC_KEY);
}
};
return new DefaultEventConsumer(appName, eventHandlerRepository, callback);
}
@Slf4j
@Component
@RocketMQMessageListener(topic = "topic_thrones_${spring.profiles.active}",
consumerGroup = "GID_topic_thrones_${spring.application.name}_${spring.profiles.active}",
consumeMode = ConsumeMode.ORDERLY,
nameServer = "${rocketmq.name-server}"
)
public static class DefaultListener extends BaseListener implements RocketMQListener<MessageExt> {
@Autowired
private EventConsumer eventConsumer;
@Override
public void onMessage(MessageExt message) {
super.onEvent(message, eventConsumer);
}
}
@Bean
EventHandlerRepository eventHandlerRepository() {
return new EventHandlerRepository((ex, logText) -> {
log.warn("MQ, handle warning {}", logText, ex);
});
}
}

View File

@ -9,7 +9,11 @@ import lombok.Getter;
public enum BizResultCode implements IResultCode {
CANT_DELETE_ROLE_GROUP("100001", "不能删除角色分组,当前角色分组下有子角色分组"),
ROLE_GROUP_NOT_FOUND("100002", "角色分组不存在");
ROLE_GROUP_NOT_FOUND("100002", "角色分组不存在"),
REDIS_ROLE_NOT_NULL("100003", "角色id不能为空"),
REDIS_PRODUCT_NOT_NULL("100004", "产品不能为空"),
FEATURE_RESOURCE_NOT_FOUND("100005", "菜单资源不存在"),
WORKSPACE_ID_NOT_NULL("100006", "项目id不能为空");
private String errorCode;
private String errorMessage;

View File

@ -1,27 +1,54 @@
package cn.axzo.tyr.server.controller;
import cn.axzo.basics.common.constant.enums.DeleteEnum;
import cn.axzo.basics.common.constant.enums.TableIsDeleteEnum;
import cn.axzo.basics.common.util.TreeUtil;
import cn.axzo.tyr.client.common.enums.FeatureResourceType;
import cn.axzo.foundation.page.PageResp;
import cn.axzo.framework.domain.web.result.ApiResult;
import cn.axzo.framework.rocketmq.Event;
import cn.axzo.pokonyan.config.mybatisplus.BaseEntity;
import cn.axzo.tyr.client.model.req.CommonDictQueryReq;
import cn.axzo.tyr.client.model.req.FeatureResourceTreeSaveReq;
import cn.axzo.tyr.client.model.req.GetFeatureResourceTreeReq;
import cn.axzo.tyr.client.model.req.PagePgroupPermissionRelationReq;
import cn.axzo.tyr.client.model.req.PageProductFeatureRelationReq;
import cn.axzo.tyr.client.model.req.PermissionCheckReq;
import cn.axzo.tyr.client.model.req.QuerySaasRoleGroupReq;
import cn.axzo.tyr.client.model.res.CommonDictResp;
import cn.axzo.tyr.client.model.res.FeatureResourceDTO;
import cn.axzo.tyr.client.model.res.FeatureResourceTreeNode;
import cn.axzo.tyr.client.model.res.SaasRoleRes;
import cn.axzo.tyr.client.model.vo.SaasRoleGroupVO;
import cn.axzo.tyr.client.model.vo.SaveOrUpdateRoleVO;
import cn.axzo.tyr.server.event.outer.CacheWorkspaceProductHandler;
import cn.axzo.tyr.server.event.payload.ServicePkgProductCreatedPayload;
import cn.axzo.tyr.server.repository.dao.SaasFeatureDao;
import cn.axzo.tyr.server.repository.dao.SaasFeatureResourceDao;
import cn.axzo.tyr.server.repository.dao.SaasPgroupPermissionRelationDao;
import cn.axzo.tyr.server.repository.dao.SaasPgroupRoleRelationDao;
import cn.axzo.tyr.server.repository.dao.SaasRoleDao;
import cn.axzo.tyr.server.repository.dao.SaasRoleGroupDao;
import cn.axzo.tyr.server.repository.dao.SaasRoleGroupRelationDao;
import cn.axzo.tyr.server.repository.entity.SaasFeature;
import cn.axzo.tyr.server.repository.entity.SaasFeatureResource;
import cn.axzo.tyr.server.repository.entity.SaasPgroupPermissionRelation;
import cn.axzo.tyr.server.repository.entity.SaasPgroupRoleRelation;
import cn.axzo.tyr.server.repository.entity.SaasProductModuleFeatureRelation;
import cn.axzo.tyr.server.repository.entity.SaasRole;
import cn.axzo.tyr.server.repository.entity.SaasRoleGroup;
import cn.axzo.tyr.server.repository.entity.SaasRoleGroupRelation;
import cn.axzo.tyr.server.service.ProductFeatureRelationService;
import cn.axzo.tyr.server.service.ProductPermissionCacheService;
import cn.axzo.tyr.server.service.RoleService;
import cn.axzo.tyr.server.service.SaasCommonDictService;
import cn.axzo.tyr.server.service.SaasFeatureResourceService;
import cn.axzo.tyr.server.service.SaasPgroupPermissionRelationService;
import cn.axzo.tyr.server.service.SaasRoleGroupService;
import cn.axzo.tyr.server.service.TyrSaasAuthService;
import cn.axzo.tyr.server.service.WorkspaceProductService;
import cn.axzo.tyr.server.service.impl.SaasFeatureResourceCacheService;
import cn.axzo.tyr.server.util.FeatureCodeUtil;
import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.annotation.ExcelProperty;
import com.alibaba.fastjson.JSON;
import com.google.common.collect.Lists;
import lombok.AllArgsConstructor;
import lombok.Builder;
@ -34,20 +61,27 @@ import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestPart;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;
import java.io.IOException;
import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import java.util.function.Function;
import java.util.stream.Collectors;
import java.util.stream.IntStream;
import static cn.axzo.tyr.server.repository.entity.SaasPgroupPermissionRelation.NEW_FEATURE;
import static cn.axzo.tyr.server.repository.entity.SaasPgroupPermissionRelation.OLD_FEATURE;
@Slf4j
@RestController
@RequiredArgsConstructor
@ -62,12 +96,33 @@ public class PrivateController {
@Autowired
private RoleService roleService;
@Autowired
private SaasFeatureResourceService saasFeatureResourceService;
@Autowired
private SaasFeatureResourceDao saasFeatureResourceDao;
@Autowired
private SaasFeatureResourceCacheService saasFeatureResourceCacheService;
@Autowired
private ProductPermissionCacheService productPermissionCacheService;
@Autowired
private TyrSaasAuthService tyrSaasAuthService;
@Autowired
private SaasFeatureDao saasFeatureDao;
@Autowired
private SaasPgroupPermissionRelationService saasPgroupPermissionRelationService;
@Autowired
private SaasRoleDao saasRoleDao;
@Autowired
private SaasPgroupRoleRelationDao saasPgroupRoleRelationDao;
@Autowired
private SaasPgroupPermissionRelationDao saasPgroupPermissionRelationDao;
@Autowired
private ProductFeatureRelationService productFeatureRelationService;
@Autowired
private FeatureCodeUtil featureCodeUtil;
@Autowired
private WorkspaceProductService workspaceProductService;
@Autowired
private CacheWorkspaceProductHandler cacheWorkspaceProductHandler;
@Autowired
private SaasRoleGroupDao saasRoleGroupDao;
/**
* 统一层级的roleGroup按照id升序sort从1递增
@ -251,6 +306,381 @@ public class PrivateController {
});
}
@PostMapping("/api/private/productPermission/add")
public Object addProductPermission(@Validated @RequestBody ProductPermissionCacheService.StoreProductPermissionParam request) {
productPermissionCacheService.store(request);
return "ok";
}
@PostMapping("/api/private/productPermission/get")
public Object getProductPermission(@Validated @RequestBody ProductPermissionCacheService.ListProductPermissionParam request) {
return productPermissionCacheService.list(request);
}
@PostMapping("/api/private/productPermission/has")
public Object hasProductIds(@Validated @RequestBody ProductPermissionCacheService.HasProductPermissionParam request) {
return productPermissionCacheService.hasProductIds(request);
}
@PostMapping("/api/private/permission/auth")
public Object authPermission(@Validated @RequestBody PermissionCheckReq request) {
return tyrSaasAuthService.authPermission(request);
}
/** 刷新表saas_pgroup_permission_relation的type字段 **/
@PostMapping("/api/private/pgroupPermissionRelation/refresh")
public ApiResult<Void> refreshPgroupPermissionRelation(@Validated @RequestBody RefreshPgroupPermissionRelationParam request) {
List<Integer> workspaceTypes = Lists.newArrayList(3,6);
if (!workspaceTypes.contains(request.getWorkspaceType())) {
return ApiResult.err("非oms、政务的角色不能清洗。");
}
Long startRoleId = 0L;
while (true) {
List<SaasRole> saasRoles = saasRoleDao.lambdaQuery()
.eq(BaseEntity::getIsDelete, DeleteEnum.NORMAL.getValue())
.eq(SaasRole::getWorkspaceType, request.getWorkspaceType())
.gt(BaseEntity::getId, startRoleId)
.orderByAsc(BaseEntity::getId)
.last("LIMIT " + request.getPageSize())
.list();
if (CollectionUtils.isEmpty(saasRoles)) {
return ApiResult.ok();
}
processRole(saasRoles.stream().map(BaseEntity::getId).collect(Collectors.toList()));
startRoleId = saasRoles.get(saasRoles.size() - 1).getId();
}
}
private void processRole(List<Long> roleIds) {
List<SaasPgroupRoleRelation> saasPgroupRoleRelations = saasPgroupRoleRelationDao.findByRoleIds(roleIds);
if (CollectionUtils.isEmpty(saasPgroupRoleRelations)) {
log.info("refreshPgroupPermissionRelation roleIds:{} has no pgroup role relation", JSON.toJSONString(roleIds));
return;
}
List<Long> groupIds = saasPgroupRoleRelations.stream().map(SaasPgroupRoleRelation::getGroupId).filter(Objects::nonNull).distinct().collect(Collectors.toList());
if (CollectionUtils.isEmpty(groupIds)) {
return;
}
saasPgroupPermissionRelationDao.lambdaUpdate()
.eq(BaseEntity::getIsDelete, TableIsDeleteEnum.NORMAL.value)
.in(SaasPgroupPermissionRelation::getGroupId, groupIds)
.set(SaasPgroupPermissionRelation::getType, 1)
.update();
}
/**
* 刷新saas_pgroup_permission_relation表的featureType
* 1type = 0的数据从saas_feature中查询
* 2type = 1的数据从saas_feature_resource中查询
* @param request
* @return
*/
@PostMapping("/api/private/pGroupPermissionRelation/featureResource/refresh")
public Object reFreshFeature(@Validated @RequestBody RefreshPGroupPermissionFeatureParam request) {
final Integer DEFAULT_PAGE_SIZE = 100;
Integer pageNumber = 1;
while (true) {
PagePgroupPermissionRelationReq req = PagePgroupPermissionRelationReq.builder()
.ids(request.getIds())
.page(pageNumber++)
.pageSize(DEFAULT_PAGE_SIZE)
.build();
PageResp<SaasPgroupPermissionRelation> page = saasPgroupPermissionRelationService.page(req);
if (CollectionUtils.isNotEmpty(page.getData())) {
updateOldRoleFeature(page.getData());
updateNewRoleFeature(page.getData());
}
if (!page.hasNext()) {
break;
}
}
return "ok";
}
private void updateNewRoleFeature(List<SaasPgroupPermissionRelation> saasPgroupPermissionRelations) {
List<SaasPgroupPermissionRelation> newFeatureRelations = saasPgroupPermissionRelations.stream()
.filter(e -> Objects.equals(e.getType(), NEW_FEATURE))
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(newFeatureRelations)) {
return;
}
Map<Long, SaasFeatureResource> saasFeatureResourceMap = saasFeatureResourceDao.listByIds(Lists.transform(newFeatureRelations, SaasPgroupPermissionRelation::getFeatureId))
.stream()
.collect(Collectors.toMap(SaasFeatureResource::getId, Function.identity()));
List<SaasPgroupPermissionRelation> update = newFeatureRelations.stream()
.map(e -> {
SaasFeatureResource saasFeatureResource = saasFeatureResourceMap.get(e.getFeatureId());
if (saasFeatureResource == null) {
return null;
}
SaasPgroupPermissionRelation saasPgroupPermissionRelation = new SaasPgroupPermissionRelation();
saasPgroupPermissionRelation.setId(e.getId());
saasPgroupPermissionRelation.setFeatureType(saasFeatureResource.getFeatureType());
return saasPgroupPermissionRelation;
})
.filter(Objects::nonNull)
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(update)) {
return;
}
saasPgroupPermissionRelationService.updateBatchById(update);
}
private void updateOldRoleFeature(List<SaasPgroupPermissionRelation> saasPgroupPermissionRelations) {
List<SaasPgroupPermissionRelation> oldFeatureRelations = saasPgroupPermissionRelations.stream()
.filter(e -> Objects.equals(e.getType(), OLD_FEATURE))
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(oldFeatureRelations)) {
return;
}
Map<Long, SaasFeature> saasFeatureMap = saasFeatureDao.listByIds(Lists.transform(oldFeatureRelations, SaasPgroupPermissionRelation::getFeatureId))
.stream()
.collect(Collectors.toMap(SaasFeature::getId, Function.identity()));
List<SaasPgroupPermissionRelation> update = oldFeatureRelations.stream()
.map(e -> {
SaasFeature saasFeature = saasFeatureMap.get(e.getFeatureId());
if (saasFeature == null) {
return null;
}
SaasPgroupPermissionRelation saasPgroupPermissionRelation = new SaasPgroupPermissionRelation();
saasPgroupPermissionRelation.setId(e.getId());
saasPgroupPermissionRelation.setFeatureType(saasFeature.getFeatureType());
return saasPgroupPermissionRelation;
})
.filter(Objects::nonNull)
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(update)) {
return;
}
saasPgroupPermissionRelationService.updateBatchById(update);
}
/**
* 刷新saas_product_module_feature_relation表的featureType
* 1type = 0的数据从saas_feature中查询
* 2type = 1的数据从saas_feature_resource中查询
* @param request
* @return
*/
@PostMapping("/api/private/ProductPermissionRelation/featureResource/refresh")
public Object reFreshProductFeature(@Validated @RequestBody RefreshProductPermissionFeatureParam request) {
final Integer DEFAULT_PAGE_SIZE = 100;
Integer pageNumber = 1;
while (true) {
PageProductFeatureRelationReq req = PageProductFeatureRelationReq.builder()
.ids(request.getIds())
.page(pageNumber++)
.pageSize(DEFAULT_PAGE_SIZE)
.build();
PageResp<SaasProductModuleFeatureRelation> page = productFeatureRelationService.page(req);
if (CollectionUtils.isNotEmpty(page.getData())) {
updateOldProductFeature(page.getData());
updateNewProductFeature(page.getData());
}
if (!page.hasNext()) {
break;
}
}
return "ok";
}
private void updateNewProductFeature(List<SaasProductModuleFeatureRelation> saasProductModuleFeatureRelations) {
List<SaasProductModuleFeatureRelation> newFeatureRelations = saasProductModuleFeatureRelations.stream()
.filter(e -> Objects.equals(e.getType(), NEW_FEATURE))
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(newFeatureRelations)) {
return;
}
Map<Long, SaasFeatureResource> saasFeatureResourceMap = saasFeatureResourceDao.listByIds(Lists.transform(newFeatureRelations, SaasProductModuleFeatureRelation::getFeatureId))
.stream()
.collect(Collectors.toMap(SaasFeatureResource::getId, Function.identity()));
List<SaasProductModuleFeatureRelation> update = newFeatureRelations.stream()
.map(e -> {
SaasFeatureResource saasFeatureResource = saasFeatureResourceMap.get(e.getFeatureId());
if (saasFeatureResource == null) {
return null;
}
SaasProductModuleFeatureRelation saasProductModuleFeatureRelation = new SaasProductModuleFeatureRelation();
saasProductModuleFeatureRelation.setId(e.getId());
saasProductModuleFeatureRelation.setFeatureType(saasFeatureResource.getFeatureType());
return saasProductModuleFeatureRelation;
})
.filter(Objects::nonNull)
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(update)) {
return;
}
productFeatureRelationService.updateBatchById(update);
}
private void updateOldProductFeature(List<SaasProductModuleFeatureRelation> saasProductModuleFeatureRelations) {
List<SaasProductModuleFeatureRelation> oldFeatureRelations = saasProductModuleFeatureRelations.stream()
.filter(e -> Objects.equals(e.getType(), OLD_FEATURE))
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(oldFeatureRelations)) {
return;
}
Map<Long, SaasFeature> saasFeatureMap = saasFeatureDao.listByIds(Lists.transform(oldFeatureRelations, SaasProductModuleFeatureRelation::getFeatureId))
.stream()
.collect(Collectors.toMap(SaasFeature::getId, Function.identity()));
List<SaasProductModuleFeatureRelation> update = oldFeatureRelations.stream()
.map(e -> {
SaasFeature saasFeature = saasFeatureMap.get(e.getFeatureId());
if (saasFeature == null) {
return null;
}
SaasProductModuleFeatureRelation saasProductModuleFeatureRelation = new SaasProductModuleFeatureRelation();
saasProductModuleFeatureRelation.setId(e.getId());
saasProductModuleFeatureRelation.setFeatureType(saasFeature.getFeatureType());
return saasProductModuleFeatureRelation;
})
.filter(Objects::nonNull)
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(update)) {
return;
}
productFeatureRelationService.updateBatchById(update);
}
@PostMapping("/api/private/featureCode/resolve")
public Object resolveFeatureCode(@RequestBody ResolveFeatureCodeParam request) {
return featureCodeUtil.resolveFeatureCode(request.getFeatureCodes());
}
@PostMapping("/api/private/workspaceProduct/store")
public Object storeWorkspaceProduct(@RequestBody WorkspaceProductService.StoreWorkspaceProductParam request) {
workspaceProductService.storeWorkspaceProduct(request);
return "ok";
}
@PostMapping("/api/private/workspaceProduct/list")
public Object listWorkspaceProduct(@RequestBody WorkspaceProductService.WorkspaceProductParam request) {
return workspaceProductService.listWorkspaceProductCached(request);
}
@PostMapping("/api/private/cacheWorkspaceProductHandler/process")
public Object processCacheWorkspaceProductHandler(@RequestBody ServicePkgProductCreatedPayload request) {
Event event = Event.builder()
.data(request)
.build();
cacheWorkspaceProductHandler.onEvent(event, null);
return "ok";
}
@PostMapping("/api/private/role/insert")
public Object insertRole(@RequestPart("file") MultipartFile file) throws IOException {
List<CreateRoleParam> importExcels = EasyExcel.read(file.getInputStream())
.head(CreateRoleParam.class)
.sheet()
.doReadSync();
importExcels = importExcels.stream()
.filter(e -> Objects.equals(e.getType(), "c"))
.filter(e -> Objects.nonNull(e.getGroupId()))
.collect(Collectors.toList());
Set<Long> roleGroupIds = importExcels.stream()
.map(CreateRoleParam::getGroupId)
.collect(Collectors.toSet());
Map<Long, SaasRoleGroup> saasRoleGroups = saasRoleGroupDao.listByIds(roleGroupIds).stream()
.collect(Collectors.toMap(SaasRoleGroup::getId, Function.identity()));
importExcels.forEach(e -> {
SaasRoleGroup saasRoleGroup = saasRoleGroups.get(e.getGroupId());
if (saasRoleGroup == null) {
log.info("not found saasRoleGroup,{}", e.getGroupId());
return;
}
SaveOrUpdateRoleVO.GroupInfoVO groupInfoVO = new SaveOrUpdateRoleVO.GroupInfoVO();
groupInfoVO.setId(e.getGroupId());
groupInfoVO.setWorkspaceTypeCode(saasRoleGroup.getWorkspaceTypeCode());
SaveOrUpdateRoleVO saveOrUpdateRoleVO = SaveOrUpdateRoleVO.builder()
.name(e.getRoleName())
.roleType("init")
.workspaceId(-1L)
.ownerOuId(-1L)
.operatorId(2007696L)
.operatorName("李龙")
.groupTree(Lists.newArrayList(groupInfoVO))
.permissionGroupName("通用权限")
.permissionGroupType("feature")
.roleCode(e.getRoleCode())
.isDisplay(true)
.enabled(true)
.build();
try {
roleService.saveOrUpdate(saveOrUpdateRoleVO);
} catch (Exception ex) {
log.info("roleName {},ex:", e.getRoleName(), ex);
}
});
return "ok";
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class CreateRoleParam {
@ExcelProperty("角色名")
private String roleName;
@ExcelProperty("分组ID")
private Long groupId;
@ExcelProperty("单位类型type")
private Integer productUnitType;
@ExcelProperty("角色编码")
private String roleCode;
@ExcelProperty("操作类型")
private String type;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class ResolveFeatureCodeParam {
private Set<String> featureCodes;
}
@Data
@Builder
@NoArgsConstructor
@ -262,4 +692,34 @@ public class PrivateController {
@NotNull(message = "rootId不能为空")
private Long rootId;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class RefreshPgroupPermissionRelationParam {
@NotNull(message = "workspaceType不能为空oms:6,政务:3")
private Integer workspaceType;
@Builder.Default
private Integer pageSize = 10;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class RefreshPGroupPermissionFeatureParam {
private List<Long> ids;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class RefreshProductPermissionFeatureParam {
private List<Long> ids;
}
}

View File

@ -63,7 +63,6 @@ public class TyrSaasAuthController implements TyrSaasAuthApi {
}
return ApiResult.ok(tyrSaasAuthService.findIdentityAuthMix(identityAuthReq));
}
@Override
public ApiResult<Boolean> hasPermissionForIdentityV2(CheckIdentityPermissionReq req) {
//单独做下参数校验

View File

@ -1,12 +1,11 @@
package cn.axzo.tyr.server.controller.permission;
import cn.axzo.basics.common.exception.ServiceException;
import cn.axzo.framework.domain.web.result.ApiResult;
import cn.axzo.tyr.client.feign.FeatureResourceApi;
import cn.axzo.tyr.client.model.req.DeleteFeatureResourceReq;
import cn.axzo.tyr.client.model.req.FeatureResourceTreeSaveReq;
import cn.axzo.tyr.client.model.req.GetFeatureResourceTreeReq;
import cn.axzo.tyr.client.model.req.ResourceSyncReq;
import cn.axzo.tyr.client.model.res.FeatureResourceDetailResp;
import cn.axzo.tyr.client.model.res.FeatureResourceTreeNode;
import cn.axzo.tyr.server.service.FeatureResourceSyncService;
import cn.axzo.tyr.server.service.SaasFeatureResourceService;
@ -16,6 +15,7 @@ import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
import java.util.Map;
/**
* 功能资源接口实现
@ -58,11 +58,10 @@ public class FeatureResourceController implements FeatureResourceApi {
}
@Override
public ApiResult<Void> deleteFeatureResource(Long featureId, Long operatorId) {
throw new ServiceException("暂时不支持删除权限点");
// log.info("deleteFeatureResource featureId : {}, operatorId : {}", featureId, operatorId);
// featureResourceService.deleteMenuFeature(featureId, operatorId);
// return ApiResult.ok();
public ApiResult<Void> deleteFeatureResource(DeleteFeatureResourceReq req) {
log.info("deleteFeatureResource req : {}", req);
featureResourceService.deleteFeatureResource(req);
return ApiResult.ok();
}
@Override
@ -87,4 +86,9 @@ public class FeatureResourceController implements FeatureResourceApi {
public ApiResult<List<FeatureResourceTreeNode>> getBaseTree(GetFeatureResourceTreeReq req) {
return ApiResult.ok(featureResourceSyncService.getBaseTree(req));
}
@Override
public ApiResult<Map<Long, String>> listFeatureCodeByFeatureResourceIds(List<Long> featureResourceIds) {
return ApiResult.ok(featureResourceSyncService.listFeatureCodeByFeatureResourceIds(featureResourceIds));
}
}

View File

@ -0,0 +1,54 @@
package cn.axzo.tyr.server.controller.permission;
import cn.axzo.framework.domain.web.result.ApiPageResult;
import cn.axzo.framework.domain.web.result.ApiResult;
import cn.axzo.tyr.client.feign.PageElementApi;
import cn.axzo.tyr.client.model.req.*;
import cn.axzo.tyr.client.model.res.GetUserHasPermissionPageElementResp;
import cn.axzo.tyr.client.model.res.PageElementResp;
import cn.axzo.tyr.server.service.SaasPageElementService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/18
*/
@Slf4j
@RestController
@RequiredArgsConstructor
public class PageElementController implements PageElementApi {
private final SaasPageElementService saasPageElementService;
@Override
public ApiResult<Void> report(PageElementReportReq req) {
saasPageElementService.report(req);
return ApiResult.ok();
}
@Override
public ApiResult<List<PageElementResp>> getPageElement(GetPageElementReq req) {
return ApiResult.ok(saasPageElementService.getPageElement(req));
}
@Override
public ApiResult<Void> modifyPageElementRelation(ModifyPageElementRelationDTO req) {
saasPageElementService.modifyPageElementRelation(req);
return ApiResult.ok();
}
@Override
public ApiPageResult<PageElementResp> page(PageQueryElementReq req) {
return ApiPageResult.ok(saasPageElementService.page(req));
}
@Override
public ApiResult<GetUserHasPermissionPageElementResp> getUserHasPermissionPageElement(GetUserHasPermissionPageElementReq req) {
return ApiResult.ok(saasPageElementService.getUserHasPermissionPageElement(req));
}
}

View File

@ -6,10 +6,12 @@ import cn.axzo.tyr.client.model.req.NavTreeReq;
import cn.axzo.tyr.client.model.req.PagePermissionReq;
import cn.axzo.tyr.client.model.req.PagePermissionResp;
import cn.axzo.tyr.client.model.req.PermissionCheckReq;
import cn.axzo.tyr.client.model.req.TreePermissionReq;
import cn.axzo.tyr.client.model.req.TreeProductFeatureResourceReq;
import cn.axzo.tyr.client.model.res.FeatureResourceDTO;
import cn.axzo.tyr.client.model.res.NavTreeResp;
import cn.axzo.tyr.client.model.res.ProductFeatureResourceResp;
import cn.axzo.tyr.client.model.res.TreePermissionResp;
import cn.axzo.tyr.server.service.PermissionQueryService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
@ -55,4 +57,9 @@ public class PermissionQueryController implements PermissionQueryApi {
public ApiResult<List<FeatureResourceDTO>> listFeatureResource(TreeProductFeatureResourceReq request) {
return ApiResult.ok(permissionService.listFeatureResource(request));
}
@Override
public ApiResult<List<TreePermissionResp>> treePermission(TreePermissionReq req) {
return ApiResult.ok(permissionService.treePermission(req));
}
}

View File

@ -3,14 +3,7 @@ package cn.axzo.tyr.server.controller.product;
import cn.axzo.framework.domain.web.result.ApiPageResult;
import cn.axzo.framework.domain.web.result.ApiResult;
import cn.axzo.tyr.client.feign.ProductApi;
import cn.axzo.tyr.client.model.product.ProductAddReq;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationSearchReq;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationUpdateReq;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationVO;
import cn.axzo.tyr.client.model.product.ProductSearchListReq;
import cn.axzo.tyr.client.model.product.ProductSearchPageReq;
import cn.axzo.tyr.client.model.product.ProductUpdateReq;
import cn.axzo.tyr.client.model.product.ProductVO;
import cn.axzo.tyr.client.model.product.*;
import cn.axzo.tyr.client.model.req.ProductSaveReq;
import cn.axzo.tyr.client.model.req.UpdateProductStatusReq;
import cn.axzo.tyr.client.model.res.GovernmentTerminalResp;
@ -72,7 +65,7 @@ public class ProductController implements ProductApi {
*/
@Override
public ApiResult<ProductVO> getById(Long id) {
return productService.getById(id);
return productService.getById(id, Boolean.FALSE);
}
/**
@ -159,6 +152,7 @@ public class ProductController implements ProductApi {
*/
@Override
public ApiResult<Long> saveOrUpdate(ProductSaveReq req) {
permissionCacheService.markTempDisable(PermissionCacheKey.builder().disableAll(true).build());
return productService.saveOrUpdate(req);
}
@ -183,4 +177,9 @@ public class ProductController implements ProductApi {
public ApiResult<WorkspaceProductResp> getWorkspaceProduct(String workspaceType) {
return productService.getWorkspaceProduct(workspaceType);
}
@Override
public ApiResult<ProductVO> getDetail(ProductDetailReq req) {
return productService.getById(req.getProductId(), req.getQueryFeatureScope());
}
}

View File

@ -35,7 +35,6 @@ import cn.axzo.tyr.client.model.vo.SaasRoleVO;
import cn.axzo.tyr.client.model.vo.SaveOrUpdateRoleVO;
import cn.axzo.tyr.server.model.PermissionCacheKey;
import cn.axzo.tyr.server.repository.dao.SaasRoleGroupRelationDao;
import cn.axzo.tyr.server.repository.dao.SaasRoleUserRelationDao;
import cn.axzo.tyr.server.repository.entity.SaasRole;
import cn.axzo.tyr.server.repository.entity.SaasRoleGroupRelation;
import cn.axzo.tyr.server.service.PermissionCacheService;
@ -52,8 +51,6 @@ import org.apache.commons.lang3.BooleanUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;
import java.util.Collections;
@ -83,8 +80,6 @@ public class SaasRoleController implements TyrSaasRoleApi {
@Autowired
PermissionCacheService permissionCacheService;
@Autowired
private SaasRoleUserRelationDao saasRoleUserRelationDao;
@Autowired
private SaasCommonDictService saasCommonDictService;
@Autowired
private SaasRoleGroupService saasRoleGroupService;
@ -219,7 +214,9 @@ public class SaasRoleController implements TyrSaasRoleApi {
// 因为根节点在roleGroup里面没有都是workspaceTypeCode描述是放在字典表里
List<CommonDictResp> commonDicts = listRootRole(req);
if (CollectionUtils.isEmpty(commonDicts)) {
return ApiListResult.ok();
}
List<RoleTreeRes> roots = commonDicts.stream()
.map(e -> RoleTreeRes.builder()
@ -453,18 +450,32 @@ public class SaasRoleController implements TyrSaasRoleApi {
}
private List<CommonDictResp> listRootRole(TreeRoleReq req) {
CommonDictQueryReq commonDictQueryReq = CommonDictQueryReq.builder()
.codes(StringUtils.isBlank(req.getWorkspaceTypeCode()) ? null : Lists.newArrayList(req.getWorkspaceTypeCode()))
.scope("role")
.build();
List<String> workspaceTypeCodes = StringUtils.isNotBlank(req.getWorkspaceTypeCode()) ? Lists.newArrayList(req.getWorkspaceTypeCode())
: Lists.newArrayList();
if (StringUtils.isNotBlank(req.getTerminal())) {
List<String> workspaceTypeCodes = TERMINAL_WORKSPACE_CODES.get(req.getTerminal());
if (CollectionUtils.isEmpty(workspaceTypeCodes)) {
List<String> terminalWorkspaceTypeCodes = TERMINAL_WORKSPACE_CODES.get(req.getTerminal());
if (CollectionUtils.isEmpty(terminalWorkspaceTypeCodes)) {
return Collections.emptyList();
}
commonDictQueryReq.setCodes(workspaceTypeCodes);
if (StringUtils.isBlank(req.getWorkspaceTypeCode())) {
workspaceTypeCodes = terminalWorkspaceTypeCodes;
} else {
workspaceTypeCodes = terminalWorkspaceTypeCodes.stream()
.filter(e -> Objects.equals(e, req.getWorkspaceTypeCode()))
.collect(Collectors.toList());
if (CollectionUtils.isEmpty(workspaceTypeCodes)) {
return Collections.emptyList();
}
}
}
CommonDictQueryReq commonDictQueryReq = CommonDictQueryReq.builder()
.codes(workspaceTypeCodes)
.scope("role")
.build();
return saasCommonDictService.query(commonDictQueryReq);
}
}

View File

@ -0,0 +1,58 @@
package cn.axzo.tyr.server.event.outer;
import cn.axzo.framework.rocketmq.Event;
import cn.axzo.framework.rocketmq.EventConsumer;
import cn.axzo.framework.rocketmq.EventHandler;
import cn.axzo.tyr.server.event.payload.ServicePkgProductCreatedPayload;
import cn.axzo.tyr.server.service.WorkspaceProductService;
import com.google.common.collect.Lists;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections.CollectionUtils;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import java.util.Objects;
import java.util.stream.Collectors;
/**
* 缓存项目的产品
*/
@Slf4j
@Component
public class CacheWorkspaceProductHandler implements EventHandler, InitializingBean {
@Autowired
private EventConsumer eventConsumer;
@Autowired
private WorkspaceProductService workspaceProductService;
@Override
public void onEvent(Event event, EventConsumer.Context context) {
log.info("begin cached workspace product handler rocketmq event: {}", event);
ServicePkgProductCreatedPayload payload = event.normalizedData(ServicePkgProductCreatedPayload.class);
if (Objects.isNull(payload) || CollectionUtils.isEmpty(payload.getSaasServicePkgProducts())) {
return;
}
WorkspaceProductService.WorkspaceProductDTO workspaceProductDTO = WorkspaceProductService.WorkspaceProductDTO.builder()
.workspaceId(payload.getSaasServicePackage().getSpaceId())
.productIds(payload.getSaasServicePkgProducts().stream()
.map(ServicePkgProductCreatedPayload.SaasServicePkgProductPo::getProductId)
.collect(Collectors.toSet()))
.build();
WorkspaceProductService.StoreWorkspaceProductParam storeWorkspaceProductParam = WorkspaceProductService.StoreWorkspaceProductParam.builder()
.workspaceProducts(Lists.newArrayList(workspaceProductDTO))
.build();
workspaceProductService.storeWorkspaceProduct(storeWorkspaceProductParam);
log.info("end cached workspace product handler rocketmq event: {}", event);
}
@Override
public void afterPropertiesSet() throws Exception {
eventConsumer.registerHandler(EventTypeEnum.SERVICE_PKG_PRODUCT_CREATED.getEventCode(), this);
}
}

View File

@ -0,0 +1,31 @@
package cn.axzo.tyr.server.event.outer;
import cn.axzo.framework.rocketmq.Event;
import lombok.Getter;
/**
* @Classname EventTypeEnum
* @Date 2021/2/7 6:05 下午
* @Created by lilong
*/
@Getter
public enum EventTypeEnum {
SERVICE_PKG_PRODUCT_CREATED("service-pkg-product", "service-pkg-product-created", "创建服务包的产品"),
;
EventTypeEnum(String model, String name, String desc) {
this.eventCode = Event.EventCode.builder()
.module(model)
.name(name)
.build();
this.model = model;
this.name = name;
this.desc = desc;
}
private String model;
private String name;
private String desc;
private Event.EventCode eventCode;
}

View File

@ -0,0 +1,99 @@
package cn.axzo.tyr.server.event.payload;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.Serializable;
import java.time.LocalDateTime;
import java.util.List;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class ServicePkgProductCreatedPayload implements Serializable {
private SaasServicePackagePo saasServicePackage;
private List<SaasServicePkgProductPo> saasServicePkgProducts;
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class SaasServicePackagePo {
private Long id;
/**
* 单位ID
*/
private Long ouId;
/**
* 租户id
*/
private Long saasTenantId;
/**
* 服务包类型: 1.企业空间 2.项目空间 3.政企空间6.OMS空间
*/
private Integer type;
/**
* 空间id
*/
private Long spaceId;
/**
* license 名称
*/
private String name;
/**
* 有效期开始
*/
private LocalDateTime effectiveDate;
/**
* 有效斯结束
*/
private LocalDateTime ineffectiveDate;
/**
* license状态 : 1.未生效 2.有效 3.限制使用 4.停用 5.过期
*/
private Integer status;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public static class SaasServicePkgProductPo {
private Long id;
/**
* license id
*/
private Long servicePkgId;
/**
* license相关联的产品
*/
private Long productId;
/**
* 产品功能名称
*/
private String productName;
/**
* 0是基础产品 1非基础产品
*/
private Boolean isBasic;
}
}

View File

@ -1,22 +0,0 @@
package cn.axzo.tyr.server.model;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* @author likunpeng
* @version 1.0
* @date 2024/5/22
*/
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class FeatureResourceRoleCodeDTO {
private Long featureResourceId;
private String roleCode;
}

View File

@ -33,6 +33,8 @@ public class PermissionCacheKey {
private Boolean disableAll;
public String buildAuthKey() {
// 因为personIdidentityIdidentityType这三个参数用户现在可以随意组合
//
return personId == null ? KeyUtil.buildKeyBySeparator("auth-i", identityId, identityType.getCode(), ouId, workspaceId)
: KeyUtil.buildKeyBySeparator("auth-p", personId, ouId, workspaceId);
}

View File

@ -27,4 +27,9 @@ public class ResourcePermission {
private Integer featureType;
private Integer authType;
/**
* 资源所属端
*/
private String terminal;
}

View File

@ -12,6 +12,7 @@ import cn.axzo.tyr.server.repository.mapper.SaasBasicDictMapper;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.stereotype.Service;
import java.util.List;
@ -33,7 +34,8 @@ public class SaasBasicDictDao extends ServiceImpl<SaasBasicDictMapper, SaasBasic
queryChainWrapper.eq(Objects.nonNull(req.getParentId()), SaasBasicDict::getParentId, req.getParentId())
.eq(Objects.nonNull(req.getWorkspaceType()), SaasBasicDict::getWorkspaceType, req.getWorkspaceType())
.eq(Objects.nonNull(req.getType()), SaasBasicDict::getType, req.getType())
.in(Objects.nonNull(req.getCodes()), SaasBasicDict::getCode, req.getCodes())
.in(CollectionUtils.isNotEmpty(req.getCodes()), SaasBasicDict::getCode, req.getCodes())
.in(CollectionUtils.isNotEmpty(req.getIds()), SaasBasicDict::getId, req.getIds())
.eq(Objects.nonNull(req.getStatus()), SaasBasicDict::getStatus, req.getStatus())
.eq(Objects.nonNull(req.getLevel()), SaasBasicDict::getLevel, req.getLevel())
.like(Objects.nonNull(req.getName()), SaasBasicDict::getName, req.getName());

View File

@ -2,18 +2,14 @@ package cn.axzo.tyr.server.repository.dao;
import cn.axzo.basics.common.constant.enums.TableIsDeleteEnum;
import cn.axzo.tyr.client.model.req.GetFeatureResourceTreeReq;
import cn.axzo.tyr.server.model.FeatureResourceRoleCodeDTO;
import cn.axzo.tyr.server.repository.entity.SaasFeatureResource;
import cn.axzo.tyr.server.repository.mapper.SaasFeatureResourceMapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.google.common.collect.Maps;
import org.apache.commons.collections.CollectionUtils;
import org.springframework.stereotype.Repository;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.stream.Collectors;
/**
* <p>
@ -35,7 +31,8 @@ public class SaasFeatureResourceDao extends ServiceImpl<SaasFeatureResourceMappe
return this.lambdaQuery().select(SaasFeatureResource::getId, SaasFeatureResource::getFeatureCode,
SaasFeatureResource::getFeatureName, SaasFeatureResource::getFeatureType,
SaasFeatureResource::getTerminal, SaasFeatureResource::getParentId,
SaasFeatureResource::getDisplayOrder)
SaasFeatureResource::getDisplayOrder,
SaasFeatureResource::getWorkspaceType)
.eq(SaasFeatureResource::getIsDelete, TableIsDeleteEnum.NORMAL.value)
.in(CollectionUtils.isNotEmpty(req.getTerminals()), SaasFeatureResource::getTerminal, req.getTerminals())
.eq(Objects.nonNull(req.getStatus()), SaasFeatureResource::getStatus, req.getStatus())
@ -43,13 +40,4 @@ public class SaasFeatureResourceDao extends ServiceImpl<SaasFeatureResourceMappe
.list();
}
public Map<Long, List<String>> getFeatureResourceRoleCodeMap(List<Long> featureResourceIds) {
if (org.apache.commons.collections4.CollectionUtils.isEmpty(featureResourceIds)) {
return Maps.newHashMap();
}
List<FeatureResourceRoleCodeDTO> featureResourceRoleCodes = this.baseMapper.listRoleCodes(featureResourceIds);
return org.apache.commons.collections4.CollectionUtils.emptyIfNull(featureResourceRoleCodes).stream()
.collect(Collectors.groupingBy(FeatureResourceRoleCodeDTO::getFeatureResourceId, Collectors.mapping(FeatureResourceRoleCodeDTO::getRoleCode, Collectors.toList())));
}
}

View File

@ -0,0 +1,44 @@
package cn.axzo.tyr.server.repository.dao;
import cn.axzo.basics.common.constant.enums.DeleteEnum;
import cn.axzo.tyr.server.repository.entity.SaasPageElement;
import cn.axzo.tyr.server.repository.entity.SaasPageElementFeatureResourceRelation;
import cn.axzo.tyr.server.repository.mapper.SaasPageElementMapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.stereotype.Repository;
import java.util.List;
import java.util.Objects;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/18
*/
@Repository
public class SaasPageElementDao extends ServiceImpl<SaasPageElementMapper, SaasPageElement> {
public void deleteAllByTerminal(String terminal) {
lambdaUpdate()
.eq(SaasPageElement::getTerminal, terminal)
.set(SaasPageElement::getIsDelete, DeleteEnum.DELETE.getValue())
.update();
}
public List<SaasPageElement> listByCodes(List<String> codes, String terminal) {
return lambdaQuery()
.eq(SaasPageElement::getTerminal, terminal)
.in(SaasPageElement::getCode, codes)
.list();
}
public List<SaasPageElement> listByGroupCodesAndExcludeIds(List<String> groupCodes, List<Long> excludeIds, String terminal, List<String> types) {
return lambdaQuery()
.eq(SaasPageElement::getTerminal, terminal)
.in(SaasPageElement::getGroupCode, groupCodes)
.in(CollectionUtils.isNotEmpty(types), SaasPageElement::getType, types)
.notIn(CollectionUtils.isNotEmpty(excludeIds), SaasPageElement::getId, excludeIds)
.list();
}
}

View File

@ -0,0 +1,49 @@
package cn.axzo.tyr.server.repository.dao;
import cn.axzo.basics.common.constant.enums.DeleteEnum;
import cn.axzo.pokonyan.config.mybatisplus.BaseEntity;
import cn.axzo.tyr.server.repository.entity.SaasPageElementFeatureResourceRelation;
import cn.axzo.tyr.server.repository.mapper.SaasPageElementFeatureResourceRelationMapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.stereotype.Repository;
import java.util.List;
import java.util.Objects;
/**
* @author likunpeng
* @version 1.0
* @date 2024/6/18
*/
@Repository
public class SaasPageElementFeatureResourceRelationDao extends ServiceImpl<SaasPageElementFeatureResourceRelationMapper, SaasPageElementFeatureResourceRelation> {
public List<SaasPageElementFeatureResourceRelation> listByPageElementCode(String pageElementCode, String terminal, List<Integer> types) {
return lambdaQuery()
.eq(SaasPageElementFeatureResourceRelation::getIsDelete, DeleteEnum.NORMAL.getValue())
.eq(SaasPageElementFeatureResourceRelation::getPageElementCode, pageElementCode)
.eq(SaasPageElementFeatureResourceRelation::getTerminal, terminal)
.in(CollectionUtils.isNotEmpty(types), SaasPageElementFeatureResourceRelation::getType, types)
.orderByDesc(BaseEntity::getId)
.list();
}
public List<SaasPageElementFeatureResourceRelation> listByUniCodeAndTerminal(List<String> featureResourceUniCodes, String terminal, List<Integer> types) {
return lambdaQuery()
.eq(SaasPageElementFeatureResourceRelation::getIsDelete, DeleteEnum.NORMAL.getValue())
.in(SaasPageElementFeatureResourceRelation::getFeatureResourceUniCode, featureResourceUniCodes)
.in(CollectionUtils.isNotEmpty(types), SaasPageElementFeatureResourceRelation::getType, types)
.eq(SaasPageElementFeatureResourceRelation::getTerminal, terminal)
.list();
}
public void deleteByTerminalAndUniCodes(String terminal, List<String> featureResourceUniCodes, List<Integer> types, Long operatorId) {
lambdaUpdate()
.eq(SaasPageElementFeatureResourceRelation::getTerminal, terminal)
.in(SaasPageElementFeatureResourceRelation::getFeatureResourceUniCode, featureResourceUniCodes)
.in(CollectionUtils.isNotEmpty(types), SaasPageElementFeatureResourceRelation::getType, types)
.set(SaasPageElementFeatureResourceRelation::getIsDelete, DeleteEnum.DELETE.getValue())
.set(Objects.nonNull(operatorId), SaasPageElementFeatureResourceRelation::getUpdateBy, operatorId)
.update();
}
}

View File

@ -34,7 +34,7 @@ public class DataObjectRule extends BaseOperatorEntity<DataObjectRule> implement
private String name;
/**
* 行级数据权限单选 1:仅本人数据 2:本人及下属数据 3:仅本部门数据 4:本部门及以下数据
* 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据
* 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据
*/
private Integer rowPermission;
/**

View File

@ -41,7 +41,7 @@ public class DataObjectRuleAttr extends BaseOperatorEntity<DataObjectRuleAttr> i
private Integer sort;
/**
* 字段值查看范围 1:仅本人数据 2:本人及下属数据 3:仅本部门数据 4:本部门及以下数据
* 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据
* 5:仅本单位数据 6:本单位及下级直属单位数据 7:本单位及下级协同直属+合作单位数据 8:本单位及以下协同直属+合作单位数据 9:本项目数据
* 10:同行级数据权限
*/
private Integer visibilityScope;

View File

@ -1,5 +1,7 @@
package cn.axzo.tyr.server.repository.entity;
import cn.axzo.tyr.client.common.enums.FeatureResourceType;
import cn.axzo.tyr.client.model.req.FeatureIdPair;
import lombok.Builder;
import lombok.Data;
@ -22,6 +24,18 @@ public class ProductFeatureQuery {
private String terminal;
private Integer workspaceJoinType;
//
private Set<Long> featureIds;
/**
* 菜单资源数节点类型
*/
private List<FeatureResourceType> featureResourceTypes;
private List<FeatureIdPair> featureIdPairs;
/**
* 区分新老菜单资源树
*/
private Integer type;
}

View File

@ -1,15 +1,20 @@
package cn.axzo.tyr.server.repository.entity;
import cn.axzo.pokonyan.config.mybatisplus.BaseEntity;
import cn.axzo.tyr.client.model.base.FeatureResourceExtraDO;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import com.baomidou.mybatisplus.extension.handlers.FastjsonTypeHandler;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.Getter;
import lombok.NoArgsConstructor;
import org.apache.commons.lang3.StringUtils;
import java.util.Collections;
import java.util.List;
import java.util.Objects;
import java.util.stream.Collectors;
/**
@ -23,15 +28,32 @@ import java.util.stream.Collectors;
@Data
@NoArgsConstructor
@AllArgsConstructor
@TableName("saas_feature_resource")
public class SaasFeatureResource extends BaseEntity<SaasFeature> {
@TableName(value = "saas_feature_resource", autoResultMap = true)
public class SaasFeatureResource extends BaseEntity<SaasFeatureResource> {
private static final long serialVersionUID = 1L;
/**
* 数据库默认的workspaceType
*/
public static final Long DEFAULT_WORKSPACE_TYPE = 0L;
/**
* 显示状态
*/
public static final Integer DISPLAY_STATUS = 1;
/**
* 隐藏状态
*/
public static final Integer HIDE_STATUS = 0;
/**
* 资源编码-权限码
* 废弃同步数据使用uniCode
*/
@Deprecated
private String featureCode;
/**
@ -112,7 +134,8 @@ public class SaasFeatureResource extends BaseEntity<SaasFeature> {
/**
* 扩展字段
*/
private String extra;
@TableField(value = "extra", typeHandler = FastjsonTypeHandler.class)
private FeatureResourceExtraDO extra;
/**
* 授权类型0-全部角色 1-指定角色
@ -156,5 +179,18 @@ public class SaasFeatureResource extends BaseEntity<SaasFeature> {
return StrUtil.split(this.path, ",").stream().filter(StringUtils::isNotBlank).map(Long::valueOf).collect(Collectors.toList());
}
@Getter
@AllArgsConstructor
public enum AuthType {
ALL_ROLE(0, "全部角色"),
ASSIGN_ROLE(1, "指定角色");
private Integer value;
private String desc;
public static boolean isAllRole(Integer authType) {
return Objects.equals(ALL_ROLE.getValue(), authType);
}
}
}

View File

@ -0,0 +1,58 @@
package cn.axzo.tyr.server.repository.entity;
import cn.axzo.pokonyan.config.mybatisplus.BaseEntity;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.*;
/**
* 页面元素表
*
* @author likunpeng
* @version 1.0
* @date 2024/6/18
*/
@Getter
@Setter
@ToString
@Builder
@EqualsAndHashCode(callSuper = true)
@TableName("saas_page_element")
public class SaasPageElement extends BaseEntity<SaasPageElement> {
/**
* 元素的组编码
*/
@TableField("group_code")
private String groupCode;
/**
* 页面元素编码
*/
@TableField("code")
private String code;
/**
* 页面元素名称
*/
@TableField("name")
private String name;
/**
* 页面元素类型PAGE:页面COMPONENT:组件
*/
@TableField("type")
private String type;
/**
* 页面路由地址
*/
@TableField("link_url")
private String linkUrl;
/**
* 所属端
*/
@TableField("terminal")
private String terminal;
}

View File

@ -0,0 +1,59 @@
package cn.axzo.tyr.server.repository.entity;
import cn.axzo.pokonyan.config.mybatisplus.BaseEntity;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.*;
/**
* 页面元素与菜单组件关系表
*
* @author likunpeng
* @version 1.0
* @date 2024/6/18
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
@Builder
@TableName(value = "saas_page_element_feature_resource_relation", autoResultMap = true)
public class SaasPageElementFeatureResourceRelation extends BaseEntity<SaasPageElementFeatureResourceRelation> {
/**
* 绑定类型0默认类型 1(页面默认路由)
* @see cn.axzo.tyr.client.common.enums.PageElementFeatureResourceRelationTypeEnum
*/
@TableField("type")
private Integer type;
/**
* 创建人
*/
@TableField("create_by")
private Long createBy;
/**
* 更新人
*/
@TableField("update_by")
private Long updateBy;
/**
* 页面元素code
*/
@TableField("page_element_code")
private String pageElementCode;
/**
* 菜单组件code
*/
@TableField("feature_resource_uni_code")
private String featureResourceUniCode;
/**
* 所属端
*/
@TableField("terminal")
private String terminal;
}

View File

@ -1,7 +1,10 @@
package cn.axzo.tyr.server.repository.entity;
import cn.axzo.pokonyan.config.mybatisplus.BaseEntity;
import com.alibaba.fastjson.JSONArray;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableName;
import com.baomidou.mybatisplus.extension.handlers.FastjsonTypeHandler;
import lombok.EqualsAndHashCode;
import lombok.Getter;
import lombok.Setter;
@ -23,6 +26,9 @@ import java.util.Objects;
@TableName("saas_pgroup_permission_relation")
public class SaasPgroupPermissionRelation extends BaseEntity<SaasPgroupPermissionRelation> {
public static final Integer OLD_FEATURE = 0;
public static final Integer NEW_FEATURE = 1;
/**
* 权限集id
@ -43,6 +49,26 @@ public class SaasPgroupPermissionRelation extends BaseEntity<SaasPgroupPermissio
*/
private Long updateBy;
/**
* 关联类型0saas_feature,1:saas_feature_resource
* 暂时的因为cms端会有灰度数据从saas_feature和saas_feature_resource出
*/
private Integer type;
/**
* 菜单资源类型1-菜单 2-页面 3-应用入口 4-组件
* 冗余菜单资源类型是在cms端查询菜单和页面时方便快速查询
* type = 0时featureType是saas_feature表的featureType
* type = 1时featureType是saas_feature_resource表的featureType
* 后面会全部切换到saas_feature_resource
* FeatureResourceType
*/
private Integer featureType;
/**
* featureId所在端
*/
private String terminal;
/**
* 获取主键值

View File

@ -47,6 +47,16 @@ public class SaasProductModuleFeatureRelation extends BaseEntity<SaasProductModu
*/
private Integer type;
/**
* 功能资源类型 默认为0
* @see cn.axzo.tyr.client.common.enums.FeatureResourceType
*/
private Integer featureType;
/**
*
*/
private String terminal;
/**
* 获取主键值

View File

@ -1,13 +1,10 @@
package cn.axzo.tyr.server.repository.mapper;
import cn.axzo.tyr.server.model.FeatureResourceRoleCodeDTO;
import cn.axzo.tyr.server.repository.entity.SaasFeatureResource;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Update;
import java.util.List;
/**
* <p>
* 功能资源表 Mapper 接口
@ -22,6 +19,4 @@ public interface SaasFeatureResourceMapper extends BaseMapper<SaasFeatureResourc
" SET path = REPLACE(path, #{oldPath}, #{newPath})" +
" WHERE is_delete = 0 AND path LIKE CONCAT(#{oldPath}, '%')")
void replacePath(@Param("oldPath") String oldPath, @Param("newPath") String newPath);
List<FeatureResourceRoleCodeDTO> listRoleCodes(@Param("ids") List<Long> ids);
}

View File

@ -0,0 +1,9 @@
package cn.axzo.tyr.server.repository.mapper;
import cn.axzo.tyr.server.repository.entity.SaasPageElementFeatureResourceRelation;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
public interface SaasPageElementFeatureResourceRelationMapper extends BaseMapper<SaasPageElementFeatureResourceRelation> {
}

View File

@ -0,0 +1,9 @@
package cn.axzo.tyr.server.repository.mapper;
import cn.axzo.tyr.server.repository.entity.SaasPageElement;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
public interface SaasPageElementMapper extends BaseMapper<SaasPageElement> {
}

View File

@ -26,8 +26,6 @@ public interface SaasRoleMapper extends BaseMapper<SaasRole> {
List<SaasRole> listForOUWorkspace(Long ouId, Long workspaceId, Integer workspaceJoinType);
List<SaasRole> listRoleByFeatures(@Param("featureIds") Set<Long> featureIds);
List<RoleFeatureRelation> listFeatureByIds(@Param("roleIds") Set<Long> roleIds, @Param("featureIds") Set<Long> featureIds);
}

View File

@ -5,6 +5,7 @@ import cn.axzo.tyr.client.model.req.ResourceSyncReq;
import cn.axzo.tyr.client.model.res.FeatureResourceTreeNode;
import java.util.List;
import java.util.Map;
/**
* 功能资源同步服务
@ -20,4 +21,6 @@ public interface FeatureResourceSyncService {
void syncFromBase(ResourceSyncReq req);
List<FeatureResourceTreeNode> getBaseTree(GetFeatureResourceTreeReq req);
Map<Long, String> listFeatureCodeByFeatureResourceIds(List<Long> featureResourceIds);
}

View File

@ -2,6 +2,13 @@ package cn.axzo.tyr.server.service;
import cn.axzo.tyr.client.model.res.IdentityAuthRes;
import cn.axzo.tyr.server.model.PermissionCacheKey;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
import java.util.Set;
/**
* 授权缓存服务
@ -23,4 +30,128 @@ public interface PermissionCacheService {
/** 标记缓存暂时不可用 - 等缓存全部失效 **/
void markTempDisable(PermissionCacheKey key);
/**
* 缓存权限码跟角色的信息采用set数据结构
* redisKeyfeatureCode
* redisValue: roleId
* @param param
*/
void cachePermissionRole(CachePermissionRoleParam param);
/**
* 根据权限码查询对应的角色信息
* @param param
* @return
*/
List<PermissionRole> listPermissionRole(ListPermissionRoleParam param);
/**
* 缓存权限码跟产品和单位类型的信息采用set数据结构
* redisKey: featureCode
* redisValue: 产品信息
* @param param
*/
void cachePermissionProduct(CachePermissionProductParam param);
/**
* 根据权限码查询对应的产品信息
* 一个权限点对应的产品数据比较少一般10多个所以没有聚合返回方便排查哪些权限点已经在redis中不用从数据库中查询
* @param param
* @return
*/
List<PermissionProduct> listPermissionProduct(ListPermissionProductParam param);
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class HasPermissionRoleParam {
private List<String> featureCodes;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class ListPermissionRoleParam {
private List<String> featureCodes;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class CachePermissionRoleParam {
private List<PermissionRole> permissionRoles;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class PermissionRole {
/**
* 权限码
*/
private String featureCode;
/**
* 角色id
*/
private List<Long> roleIds;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class ListPermissionProductParam {
private List<String> featureCodes;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class CachePermissionProductParam {
private List<PermissionProduct> permissionProducts;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class PermissionProduct {
/**
* 权限码
*/
private String featureCode;
/**
* 产品信息
*/
private List<Product> products;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class Product {
/**
* 产品id
*/
private Long productId;
/**
* 单位类型
*/
private Integer ouType;
}
}

View File

@ -4,10 +4,12 @@ import cn.axzo.tyr.client.model.req.NavTreeReq;
import cn.axzo.tyr.client.model.req.PagePermissionReq;
import cn.axzo.tyr.client.model.req.PagePermissionResp;
import cn.axzo.tyr.client.model.req.PermissionCheckReq;
import cn.axzo.tyr.client.model.req.TreePermissionReq;
import cn.axzo.tyr.client.model.req.TreeProductFeatureResourceReq;
import cn.axzo.tyr.client.model.res.FeatureResourceDTO;
import cn.axzo.tyr.client.model.res.NavTreeResp;
import cn.axzo.tyr.client.model.res.ProductFeatureResourceResp;
import cn.axzo.tyr.client.model.res.TreePermissionResp;
import cn.axzo.tyr.server.repository.entity.SaasFeatureResource;
import java.util.List;
@ -22,6 +24,7 @@ import java.util.List;
public interface PermissionQueryService {
/** 获取导航菜单页面 **/
@Deprecated
List<NavTreeResp> getNavTree(NavTreeReq req);
boolean hasPermission(PermissionCheckReq req);
@ -41,4 +44,11 @@ public interface PermissionQueryService {
* @return
*/
List<FeatureResourceDTO> listFeatureResource(TreeProductFeatureResourceReq request);
/**
* 查询人的权限点树
* @param req
* @return
*/
List<TreePermissionResp> treePermission(TreePermissionReq req);
}

View File

@ -1,11 +1,14 @@
package cn.axzo.tyr.server.service;
import cn.axzo.foundation.page.PageResp;
import cn.axzo.framework.domain.web.result.ApiResult;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationSearchReq;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationUpdateReq;
import cn.axzo.tyr.client.model.product.ProductFeatureRelationVO;
import cn.axzo.tyr.client.model.req.PageProductFeatureRelationReq;
import cn.axzo.tyr.server.repository.entity.ProductFeatureQuery;
import cn.axzo.tyr.server.repository.entity.SaasProductModuleFeatureRelation;
import com.baomidou.mybatisplus.extension.service.IService;
import java.util.List;
import java.util.Map;
@ -17,11 +20,20 @@ import java.util.Set;
* @author wangli
* @since 2023/9/7 14:26
*/
public interface ProductFeatureRelationService {
public interface ProductFeatureRelationService extends IService<SaasProductModuleFeatureRelation> {
ApiResult<List<ProductFeatureRelationVO>> featureList(ProductFeatureRelationSearchReq req);
ApiResult<Boolean> updateFeatureRelation(List<ProductFeatureRelationUpdateReq> req);
/**
* 更新产品功能权限关系仅支持saas_feature_resource功能点
*
* @param req
*/
void updateFeatureResourceRelation(List<ProductFeatureRelationUpdateReq> req, int relationType);
void removeFeatureResourceRelationByProductIdAndType(Long productId, int relationType);
ApiResult<List<ProductFeatureRelationVO>> featureListByProduct(List<Long> productIds);
/**
@ -37,4 +49,16 @@ public interface ProductFeatureRelationService {
boolean refreshFeature(Integer workspaceType, Long productId);
void removeByProductId(Long productId);
/**
* 新增编辑产品时做新老产品判断时使用
*
* @param productId
* @return
*/
SaasProductModuleFeatureRelation getOneByProductId(Long productId);
PageResp<SaasProductModuleFeatureRelation> page(PageProductFeatureRelationReq param);
List<SaasProductModuleFeatureRelation> list(PageProductFeatureRelationReq param);
}

View File

@ -0,0 +1,68 @@
package cn.axzo.tyr.server.service;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
public interface ProductPermissionCacheService {
List<PermissionDTO> list(ListProductPermissionParam param);
void store(StoreProductPermissionParam param);
List<Long> hasProductIds(HasProductPermissionParam param);
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class HasProductPermissionParam {
private List<Long> productIds;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class StoreProductPermissionParam {
private List<ProductPermission> productPermissions;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class ProductPermission {
private Long productId;
private List<PermissionDTO> permissions;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class ListProductPermissionParam {
private List<Long> productIds;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class PermissionDTO {
/**
* 产品关联的字典 Code 原值
*/
private String dictCode;
private Long featureId;
private String featureCode;
}
}

View File

@ -26,7 +26,7 @@ public interface ProductService {
ApiPageResult<ProductVO> page(ProductSearchPageReq req);
ApiResult<ProductVO> getById(Long id);
ApiResult<ProductVO> getById(Long id, Boolean queryFeatureScope);
ApiResult<ProductVO> add(ProductAddReq req);

View File

@ -0,0 +1,84 @@
package cn.axzo.tyr.server.service;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
import java.util.Set;
public interface RolePermissionCacheService {
List<PermissionDTO> list(ListRolePermissionParam param);
/**
* redisKey:roleId
* redisValue:permission
* @param param
*/
void store(StoreRolePermissionParam param);
List<Long> hasRoleIds(HasRolePermissionParam param);
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class HasRolePermissionParam {
private List<Long> roleIds;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class StoreRolePermissionParam {
private List<RolePermission> rolePermissions;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class RolePermission {
private Long roleId;
private List<PermissionDTO> permissions;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class ListRolePermissionParam {
private List<Long> roleIds;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class RolePermissionDTO {
private Long roleId;
private List<PermissionDTO> permissions;
}
@Data
@Builder
@NoArgsConstructor
@AllArgsConstructor
class PermissionDTO {
private Long featureId;
private String featureCode;
/**
* 资源所属端
*/
private String terminal;
}
}

View File

@ -4,12 +4,13 @@ import cn.axzo.foundation.dao.support.wrapper.CriteriaField;
import cn.axzo.foundation.dao.support.wrapper.Operator;
import cn.axzo.foundation.page.IPageReq;
import cn.axzo.framework.domain.page.PageResp;
import cn.axzo.tyr.client.common.enums.FeatureResourceType;
import cn.axzo.tyr.client.model.enums.IdentityType;
import cn.axzo.tyr.client.model.req.ChangeGroupLeaderRoleReq;
import cn.axzo.tyr.client.model.req.FeatureIdPair;
import cn.axzo.tyr.client.model.req.FeatureRoleRelationReq;
import cn.axzo.tyr.client.model.req.QueryByIdentityIdTypeReq;
import cn.axzo.tyr.client.model.req.QueryRoleByNameReq;
import cn.axzo.tyr.client.model.req.QuerySaasRoleGroupReq;
import cn.axzo.tyr.client.model.req.QuerySaasRoleReq;
import cn.axzo.tyr.client.model.req.RoleWithUserQueryReq;
import cn.axzo.tyr.client.model.res.FeatureRoleRelationResp;
@ -25,10 +26,9 @@ import cn.axzo.tyr.client.model.vo.SaasRoleGroupCodeVO;
import cn.axzo.tyr.client.model.vo.SaasRoleVO;
import cn.axzo.tyr.client.model.vo.SaveOrUpdateRoleVO;
import cn.axzo.tyr.server.model.RoleWithFeature;
import cn.axzo.tyr.server.repository.entity.SaasFeature;
import cn.axzo.tyr.server.repository.entity.SaasRole;
import cn.axzo.tyr.server.repository.entity.SaasRoleWithUser;
import cn.axzo.tyr.server.service.impl.TyrSaasAuthServiceImpl;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.IService;
import lombok.AllArgsConstructor;
import lombok.Data;
@ -66,17 +66,6 @@ public interface RoleService extends IService<SaasRole> {
List<SaasRoleWithUser> listRoleUserByPermissionGroup(List<Long> permissionGroupIdList, Set<Long> workspaceIds);
/**
* * 过滤角色的按钮权限
* * 1.分组上的适用单位类型过滤
* * 2.角色的例外过滤
* @param role
* @param userRoleInfoMap
* @return 按钮级别权限点ID
*/
Set<Long> filterPermissionPoint(Set<SaasRoleVO> role, TyrSaasAuthServiceImpl.OUWRoleInfo userRoleInfoMap);
/**
* 通过角色名字获取角色信息
* @param req
@ -87,17 +76,6 @@ public interface RoleService extends IService<SaasRole> {
/** 分页查询角色含用户 **/
PageResp<RoleWithUserRes> queryRoleWithUser(RoleWithUserQueryReq req);
/**
* 通过角色类型获取角色
* @param req
* @param roleTypes
* @return
*/
List<SaasRoleVO> queryRoleByRoleTypes(QueryByIdentityIdTypeReq req, List<String> roleTypes);
List<SaasRole> listForOUWorkspace(Long ouId, Long workspaceId, Integer workspaceJoinType);
List<SaasRoleAndGroupVO> queryInitRoleByWorkspaceId(String workspaceType);
/**
@ -106,8 +84,6 @@ public interface RoleService extends IService<SaasRole> {
*/
void deleteRole(DeleteRoleVO deleteRoleParam);
List<SaasRole> queryRoleByFeatures(Set<Long> matchedFeatureIds);
List<SaasRole> getByIds(Set<Long> ids);
List<SaasRoleCategoryVO> queryByCategoryCode(List<String> categoryCodes);
@ -127,6 +103,8 @@ public interface RoleService extends IService<SaasRole> {
FeatureRoleRelationResp queryFeatureRoleRelation(Long featureId);
List<SaasFeature> validFeature(List<Long> featureIds);
@SuperBuilder
@Data
@NoArgsConstructor
@ -160,6 +138,9 @@ public interface RoleService extends IService<SaasRole> {
@CriteriaField(field = "id", operator = Operator.NE)
private Long idNE;
/**
* 权限点从saas_feature_resource表查询
*/
@CriteriaField(ignore = true)
private Boolean needPermission;
@ -168,6 +149,40 @@ public interface RoleService extends IService<SaasRole> {
@CriteriaField(ignore = true)
private Boolean needRoleUser;
/**
* 当前非oms和政务端的权限存储在saas_feature
* 权限点从saas_feature表查询
*/
@CriteriaField(ignore = true)
private Boolean needPermissionOld;
/**
* 根据权限点id过滤
*/
@CriteriaField(ignore = true)
private List<Long> featureIds;
@CriteriaField(ignore = true)
private Boolean needPermissionRelation;
/**
* 查询菜单树节点类型
*/
@CriteriaField(ignore = true)
private List<FeatureResourceType> featureResourceTypes;
/**
* 新旧权限点needPermissionRelation = true时最好带上因为新旧权限点会有冲突的情况发生
*/
@CriteriaField(ignore = true)
private Integer type;
/**
* 查询权限点时会根据端过滤增加效率目前只有CMS端的新版本才冗余了端
*/
@CriteriaField(ignore = true)
private String terminal;
}
@SuperBuilder

View File

@ -1,12 +1,16 @@
package cn.axzo.tyr.server.service;
import cn.axzo.foundation.page.PageResp;
import cn.axzo.tyr.client.model.req.DeleteFeatureResourceReq;
import cn.axzo.tyr.client.model.req.FeatureResourceTreeSaveReq;
import cn.axzo.tyr.client.model.req.GetFeatureResourceTreeReq;
import cn.axzo.tyr.client.model.req.PageSaasFeatureResourceReq;
import cn.axzo.tyr.client.model.res.FeatureResourceTreeNode;
import cn.axzo.tyr.client.model.res.SaasFeatureResourceResp;
import cn.axzo.tyr.server.model.ResourcePermission;
import cn.axzo.tyr.server.model.ResourcePermissionQueryDTO;
import cn.axzo.tyr.server.repository.entity.SaasFeatureResource;
import cn.axzo.tyr.client.model.req.FeatureResourceTreeSaveReq;
import io.swagger.models.auth.In;
import com.baomidou.mybatisplus.extension.service.IService;
import java.util.List;
import java.util.Set;
@ -18,15 +22,12 @@ import java.util.Set;
* @author: ZhanSiHu
* @date: 2024/4/3 10:17
*/
public interface SaasFeatureResourceService {
public interface SaasFeatureResourceService extends IService<SaasFeatureResource> {
Long saveOrUpdateMenu(FeatureResourceTreeSaveReq req);
void updateFeatureAuthType(Long featureId, Integer authType);
/**递归的**/
List<SaasFeatureResource> listDescendant(Long featureId);
/**递归的**/
List<SaasFeatureResource> batchListDescendant(List<Long> featureIds);
@ -34,9 +35,6 @@ public interface SaasFeatureResourceService {
FeatureResourceTreeNode getTreeFeatureDescendant(Long featureId, Integer featureType);
/**删除指定菜单**/
void deleteMenuFeature(Long featureId, Long operatorId);
/**菜单重排序**/
void reorderMenuFeature(Long featureId, Integer offset);
@ -53,7 +51,12 @@ public interface SaasFeatureResourceService {
Set<Long> listAuthFree();
List<SaasFeatureResource> listNavMenu(String terminal);
List<SaasFeatureResource> listByParentIdAndTerminalAndIds(Long parentId, String terminal, List<Long> featureIds);
List<SaasFeatureResourceResp> list(PageSaasFeatureResourceReq param);
PageResp<SaasFeatureResourceResp> page(PageSaasFeatureResourceReq param);
void deleteFeatureResource(DeleteFeatureResourceReq param);
}

View File

@ -0,0 +1,15 @@
package cn.axzo.tyr.server.service;
import cn.axzo.foundation.page.PageResp;
import cn.axzo.tyr.client.model.req.PageElementFeatureResourceRelationReq;
import cn.axzo.tyr.server.repository.entity.SaasPageElementFeatureResourceRelation;
import com.baomidou.mybatisplus.extension.service.IService;
import java.util.List;
public interface SaasPageElementFeatureResourceRelationService extends IService<SaasPageElementFeatureResourceRelation> {
List<SaasPageElementFeatureResourceRelation> list(PageElementFeatureResourceRelationReq param);
PageResp<SaasPageElementFeatureResourceRelation> page(PageElementFeatureResourceRelationReq param);
}

Some files were not shown because too many files have changed in this diff Show More