# JeePlus Cloud v9.0 — 项目架构百科 (Repo Wiki)

> **项目名称**: jeeplus cloud  
> **组织**: org.jeeplus  
> **版本**: 9.0  
> **架构模式**: Spring Cloud 微服务 + 多模块 Maven 工程  
> **JDK**: 1.8  
> **构建工具**: Maven  

---

## 目录

1. [项目总览与拓扑结构](#1-项目总览与拓扑结构)
2. [Maven 模块全景图](#2-maven-模块全景图)
3. [基础设施与中间件](#3-基础设施与中间件)
4. [各微服务详细分析](#4-各微服务详细分析)
   - [4.1 jeeplus-gateway — API 网关](#41-jeeplus-gateway--api-网关)
   - [4.2 jeeplus-auth — 认证中心](#42-jeeplus-auth--认证中心)
   - [4.3 jeeplus-api — 接口定义层](#43-jeeplus-api--接口定义层)
   - [4.4 jeeplus-common — 公共组件层](#44-jeeplus-common--公共组件层)
   - [4.5 jeeplus-modules — 业务模块层](#45-jeeplus-modules--业务模块层)
5. [核心基类体系](#5-核心基类体系)
6. [常用工具类](#6-常用工具类)
7. [服务间调用与依赖关系](#7-服务间调用与依赖关系)
8. [接口规范](#8-接口规范)
9. [权限控制逻辑](#9-权限控制逻辑)
10. [关键常量与缓存设计](#10-关键常量与缓存设计)

---

## 1. 项目总览与拓扑结构

```
┌──────────────────────────────────────────────────────────┐
│                      Nacos (8848)                        │
│          服务注册/发现 + 配置中心                           │
└──────────────────────┬───────────────────────────────────┘
                       │
┌──────────────────────┴───────────────────────────────────┐
│                   Sentinel (8858)                         │
│                  流量控制 + 熔断降级                         │
└──────────────────────┬───────────────────────────────────┘
                       │
                       ▼
┌──────────────────────────────────────────────────────────┐
│               jeeplus-gateway (:8088)                     │
│           Spring Cloud Gateway + WebFlux                  │
│         路由转发 / JWT鉴权 / Swagger聚合                    │
└──────────────────────┬───────────────────────────────────┘
                       │
          ┌────────────┼────────────┬──────────────┐
          ▼            ▼            ▼              ▼
┌──────────────┐ ┌──────────┐ ┌──────────┐ ┌──────────────────┐
│ jeeplus-auth │ │jeeplus-  │ │jeeplus-  │ │ jeeplus-modules   │
│   (:9211)    │ │ system   │ │ flowable │ │ (assess, finance, │
│ 登录/认证     │ │          │ │ 工作流    │ │  human, ccpm …)   │
└──────────────┘ └──────────┘ └──────────┘ └──────────────────┘
                       │
                       ▼
            ┌──────────────────┐
            │  Spring Boot     │
            │  Admin (:8989)   │
            │  服务监控          │
            └──────────────────┘
```

**请求链路**:
```
客户端请求 → Gateway(:8088) → JWTFilter 鉴权 → 路由转发 → 目标微服务
                                      │
                            Redis (token 校验/刷新)
```

---

## 2. Maven 模块全景图

```
jeeplus (POM, parent)
├── jeeplus-gateway                          [网关服务 - Spring Boot]
├── jeeplus-auth                             [认证服务 - Spring Boot]
├── jeeplus-api (POM)                        [接口定义聚合]
│   ├── jeeplus-system-api                   [系统API: IUserApi, ITenantApi, BaseDTO, TreeDTO]
│   ├── jeeplus-public-modules-api           [公共模块API: IWorkAttachmentApi]
│   ├── jeeplus-finance-api                  [财务API: ICwProjectReportApi]
│   └── jeeplus-file-api                     [文件API: IFileApi]
├── jeeplus-common (POM)                     [公共组件聚合]
│   ├── jeeplus-common-core                  [核心: Entity/DTO基类, Redis, Excel, Query, 常量]
│   ├── jeeplus-common-log                   [日志: AOP切面, @ApiLog注解]
│   ├── jeeplus-common-mybatis-plus          [ORM: MyBatis-Plus配置, 分页, 多租户]
│   ├── jeeplus-common-security              [安全: JWT, Spring Security, TokenProvider]
│   └── jeeplus-common-swagger               [文档: Knife4j/Swagger配置]
└── jeeplus-modules (POM)                    [业务模块聚合]
    ├── jeeplus-system                       [★核心: 用户/角色/菜单/租户/部门/数据权限]
    ├── jeeplus-flowable                     [★工作流: Flowable引擎]
    ├── jeeplus-file                         [文件存储: MinIO/OSS]
    ├── jeeplus-finance                      [财务管理]
    ├── jeeplus-assess                       [评估考核]
    ├── jeeplus-human                        [人力资源管理]
    ├── jeeplus-ccpm                         [项目管理]
    ├── jeeplus-consult                      [培训咨询]
    ├── jeeplus-public-modules               [公共功能: 收藏/合同/知识库/会议室/抽奖/物料等]
    ├── jeeplus-centrecareful                [中审管理]
    ├── jeeplus-psi-management               [PSI管理]
    ├── jeeplus-devtools                     [开发工具]
    ├── jeeplus-ureport                      [报表引擎]
    ├── jeeplus-wps                          [WPS集成]
    ├── jeeplus-xxl-job-admin                [XXL-Job调度中心]
    ├── jeeplus-xxl-job-executor-sample      [XXL-Job执行器]
    ├── jeeplus-admin-server                 [Spring Boot Admin监控]
    └── jeeplus-test                         [测试模块]
```

---

## 3. 基础设施与中间件

| 组件 | 版本 | 用途 |
|------|------|------|
| Spring Boot | 2.4.4 | 微服务基础框架 |
| Spring Cloud | 2020.0.2 (Ilford) | 微服务治理 |
| Spring Cloud Alibaba | 2021.1 | 阿里云微服务生态 |
| Nacos | 2.0.0 | 服务注册/发现 + 配置中心 |
| Sentinel | 2.2.5.RELEASE | 流量防卫兵(限流/熔断) |
| Spring Cloud Gateway | — | API 网关 |
| MyBatis-Plus | 3.4.2 | ORM 增强框架 |
| Druid | 1.2.8 | 数据库连接池 |
| dynamic-datasource | 3.5.1 | 多数据源 |
| Redis (Spring Data) | — | 分布式缓存(token/字典/菜单) |
| MinIO | 8.0.3 | 对象存储(自建) |
| Aliyun OSS | 3.13.1 | 对象存储(阿里云) |
| Flowable | 6.7.2 | 工作流引擎 |
| Liquibase | 4.3.5 | 数据库版本管理 |
| XXL-Job | 2.3.1 | 分布式定时任务 |
| Knife4j (Swagger) | 2.0.8 | API 文档 |
| MapStruct | 1.4.2 | 对象映射转换 |
| Lombok | 1.18.24 | 代码简化 |
| Hutool | 5.7.13 | Java 工具包 |
| Guava | 29.0-jre | 集合/缓存工具 |
| EasyExcel | 3.1.1 | Excel 读写 |
| Auth0 JWT | 3.4.0 | JWT Token 处理 |
| Spring Boot Admin | 2.5.1 | 服务监控 |
| UReport | 2.2.9 | 报表引擎 |
| CAS Client | 3.5.1 | 单点登录客户端 |
| Easypoi | 4.3.0 | POI 工具 |

---

## 4. 各微服务详细分析

### 4.1 jeeplus-gateway — API 网关

**端口**: 8088  
**服务名**: `jeeplus-gateway`  
**技术栈**: Spring Cloud Gateway + WebFlux + Spring Security Reactive

#### 目录结构

```
jeeplus-gateway/src/main/java/com/jeeplus/gateway/
├── JeeplusGatewayApplication.java    # 启动类 (排除DataSource/MyBatisPlus自动配置)
├── config/
│   ├── SecurityConfiguration.java    # WebFlux安全配置 (白名单/认证规则)
│   └── SwaggerProvider.java          # Swagger资源聚合
├── controller/
│   └── SwaggerResourceController.java # Swagger文档入口
├── filter/
│   └── JWTFilter.java                # WebFlux JWT过滤器 (Order=-300)
├── handler/
│   └── GatewayExceptionHandler.java  # 统一异常处理 (ErrorWebExceptionHandler)
├── security/
│   └── TokenProvider.java            # 网关层Token生成/校验/刷新
├── service/
│   └── ...                           # 网关业务服务
└── excepiton/
    ├── JwtAccessDeniedHandler.java
    └── JwtAuthenticationEntryPoint.java
```

#### 核心机制

**SecurityConfiguration** 安全规则:
- 使用 `@EnableWebFluxSecurity` + `@EnableReactiveMethodSecurity`
- 从 `ignore.whiteList` 配置读取白名单 URL
- `/api/**` 路径需要认证
- `/management/**` (健康检查) 放行
- OPTIONS 预检请求放行

**JWTFilter** (网关层):
- 从请求中解析 token (query param > header > cookie)
- 从 Redis `user:cache:token` 校验 token
- Token 过期时 **自动刷新** (重新生成 accessToken 并更新 Redis)
- 刷新 Redis 中 token 和在线用户的过期时间
- 将认证信息注入 `ReactiveSecurityContextHolder`

**GatewayExceptionHandler**:
- 统一处理: `NotFoundException`, `ConnectTimeoutException`, `AccessDeniedException`
- 参数校验异常: `MethodArgumentNotValidException`, `BindException`
- 返回 JSON 格式错误信息

**依赖**:
```
spring-cloud-starter-gateway          # 网关核心
spring-cloud-starter-alibaba-nacos-discovery  # Nacos注册
spring-cloud-starter-alibaba-nacos-config     # Nacos配置
spring-cloud-starter-alibaba-sentinel         # Sentinel
spring-cloud-alibaba-sentinel-gateway         # Sentinel网关
spring-boot-starter-security                  # 安全
spring-boot-starter-actuator                  # 监控端点
springfox-boot-starter                        # Swagger
kaptcha                                      # 验证码
hutool-all                                   # 工具
jeeplus-system-api                           # 系统API(Feign)
```

---

### 4.2 jeeplus-auth — 认证中心

**端口**: 9211  
**服务名**: `jeeplus-auth`  
**技术栈**: Spring Boot + Spring Security + JWT

#### 目录结构

```
jeeplus-auth/src/main/java/com/jeeplus/auth/
├── JeeplusAuthApplication.java      # 启动类 (@EnableCaching)
├── config/
│   └── DingTalkProperties.java      # 钉钉多租户配置
├── controller/
│   ├── LoginController.java         # 登录核心控制器 (694行)
│   └── app/                         # 移动端控制器
├── model/
│   └── LoginForm.java               # 登录表单
└── service/
    └── DingTalkAuthService.java     # 钉钉AuthCode授权服务
```

#### 登录方式汇总

| 接口 | 路径 | 说明 |
|------|------|------|
| 账号密码登录 | `POST /user/login` | 标准账号密码 + 验证码 + 单一登录校验 |
| 微信登录 | `POST /user/sys/wxLogin` | 通过 openId 免密登录 |
| 钉钉免登 | `POST /user/sys/ddLogin` | 钉钉 ddId 免密登录 |
| 钉钉授权登录 | `POST /user/sys/dingtalk/login` | 钉钉 authCode OAuth2 登录 |
| 钉钉绑定登录 | `POST /user/sys/dingtalk/bindLogin` | 首次钉钉用户绑定系统账号 |
| CAS单点登录 | `GET /user/casLogin` | CAS ticket 验证 |
| 退出登录 | `GET /user/logout` | 清除 Redis token + 钉钉解绑 |
| 获取验证码 | `GET /user/getCode` | Hutool 图形验证码 |

#### 登录流程

```
1. 客户端提交 LoginForm (username/password/code/uuid)
2. 检查 Redis 登录失败次数 (超过5次需要验证码, 超过10次禁止登录)
3. Spring Security AuthenticationManager.authenticate()
4. 调用 IUserApi.getByLoginName() 获取用户信息
5. 单一登录检查: IUserApi.isEnableLogin()
6. 特殊规则: 樊莉↔黄玮 互斥登录
7. 生成 JWT Token → 存入 Redis (user:cache:token)
8. 在线用户列表存入 Redis (user:cache:online:users)
9. 更新用户最后登录信息 (IP/时间)
```

**依赖**:
```
jeeplus-system-api           # 系统API(Feign调用User/Tenant)
jeeplus-common-security      # 公共安全模块(JWT/SecurityUtils)
jeeplus-common-swagger       # Swagger文档
jeeplus-common-log           # 日志AOP
spring-boot-starter-web      # Web MVC
nacos-discovery/nacos-config # Nacos
sentinel                     # Sentinel
actuator + admin-client      # 监控
cas-client-core              # CAS单点登录
```

---

### 4.3 jeeplus-api — 接口定义层

所有微服务间的 **Feign 调用契约** 都定义在此层。每个 API 模块包含:
- `feign/` — FeignClient 接口
- `factory/` — FallbackFactory 降级工厂
- `domain/` — 共享领域对象
- `service/dto/` — DTO 传输对象

#### API 模块清单

| 模块 | 核心 Feign 接口 | 服务提供者 | 主要功能 |
|------|----------------|-----------|---------|
| jeeplus-system-api | IUserApi, ITenantApi | jeeplus-system | 用户CRUD, 权限查询, 租户 |
| jeeplus-system-api | (flowable工厂) | 各业务模块 | FlowableApi, AssessApi, CcpmApi, FinanceApi, HumanApi, ConsultApi, PsiManagementApi, ZsApi |
| jeeplus-file-api | IFileApi | jeeplus-file | 文件上传下载 |
| jeeplus-finance-api | ICwProjectReportApi | jeeplus-finance | 财务项目报告 |
| jeeplus-public-modules-api | IWorkAttachmentApi | jeeplus-public-modules | 工作附件 |

#### IUserApi 核心方法 (FeignClient)

```
FeignClient(name = "jeeplus-system", path = "/feign/sys/user")
├── 用户查询: getByLoginName(), getByOpenId(), getByDdId(), getById(), getUserDTOByName()
├── 权限查询: getPermissions(), getDataRuleList()
├── 在线管理: isEnableLogin(), getOnLineUserList()
├── 用户更新: updateUser(), saveOrUpdate(), updateUserById(), updateUserUpPassword()
├── 短信发送: sendRandomCodes(), sendEntryRandomCodes()
├── 文件操作: getFileDir(), delFile()
├── 认证相关: getCertListByUserId(), addDefaultSignatureCount()
└── 批量查询: findListByPostId(), findListByRoleId(), findListByOfficeId(), findListByCompanyId()
```

#### ITenantApi

```
FeignClient(name = "jeeplus-system")
└── getCurrentTenantId() → 从请求上下文获取当前租户ID
```

#### 核心 DTO 基类

**BaseDTO<T>** (`jeeplus-system-api`):
```
字段: taskId, procInsId, processDefinitionId (流程相关)
     id, createTime, createBy(UserDTO), updateTime, updateBy(UserDTO)
     delFlag, tenantDTO(TenantDTO)
```

**TreeDTO<T>** extends BaseDTO:
```
字段: parent(T), children(List<T>), parentIds, name, sort
方法: getParentId(), getParentName(), getRootId()="0"
```

---

### 4.4 jeeplus-common — 公共组件层

#### 4.4.1 jeeplus-common-core — 核心模块

**目录结构**:
```
jeeplus-common-core/src/main/java/com/jeeplus/
├── core/
│   ├── annotation/JeeplusCloudApplication.java  # 组合注解(@EnableDiscoveryClient+@EnableFeignClients+@EnableAsync)
│   ├── domain/BaseEntity.java                   # 实体基类
│   ├── domain/TreeEntity.java                   # 树形实体基类
│   ├── domain/TreeMapper.java                   # 树形Mapper基类
│   ├── dto/DragNode.java                        # 拖拽排序DTO
│   ├── mapstruct/EntityWrapper.java             # MapStruct DTO↔Entity映射
│   ├── mapstruct/TreeWrapper.java               # 树形映射(含parent转换)
│   ├── query/Query.java                         # @Query 查询注解
│   ├── query/QueryType.java                     # 查询类型枚举
│   └── query/QueryWrapperGenerator.java         # 动态查询条件构建器
├── common/
│   ├── constant/AppNameConstants.java           # 服务名常量
│   ├── constant/CacheNames.java                 # 缓存Key常量
│   ├── constant/ErrorConstants.java             # 错误消息常量
│   ├── constant/CommonConstants.java            # 通用常量
│   ├── excel/EasyExcelUtils.java                # EasyExcel工具
│   ├── excel/ExcelListener.java                 # Excel读取监听器
│   ├── excel/annotation/                        # Excel注解(@ExcelField等)
│   ├── redis/RedisUtils.java                    # Redis工具(1439行, 完整API)
│   ├── redis/RedisConfig.java                   # Redis配置
│   ├── utils/Collections3.java                  # 集合工具
│   ├── utils/CommonUtils.java                   # 通用工具
│   ├── utils/RequestUtils.java                  # 请求工具(token解析)
│   ├── utils/ResponseUtil.java                  # 响应构建器
│   └── converter/StringToDateConverter.java     # 日期转换器
├── config/
│   ├── AppInit.java                             # 启动信息打印(CommandLineRunner)
│   ├── DomainFeignConfig.java                   # Feign配置
│   ├── ExceptionHandlingAsyncTaskExecutor.java   # 异步任务异常处理
│   └── properties/JeePlusProperties.java        # 全局配置(token过期时间/文件路径)
└── aop/demo/                                    # AOP示例
```

**@JeeplusCloudApplication** 组合注解:
```java
@EnableAsync
@EnableDiscoveryClient
@EnableFeignClients({"com.jeeplus.*"})
@SpringBootApplication(scanBasePackages = {"com.jeeplus", "cn.hutool.extra.spring"},
    exclude = {SecurityAutoConfiguration.class})
```

#### 4.4.2 jeeplus-common-log — 日志模块

**LoggingAspect** AOP 切面:
- 切点: `@annotation(com.jeeplus.logging.annotation.ApiLog)`
- `@Around`: 记录方法执行时间 → AsyncLogService 异步保存日志
- `@AfterThrowing`: 记录异常日志
- 支持 `LogTypeEnum` (LOGIN, ACCESS 等)

#### 4.4.3 jeeplus-common-mybatis-plus — ORM 配置

```
├── config/          # MyBatis-Plus 分页插件、多租户插件、自动填充
└── database/        # 数据源配置、动态数据源
```

#### 4.4.4 jeeplus-common-security — 安全模块

**核心类**:

| 类名 | 说明 |
|------|------|
| `WebSecurityConfig` | Spring Security 配置 (BCrypt编码, 无状态Session, 白名单) |
| `TokenProvider` | JWT 生成/解析/校验 (Auth0 JWT, HMAC256, SIGN_CODE=`@#&#$^JWE@#$F123`) |
| `JWTFilter` | Token 过滤器 (GenericFilterBean) |
| `JWTConfigurer` | 将 JWTFilter 注册到 Security 链 |
| `SecurityUtils` | 安全工具 (获取当前用户/Token/密码加密) |
| `CustomUserDetailsService` | 自定义用户详情服务 |
| `DaoAuthenticationProvider` | 自定义认证提供者 |
| `JwtAuthenticationEntryPoint` | 未认证处理 |
| `JwtAccessDeniedHandler` | 权限不足处理 |
| `ExceptionTranslator` | 异常翻译器 |
| `WebConfig` | Web 配置 (CORS/拦截器) |

**工具类** (`utils/`):
- `Encodes.java` — 编码工具
- `Exceptions.java` — 异常工具
- `SecuritySpringContextHolder.java` — Spring上下文持有者
- `StringUtils.java` — 字符串工具 (22.9KB)

#### 4.4.5 jeeplus-common-swagger — API 文档

- `SwaggerConfig.java` — Knife4j 配置 (分组/认证头)
- `TypeNameIndexingAdapter.java` — 类型命名适配

---

### 4.5 jeeplus-modules — 业务模块层

#### 4.5.1 jeeplus-system — ★核心系统服务

**启动类**: `JeeplusSystemApplication` (使用 `@JeeplusCloudApplication` + `@EnableCaching`)

**分层结构**:
```
jeeplus-system/src/main/java/com/jeeplus/
├── sys/
│   ├── controller/       # REST 控制器
│   │   ├── UserController.java (93KB)      # 用户管理
│   │   ├── RoleController.java             # 角色管理
│   │   ├── MenuController.java             # 菜单管理
│   │   ├── OfficeController.java           # 组织机构
│   │   ├── PostController.java             # 岗位管理
│   │   ├── AreaController.java             # 区域管理
│   │   ├── DictController.java             # 字典管理
│   │   ├── TenantController.java           # 租户管理
│   │   ├── LogController.java              # 日志管理
│   │   ├── DataRuleController.java         # 数据权限
│   │   ├── ConfigController.java           # 系统配置
│   │   ├── DeskController.java             # 桌面配置
│   │   ├── LanguageController.java         # 国际化
│   │   └── app/                            # 移动端控制器
│   ├── service/          # 业务逻辑
│   │   ├── UserService.java (36KB)
│   │   ├── OfficeService.java (31KB)
│   │   ├── MenuService.java
│   │   ├── RoleService.java
│   │   ├── TenantService.java
│   │   ├── DictTypeService.java
│   │   ├── DataRuleService.java
│   │   ├── AreaService.java
│   │   └── dto/ + mapstruct/
│   ├── domain/           # 实体 (User, Role, Menu, Office, Post, Area, DictType, DictValue, Log...)
│   ├── mapper/           # MyBatis Mapper
│   ├── feign/            # Feign 接口实现 (供其他服务调用)
│   ├── model/            # 页面VO/Model
│   ├── sms/              # 短信服务
│   └── utils/            # 系统专用工具
├── calendar/             # 日历
├── database/             # 数据库管理
├── datav/                # 数据可视化
├── echarts/              # 图表
├── form/                 # 表单设计
├── mail/                 # 邮件
├── monitor/              # 监控
├── notify/               # 通知
└── tools/                # 工具
```

#### 4.5.2 jeeplus-flowable — 工作流服务

```
jeeplus-flowable/src/main/java/com/jeeplus/
├── flowable/
│   ├── controller/       # 流程控制器 (8个)
│   ├── service/          # 流程服务 (7个)
│   ├── model/            # 流程模型 (11个)
│   ├── mapper/           # 流程Mapper
│   ├── listener/         # 流程监听器
│   ├── utils/            # 流程工具 (13个)
│   ├── vo/               # 视图对象
│   ├── common/           # 公共流程工具
│   └── constant/         # 流程常量
├── centerservice/        # 中心服务
├── extension/            # 扩展
├── modules/              # 模块
└── weChat/               # 微信集成
```

#### 4.5.3 jeeplus-file — 文件服务

存储支持: MinIO / 阿里云 OSS

```
jeeplus-file/src/main/java/com/jeeplus/file/
├── JeeplusFileApplication.java
├── controller/           # 文件上传/下载/预览
├── repository/           # 存储仓库 (5种)
├── config/               # 存储配置
├── model/                # 文件模型
└── utils/                # 文件工具
```

#### 4.5.4 其他业务模块一览

| 模块 | 包路径 | 功能描述 |
|------|--------|---------|
| jeeplus-finance | `com.jeeplus.finance` | 财务管理 (15个子包) |
| jeeplus-assess | `com.jeeplus.assess` | 评估考核 (10个子包) |
| jeeplus-human | `com.jeeplus.human` | 人力资源管理 (5个子包) |
| jeeplus-ccpm | `com.jeeplus.ccpm` | 项目管理 (3个子包) |
| jeeplus-consult | `com.jeeplus.consultancy` | 培训咨询 (4个子包) |
| jeeplus-public-modules | `com.jeeplus.pubmodules` | 公共功能: 收藏/合同/知识库/会议室/抽奖/物料/供应商/仓库/采购/序列号/OOS/假期/编辑器/附件 |
| jeeplus-centrecareful | — | 中审管理 |
| jeeplus-psi-management | — | PSI管理 |
| jeeplus-devtools | — | 代码生成等开发工具 |
| jeeplus-ureport | — | UReport 报表引擎 |
| jeeplus-wps | — | WPS 文档在线编辑 |
| jeeplus-xxl-job-admin | — | XXL-Job 调度中心 |
| jeeplus-xxl-job-executor-sample | — | XXL-Job 执行器 |
| jeeplus-admin-server | — | Spring Boot Admin 监控服务 |
| jeeplus-test | — | 测试模块 |

---

## 5. 核心基类体系

### 5.1 实体基类 (Entity)

```
BaseEntity (jeeplus-common-core)
├── id: String                   @TableId
├── createTime: Date             @TableField(fill=INSERT)
├── createById: String           @TableField(fill=INSERT)
├── updateTime: Date             @TableField(fill=INSERT_UPDATE)
├── updateById: String           @TableField(fill=INSERT_UPDATE)
├── delFlag: Integer             @TableLogic, @TableField(fill=INSERT)
└── tenantId: String             @TableField(fill=INSERT), @Query(type=EQ)
    │
    └── TreeEntity<T> extends BaseEntity
        ├── parentId: String
        ├── parentIds: String    # 所有父级ID路径
        ├── name: String
        ├── sort: Integer
        └── children: List<T>    @TableField(exist=false)
```

### 5.2 传输对象基类 (DTO)

```
BaseDTO<T> (jeeplus-system-api)
├── taskId: String               # 流程任务ID
├── procInsId: String            # 流程实例ID
├── processDefinitionId: String  # 流程定义ID
├── id: String
├── createTime: Date
├── createBy: UserDTO
├── updateTime: Date
├── updateBy: UserDTO
├── delFlag: Integer
└── tenantDTO: TenantDTO
    │
    └── TreeDTO<T> extends BaseDTO<T>
        ├── parent: T
        ├── children: List<T>
        ├── parentIds: String
        ├── name: String
        └── sort: Integer
```

### 5.3 MapStruct 映射器

```
EntityWrapper<D, E>
├── toEntity(D dto) → E           # @Mapping: tenantDTO.id→tenantId, createBy.id→createById
├── toDTO(E entity) → D           # @Mapping: tenantId→tenantDTO.id, createById→createBy.id
├── toEntity(List<D>) → List<E>
├── toDTO(List<E>) → List<D>
├── toEntity(Page<D>) → Page<E>
└── toDTO(Page<E>) → Page<D>

TreeWrapper<D, E> extends EntityWrapper<D, E>
├── toEntity/toDTO (继承 + parent.id↔parentId 映射)
├── copyEntity / copyDTO
└── toEntity(DragNode<D>) → DragNode<E>  # 拖拽排序支持
```

### 5.4 服务基类

```
TreeService<D extends TreeMapper<T>, T extends TreeEntity<T>> extends ServiceImpl<D, T>
├── saveOrUpdate(T)           # 自动维护 parentIds 路径
├── sortList(DragNode<T>)     # 拖拽排序
├── getChildren(T)            # 查询子节点
├── removeWithChildrenById()  # 级联删除
├── treeData()                # 获取完整树
└── formatListToTree()        # 列表→树形转换 (Map分组+递归)
```

---

## 6. 常用工具类

### 6.1 RedisUtils (jeeplus-common-core)

> 位置: `com.jeeplus.common.redis.RedisUtils` (1439行)

**推荐API** (带 cacheName 前缀):
```java
RedisUtils.getInstance().get(cacheName, key)       // 读取
RedisUtils.getInstance().set(cacheName, key, value) // 写入
RedisUtils.getInstance().delete(cacheName, key)      // 删除
RedisUtils.getInstance().expire(cacheName, key, t)   // 过期
RedisUtils.getInstance().keys(cacheName, pattern)    // 模糊匹配
```

`@Deprecated` 标记的直接操作方法 (不带 cacheName) 不推荐使用，因为会使 `@CacheEvict`/`@Cacheable` 注解无效。

### 6.2 ResponseUtil (jeeplus-common-core)

```java
ResponseUtil.newInstance()
    .add("key", value)     // 链式添加响应字段
    .ok()                  // 返回 ResponseEntity (200)
    .ok("message")         // 返回带消息的 ResponseEntity
```

### 6.3 RequestUtils (jeeplus-common-core)

```java
RequestUtils.getRequest()                          // 获取 HttpServletRequest
RequestUtils.getHeader("headerName")               // 获取请求头
RequestUtils.resolveToken(request, "token")        // 解析token (param > header > cookie)
```

### 6.4 SecurityUtils (jeeplus-common-security)

```java
SecurityUtils.getLoginName()                       // 当前登录用户名
SecurityUtils.getCurrentUserDTO()                  // 当前用户完整信息
SecurityUtils.getToken()                           // 当前Token
SecurityUtils.getAuthentication()                  // 认证信息
SecurityUtils.login(username, password, authMgr)   // 手动登录
SecurityUtils.encryptPassword(password)            // BCrypt加密
SecurityUtils.validatePassword(plain, encoded)     // 密码验证
```

### 6.5 QueryWrapperGenerator (jeeplus-common-core)

基于 `@Query` 注解动态构建 MyBatis-Plus `QueryWrapper`:
```java
QueryWrapper<T> qw = QueryWrapperGenerator.buildQueryCondition(searchObj, Entity.class);
```

支持查询类型: EQ, NE, GT, GE, LT, LE, BETWEEN, NOTBETWEEN, LIKE, NOTLIKE, LIKELEFT, LIKERIGHT

### 6.6 EasyExcelUtils (jeeplus-common-core)

EasyExcel 读写封装，支持自定义 `@ExcelField` 注解的列转换。

### 6.7 TokenProvider (jeeplus-common-security)

```java
TokenProvider.createAccessToken(username)    // 生成JWT
TokenProvider.validateToken(token)           // 校验JWT
TokenProvider.getLoginName(token)            // 从Token中获取用户名
TokenProvider.getAuthentication(token)       // 获取认证对象(含权限)
TokenProvider.resolveToken(request)          // 从请求中解析Token
TokenProvider.getCurrentToken()              // 获取当前请求的Token
```

JWT 签名: `Algorithm.HMAC256("@#&#$^JWE@#$F123")`  
Token 中包含: `username` claim + `expiresAt`

### 6.8 JeePlusProperties

```java
JeePlusProperties.newInstance().getEXPIRE_TIME()    // Token过期时间(秒)
JeePlusProperties.newInstance().getUserfilesBaseDir() // 文件存储根目录
```

---

## 7. 服务间调用与依赖关系

### 7.1 服务注册名 (Nacos)

| 服务名 | 端口 | 模块 |
|--------|------|------|
| `jeeplus-gateway` | 8088 | 网关 |
| `jeeplus-auth` | 9211 | 认证 |
| `jeeplus-system` | — | 系统核心 |
| `jeeplus-flowable` | — | 工作流 |
| `jeeplus-file` | — | 文件 |
| `jeeplus-finance` | — | 财务 |
| `jeeplus-assess` | — | 评估 |
| `jeeplus-human` | — | 人事 |
| `jeeplus-ccpm` | — | 项目管理 |
| `jeeplus-public-modules` | — | 公共模块 |
| `jeeplus-centrecareful` | — | 中审 |
| `jeeplus-consultancy` | — | 培训 |
| `jeeplus-psi-management` | — | PSI |

### 7.2 Feign 调用关系图

```
jeeplus-auth ──Feign──▶ jeeplus-system  (IUserApi, ITenantApi)

jeeplus-gateway ──Feign──▶ jeeplus-system  (IUserApi)

jeeplus-flowable ──Feign──▶ jeeplus-system
                        ──▶ jeeplus-assess
                        ──▶ jeeplus-finance
                        ──▶ jeeplus-human
                        ──▶ jeeplus-ccpm
                        ──▶ jeeplus-consult
                        ──▶ jeeplus-psi-management
                        ──▶ jeeplus-centrecareful

各业务模块 ──Feign──▶ jeeplus-system     (获取用户/权限/租户)
                  ──▶ jeeplus-file       (文件存储)
                  ──▶ jeeplus-public-modules (工作附件)
```

### 7.3 Fallback 降级策略

所有 Feign 接口都配置了 `fallbackFactory`，当服务不可用时返回默认值或空对象:

| API | FallbackFactory |
|-----|----------------|
| IUserApi | UserApiFallbackFactory |
| ITenantApi | TenantApiFallbackFactory |
| IFileApi | FileApiFallbackFactory |
| IWorkAttachmentApi | WorkAttachmentApiFallbackFactory |
| ICwProjectReportApi | CwProjectReportApiFallbackFactory |
| FlowableApi | FlowableApiFallbackFactory |
| AssessApi | AssessApiFallbackFactory |
| 等... | |

---

## 8. 接口规范

### 8.1 RESTful URL 规范

```
/模块名/资源名/操作

用户管理:    /sys/user/**
角色管理:    /sys/role/**
菜单管理:    /sys/menu/**
部门管理:    /sys/office/**
岗位管理:    /sys/post/**
字典管理:    /sys/dict/**
租户管理:    /sys/tenant/**
流程管理:    /flowable/**
文件管理:    /file/**

Feign内部调用: /feign/模块名/资源名/**
```

### 8.2 Swagger 规范

- 所有 Controller 使用 `@Api(tags="xxx")` 标注分组
- 接口方法使用 `@ApiOperation("xxx")` 标注说明
- DTO 字段使用 `@ApiModelProperty` 标注
- 隐藏字段: `@IgnoreSwaggerParameter`, `@ApiModelProperty(hidden=true)`, `@ExcelIgnore`
- 文档入口: `http://{ip}:{port}/doc.html`
- Gateway 聚合了所有子服务的 Swagger 文档

### 8.3 DTO ↔ Entity 转换规范

- 使用 MapStruct 自动映射 (`EntityWrapper`, `TreeWrapper`)
- DTO 中关联对象使用完整实体 (如 `UserDTO createBy`)，Entity 中只存 ID (如 `String createById`)
- 通过 `@Mapping` 注解声明映射关系
- 前端交互统一使用 DTO，禁止直接暴露 Entity

### 8.4 分页规范

使用 MyBatis-Plus `IPage<UserDTO>` 作为分页返回类型，MapStruct 提供 `Page<DTO> ↔ Page<Entity>` 自动转换。

### 8.5 响应格式

```json
{
  "token": "xxx",
  "oldLoginDate": "2026-01-01 12:00:00",
  "oldLoginIp": "192.168.1.1"
}
```

通过 `ResponseUtil` 链式构建响应，最终返回 `ResponseEntity`。

---

## 9. 权限控制逻辑

### 9.1 认证流程架构

```
                        ┌─────────────┐
                        │   客户端     │
                        └──────┬──────┘
                               │ 用户名/密码
                               ▼
                     ┌─────────────────┐
                     │  jeeplus-auth    │
                     │  LoginController │
                     └────────┬────────┘
                              │ SpringSecurity.authenticate()
                              ▼
                     ┌─────────────────┐
                     │ DaoAuthentication│
                     │ Provider         │
                     └────────┬────────┘
                              │ BCrypt密码校验
                              ▼
                     ┌─────────────────┐
                     │ IUserApi        │──▶ jeeplus-system
                     │ getByLoginName()│    查询用户
                     └────────┬────────┘
                              │
                     ┌────────▼────────┐
                     │ 生成JWT Token   │
                     │ 存入 Redis       │
                     │ user:cache:token │
                     └────────┬────────┘
                              │ 返回 Token
                              ▼
                        ┌─────────────┐
                        │   客户端     │ 携带 Token
                        └──────┬──────┘
                               │ 每次请求带 Token
                               ▼
                     ┌─────────────────┐
                     │  jeeplus-gateway │
                     │  JWTFilter       │
                     └────────┬────────┘
                              │ 校验Redis中的Token
                              │ 过期自动刷新
                              ▼
                     ┌─────────────────┐
                     │  路由到目标服务   │
                     └────────┬────────┘
                              │
                     ┌────────▼────────┐
                     │ 微服务内部        │
                     │ WebSecurityConfig │
                     │ JWTFilter(common) │
                     └────────┬────────┘
                              │ @PreAuthorize 方法级权限
                              ▼
                     ┌─────────────────┐
                     │  执行业务逻辑     │
                     └─────────────────┘
```

### 9.2 权限模型: RBAC

```
用户(User) ──多对多──▶ 角色(Role) ──多对多──▶ 菜单权限(Menu/permission)
  │                      │
  │                      └── 数据权限(DataRule) 
  │
  └── 多对一 ──▶ 部门(Office)
  └── 多对多 ──▶ 岗位(Post)
  └── 多对一 ──▶ 租户(Tenant)
```

### 9.3 方法级权限 (`@PreAuthorize`)

`WebSecurityConfig` 开启 `@EnableGlobalMethodSecurity(prePostEnabled = true)`，支持:
```java
@PreAuthorize("hasAuthority('sys:user:edit')")
@PreAuthorize("hasRole('admin')")
```

权限标识通过 `IUserApi.getPermissions(loginName)` 获取，注入到 `Authentication.authorities`。

### 9.4 数据权限 (DataRule)

- 通过 `IUserApi.getDataRuleList(userDTO)` 获取用户数据权限规则
- 缓存: `user:cache:dataRuleList`
- 在 MyBatis 查询时动态追加数据过滤条件

### 9.5 多租户隔离

- `BaseEntity.tenantId` 自动填充 (`@TableField(fill=INSERT)`)
- `@Query(type=EQ)` 默认按租户等值查询
- `ITenantApi.getCurrentTenantId()` 从请求上下文获取当前租户
- 缓存 Key 自动包含租户上下文

### 9.6 Token 生命周期

```
登录 → createAccessToken() → Redis.set(token, ttl=EXPIRE_TIME)
     → Redis.set(onlineUsers, ttl=EXPIRE_TIME)

请求 → JWTFilter(Gateway):
    1. 从Redis校验token
    2. 若accessToken过期 → 自动生成新token → 更新Redis
    3. 刷新Redis过期时间
    4. 注入SecurityContext

退出 → LoginController.logout():
    1. Redis.delete(token)
    2. Redis.delete(onlineUsers)
    3. 清除Spring Security上下文
    4. 同用户名所有设备下线
    5. 钉钉解绑
```

### 9.7 Gateway 白名单 (`ignore.whiteList`)

通过 Nacos 配置动态管理，支持通配符路径。示例中允许:
- `/**` (全局)
- `/*/public-modules-server/luckyDraw/events/**` (抽奖活动)
- Swagger 静态资源 (`/doc.html`, `/swagger-ui.html`, `/webjars/**`)
- 管理端点 (`/management/**`)
- OPTIONS 预检请求

---

## 10. 关键常量与缓存设计

### 10.1 服务名常量 (AppNameConstants)

| 常量 | 值 |
|------|-----|
| APP_AUTH_SERVICE | `jeeplus-auth` |
| APP_SYSTEM_SERVICE | `jeeplus-system` |
| APP_FILE_SERVICE | `jeeplus-file` |
| APP_FLOWABLE_SERVICE | `jeeplus-flowable` |
| APP_PUBLIC_MODULES | `jeeplus-public-modules` |
| APP_ASSESS_MODULES | `jeeplus-assess` |
| APP_FINANCE_MODULES | `jeeplus-finance` |
| APP_HUMAN_MODULES | `jeeplus-human` |
| APP_CCPM_MODULES | `jeeplus-ccpm` |
| APP_CENTRECAREFUL_MODULES | `jeeplus-centrecareful` |
| APP_CONSULT_MODULES | `jeeplus-consultancy` |
| APP_PSI_MANAGEMENT_MODULES | `jeeplus-psi-management` |

### 10.2 Redis 缓存 Key 设计 (CacheNames)

```
sys:cache:code                  # 验证码
sys:cache:config                # 系统配置
sys:cache:areaList              # 区域列表
sys:cache:dictMap               # 字典映射
sys:cache:tenant                # 租户信息
sys:cache:menu                  # 菜单
sys:cache:languageMap           # 语言国际化

user:cache:topMenu              # 用户顶部菜单
user:cache:menuList             # 用户左侧菜单
user:cache:dataRuleList         # 用户数据权限规则
user:cache:roleList             # 用户角色列表
user:cache:userId               # 用户ID→用户信息
user:cache:loginName            # 登录名→用户信息
user:cache:token                # Token存储
user:cache:online:users         # 在线用户列表
user:cache:user:all:info        # 所有用户信息
user:assess:cache:code:loginName # 登录失败次数

ccpm:is:connect                 # CCPM系统连接状态
user:cache:dataRuleExists       # 数据权限存在标记
```

### 10.3 错误消息常量 (ErrorConstants)

```
LOGIN_ERROR_NOT_LOGIN_IN              "您尚未登录，请登录后操作!"
LOGIN_ERROR_FORBIDDEN                 "该帐号已经被禁止登录！"
LOGIN_ERROR_INCORRECT                 "用户名或者密码错误！"
LOGIN_ERROR_NOTFOUND                  "用户名不存在!"
LOGIN_ERROR_EXPIRED                   "您的登录已过期，请重新登录！"
LOGIN_ERROR_FORBID_LOGGED_IN_ELSEWHERE "您的账号已在其它地方登录，您被禁止登录！"
LOGIN_ERROR__KICK_OUT_LOGGED_IN_ELSEWHERE "您的账号在另一台设备上登录..."
LOGIN_ERROR_ERROR_VALIDATE_CODE       "您输入的验证码不正确，请重新输入！"
LOGIN_CODE                            "请输入验证码进行登录！"
LOGIN_MAX_COUNT                       "今天登录次数已达最大,请明天再登录！"
LOGIN_ERROR                           "您目前无法登录！"
```

---

## 附录: 关键配置项

### Nacos 配置 (bootstrap.yml)

```yaml
spring.cloud.nacos:
  discovery.server-addr: 127.0.0.1:8848
  discovery.namespace: ${spring.profiles.active}
  config.server-addr: 127.0.0.1:8848
  config.file-extension: yml
  config.shared-configs: [application.yml]

sentinel.transport.dashboard: 127.0.0.1:8858
ribbon.ReadTimeout: 600000
ribbon.ConnectTimeout: 600000
hystrix.command.default.execution.isolation.thread.timeoutInMillisecond: 60000
```

### JWT 配置

```yaml
jwt.accessToken.expireTime: (在Nacos中配置, 单位秒)
```

### 文件存储配置

```yaml
userfiles.basedir: (文件存储根目录)
```

---

> **生成时间**: 2026-06-01  
> **索引范围**: xg_total_process_master_cloud 全部模块 (5个顶层模块, 27个子模块)  
> **Java源文件**: 覆盖 jeeplus-gateway, jeeplus-auth, jeeplus-api, jeeplus-common, jeeplus-modules 五大模块
