This commit is contained in:
wkc
2026-01-16 16:16:13 +08:00
commit 8295b39278
662 changed files with 71808 additions and 0 deletions

55
.gitignore vendored Normal file
View File

@@ -0,0 +1,55 @@
######################################################################
# Build Tools
.gradle
/build/
!gradle/wrapper/gradle-wrapper.jar
target/
!.mvn/wrapper/maven-wrapper.jar
######################################################################
# IDE
### STS ###
.apt_generated
.classpath
.factorypath
.project
.settings
.springBeans
### IntelliJ IDEA ###
.idea
*.iws
*.iml
*.ipr
### JRebel ###
rebel.xml
### NetBeans ###
nbproject/private/
build/*
nbbuild/
dist/
nbdist/
.nb-gradle/
######################################################################
# Others
*.log
*.xml.versionsBackup
*.swp
!*/build/*.java
!*/build/*.html
!*/build/*.xml
**/_remote.repositories
mvn/
/.idea/
浙江省/
ruoyi-ui/vue.config.js

20
LICENSE Normal file
View File

@@ -0,0 +1,20 @@
The MIT License (MIT)
Copyright (c) 2018 RuoYi
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

96
README.md Normal file
View File

@@ -0,0 +1,96 @@
<p align="center">
<img alt="logo" src="https://oscimg.oschina.net/oscnet/up-d3d0a9303e11d522a06cd263f3079027715.png">
</p>
<h1 align="center" style="margin: 30px 0 30px; font-weight: bold;">RuoYi v3.8.8</h1>
<h4 align="center">基于SpringBoot+Vue前后端分离的Java快速开发框架</h4>
<p align="center">
<a href="https://gitee.com/y_project/RuoYi-Vue/stargazers"><img src="https://gitee.com/y_project/RuoYi-Vue/badge/star.svg?theme=dark"></a>
<a href="https://gitee.com/y_project/RuoYi-Vue"><img src="https://img.shields.io/badge/RuoYi-v3.8.8-brightgreen.svg"></a>
<a href="https://gitee.com/y_project/RuoYi-Vue/blob/master/LICENSE"><img src="https://img.shields.io/github/license/mashape/apistatus.svg"></a>
</p>
## 平台简介
若依是一套全部开源的快速开发平台,毫无保留给个人及企业免费使用。
* 前端采用Vue、Element UI。
* 后端采用Spring Boot、Spring Security、Redis & Jwt。
* 权限认证使用Jwt支持多终端认证系统。
* 支持加载动态权限菜单,多方式轻松权限控制。
* 高效率开发,使用代码生成器可以一键生成前后端代码。
* 提供了技术栈([Vue3](https://v3.cn.vuejs.org) [Element Plus](https://element-plus.org/zh-CN) [Vite](https://cn.vitejs.dev))版本[RuoYi-Vue3](https://github.com/yangzongzhuan/RuoYi-Vue3),保持同步更新。
* 提供了单应用版本[RuoYi-Vue-fast](https://github.com/yangzongzhuan/RuoYi-Vue-fast)Oracle版本[RuoYi-Vue-Oracle](https://github.com/yangzongzhuan/RuoYi-Vue-Oracle),保持同步更新。
* 不分离版本,请移步[RuoYi](https://gitee.com/y_project/RuoYi),微服务版本,请移步[RuoYi-Cloud](https://gitee.com/y_project/RuoYi-Cloud)
* 阿里云折扣场:[点我进入](http://aly.ruoyi.vip),腾讯云秒杀场:[点我进入](http://txy.ruoyi.vip)&nbsp;&nbsp;
* 阿里云优惠券:[点我领取](https://www.aliyun.com/minisite/goods?userCode=brki8iof&share_source=copy_link),腾讯云优惠券:[点我领取](https://cloud.tencent.com/redirect.php?redirect=1025&cps_key=198c8df2ed259157187173bc7f4f32fd&from=console)&nbsp;&nbsp;
## 内置功能
1. 用户管理:用户是系统操作者,该功能主要完成系统用户配置。
2. 部门管理:配置系统组织机构(公司、部门、小组),树结构展现支持数据权限。
3. 岗位管理:配置系统用户所属担任职务。
4. 菜单管理:配置系统菜单,操作权限,按钮权限标识等。
5. 角色管理:角色菜单权限分配、设置角色按机构进行数据范围权限划分。
6. 字典管理:对系统中经常使用的一些较为固定的数据进行维护。
7. 参数管理:对系统动态配置常用参数。
8. 通知公告:系统通知公告信息发布维护。
9. 操作日志:系统正常操作日志记录和查询;系统异常信息日志记录和查询。
10. 登录日志:系统登录日志记录查询包含登录异常。
11. 在线用户:当前系统中活跃用户状态监控。
12. 定时任务:在线(添加、修改、删除)任务调度包含执行结果日志。
13. 代码生成前后端代码的生成java、html、xml、sql支持CRUD下载 。
14. 系统接口根据业务代码自动生成相关的api接口文档。
15. 服务监控监视当前系统CPU、内存、磁盘、堆栈等相关信息。
16. 缓存监控:对系统的缓存信息查询,命令统计等。
17. 在线构建器拖动表单元素生成相应的HTML代码。
18. 连接池监视监视当前系统数据库连接池状态可进行分析SQL找出系统性能瓶颈。
## 在线体验
- admin/admin123
- 陆陆续续收到一些打赏,为了更好的体验已用于演示服务器升级。谢谢各位小伙伴。
演示地址http://vue.ruoyi.vip
文档地址http://doc.ruoyi.vip
## 演示图
<table>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/cd1f90be5f2684f4560c9519c0f2a232ee8.jpg"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/1cbcf0e6f257c7d3a063c0e3f2ff989e4b3.jpg"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-8074972883b5ba0622e13246738ebba237a.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-9f88719cdfca9af2e58b352a20e23d43b12.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-39bf2584ec3a529b0d5a3b70d15c9b37646.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-936ec82d1f4872e1bc980927654b6007307.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-b2d62ceb95d2dd9b3fbe157bb70d26001e9.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-d67451d308b7a79ad6819723396f7c3d77a.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/5e8c387724954459291aafd5eb52b456f53.jpg"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/644e78da53c2e92a95dfda4f76e6d117c4b.jpg"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-8370a0d02977eebf6dbf854c8450293c937.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-49003ed83f60f633e7153609a53a2b644f7.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/up-d4fe726319ece268d4746602c39cffc0621.png"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-c195234bbcd30be6927f037a6755e6ab69c.png"/></td>
</tr>
<tr>
<td><img src="https://oscimg.oschina.net/oscnet/b6115bc8c31de52951982e509930b20684a.jpg"/></td>
<td><img src="https://oscimg.oschina.net/oscnet/up-5e4daac0bb59612c5038448acbcef235e3a.png"/></td>
</tr>
</table>
## 若依前后端分离交流群
QQ群 [![加入QQ群](https://img.shields.io/badge/已满-937441-blue.svg)](https://jq.qq.com/?_wv=1027&k=5bVB1og) [![加入QQ群](https://img.shields.io/badge/已满-887144332-blue.svg)](https://jq.qq.com/?_wv=1027&k=5eiA4DH) [![加入QQ群](https://img.shields.io/badge/已满-180251782-blue.svg)](https://jq.qq.com/?_wv=1027&k=5AxMKlC) [![加入QQ群](https://img.shields.io/badge/已满-104180207-blue.svg)](https://jq.qq.com/?_wv=1027&k=51G72yr) [![加入QQ群](https://img.shields.io/badge/已满-186866453-blue.svg)](https://jq.qq.com/?_wv=1027&k=VvjN2nvu) [![加入QQ群](https://img.shields.io/badge/已满-201396349-blue.svg)](https://jq.qq.com/?_wv=1027&k=5vYAqA05) [![加入QQ群](https://img.shields.io/badge/已满-101456076-blue.svg)](https://jq.qq.com/?_wv=1027&k=kOIINEb5) [![加入QQ群](https://img.shields.io/badge/已满-101539465-blue.svg)](https://jq.qq.com/?_wv=1027&k=UKtX5jhs) [![加入QQ群](https://img.shields.io/badge/已满-264312783-blue.svg)](https://jq.qq.com/?_wv=1027&k=EI9an8lJ) [![加入QQ群](https://img.shields.io/badge/已满-167385320-blue.svg)](https://jq.qq.com/?_wv=1027&k=SWCtLnMz) [![加入QQ群](https://img.shields.io/badge/已满-104748341-blue.svg)](https://jq.qq.com/?_wv=1027&k=96Dkdq0k) [![加入QQ群](https://img.shields.io/badge/已满-160110482-blue.svg)](https://jq.qq.com/?_wv=1027&k=0fsNiYZt) [![加入QQ群](https://img.shields.io/badge/已满-170801498-blue.svg)](https://jq.qq.com/?_wv=1027&k=7xw4xUG1) [![加入QQ群](https://img.shields.io/badge/已满-108482800-blue.svg)](https://jq.qq.com/?_wv=1027&k=eCx8eyoJ) [![加入QQ群](https://img.shields.io/badge/已满-101046199-blue.svg)](https://jq.qq.com/?_wv=1027&k=SpyH2875) [![加入QQ群](https://img.shields.io/badge/已满-136919097-blue.svg)](https://jq.qq.com/?_wv=1027&k=tKEt51dz) [![加入QQ群](https://img.shields.io/badge/已满-143961921-blue.svg)](http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=0vBbSb0ztbBgVtn3kJS-Q4HUNYwip89G&authKey=8irq5PhutrZmWIvsUsklBxhj57l%2F1nOZqjzigkXZVoZE451GG4JHPOqW7AW6cf0T&noverify=0&group_code=143961921) [![加入QQ群](https://img.shields.io/badge/已满-174951577-blue.svg)](http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=ZFAPAbp09S2ltvwrJzp7wGlbopsc0rwi&authKey=HB2cxpxP2yspk%2Bo3WKTBfktRCccVkU26cgi5B16u0KcAYrVu7sBaE7XSEqmMdFQp&noverify=0&group_code=174951577) [![加入QQ群](https://img.shields.io/badge/已满-161281055-blue.svg)](http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=Fn2aF5IHpwsy8j6VlalNJK6qbwFLFHat&authKey=uyIT%2B97x2AXj3odyXpsSpVaPMC%2Bidw0LxG5MAtEqlrcBcWJUA%2FeS43rsF1Tg7IRJ&noverify=0&group_code=161281055) [![加入QQ群](https://img.shields.io/badge/已满-138988063-blue.svg)](http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=XIzkm_mV2xTsUtFxo63bmicYoDBA6Ifm&authKey=dDW%2F4qsmw3x9govoZY9w%2FoWAoC4wbHqGal%2BbqLzoS6VBarU8EBptIgPKN%2FviyC8j&noverify=0&group_code=138988063) [![加入QQ群](https://img.shields.io/badge/151450850-blue.svg)](http://qm.qq.com/cgi-bin/qm/qr?_wv=1027&k=DkugnCg68PevlycJSKSwjhFqfIgrWWwR&authKey=pR1Pa5lPIeGF%2FFtIk6d%2FGB5qFi0EdvyErtpQXULzo03zbhopBHLWcuqdpwY241R%2F&noverify=0&group_code=151450850) 点击按钮入群。

12
bin/clean.bat Normal file
View File

@@ -0,0 +1,12 @@
@echo off
echo.
echo [信息] 清理工程target生成路径。
echo.
%~d0
cd %~dp0
cd ..
call mvn clean
pause

12
bin/package.bat Normal file
View File

@@ -0,0 +1,12 @@
@echo off
echo.
echo [信息] 打包Web工程生成war/jar包文件。
echo.
%~d0
cd %~dp0
cd ..
call mvn clean package -Dmaven.test.skip=true
pause

14
bin/run.bat Normal file
View File

@@ -0,0 +1,14 @@
@echo off
echo.
echo [信息] 使用Jar命令运行Web工程。
echo.
cd %~dp0
cd ../ruoyi-admin/target
set JAVA_OPTS=-Xms256m -Xmx1024m -XX:MetaspaceSize=128m -XX:MaxMetaspaceSize=512m
java -jar %JAVA_OPTS% ruoyi-admin.jar
cd bin
pause

487
doc/0314sql-更新.txt Normal file
View File

@@ -0,0 +1,487 @@
alter table sys_group_customer add column `cust_lb` char(1) DEFAULT NULL COMMENT '是否行内客户'; -- 舒
-- 张淋彬
ALTER TABLE ibs.ibs_anchor_address_965 ADD source varchar(100) NULL COMMENT '地址来源';
ALTER TABLE ibs.ibs_anchor_965 ADD cust_status INT DEFAULT 1 NULL;
ALTER TABLE ibs.ibs_anchor_965 ADD cust_address_status INT DEFAULT 1 NULL;
ALTER TABLE ibs.ibs_anchor_965 ADD create_time DATETIME DEFAULT CURRENT_TIMESTAMP NULL;
CREATE INDEX `ibs_anchor_update_time_IDX` USING BTREE ON ibs.ibs_anchor_965 (update_time desc);
CREATE INDEX `ibs_anchor_cust_status_IDX` USING BTREE ON ibs.ibs_anchor_965 (cust_status,cust_address_status,delete_status,cust_type);
CREATE INDEX `ibs_anchor_cust_type_IDX` USING BTREE ON ibs.ibs_anchor_965 (cust_type,delete_status,address_id);
CREATE INDEX `ibs_anchor_cust_id_IDX` USING BTREE ON ibs.ibs_anchor_965 (cust_id,legal_id,delete_status);
ALTER TABLE ibs.cust_info_retail_965 ADD normal_location varchar(100) NULL COMMENT '常住地址';
ALTER TABLE ibs.cust_info_retail_965 ADD idc_location varchar(100) NULL COMMENT '身份证地址';
ALTER TABLE ibs.cust_info_retail_965 ADD relation_location varchar(100) NULL COMMENT '联系地址';
-- 张昱
CREATE TABLE `sys_campaign_group` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT 'id',
`campaign_id` varchar(100) DEFAULT NULL COMMENT '活动id',
`group_id` varchar(100) DEFAULT NULL COMMENT '客群id',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`create_by` varchar(10) DEFAULT NULL COMMENT '创建人',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=359 DEFAULT CHARSET=utf8 COMMENT='清单客群关系表'
-- ibs_pre.sys_campaign_second definition
CREATE TABLE `sys_campaign_second` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT 'id',
`campaign_name` varchar(100) DEFAULT NULL COMMENT '活动名称(任务名称)',
`dept_id` bigint(20) DEFAULT NULL COMMENT '部门id',
`user_id` bigint(20) DEFAULT NULL COMMENT '用户id',
`create_by` varchar(100) DEFAULT NULL COMMENT '创建者',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`update_by` varchar(100) DEFAULT NULL COMMENT '更新者',
`update_time` datetime DEFAULT NULL COMMENT '更新时间',
`start_time` datetime DEFAULT NULL COMMENT '活动开始时间',
`end_time` datetime DEFAULT NULL COMMENT '活动结束时间',
`campaign_degree` varchar(100) DEFAULT NULL COMMENT '活动紧急程度,高,中,低',
`remark` varchar(500) DEFAULT NULL COMMENT '备注',
`del_flag` char(1) DEFAULT '0' COMMENT '删除标志(0代表存在2代表删除)',
`campaign_type` varchar(100) DEFAULT NULL COMMENT '活动类型,走访,电话,短信',
`claim_type` char(1) DEFAULT NULL COMMENT '认领类型0强制认领1可选认领',
`distribute_type` varchar(100) DEFAULT NULL COMMENT '第一优先级分配规则0手动指定1按照客户归属2按照地址归属',
`campaign_id` varchar(100) DEFAULT NULL COMMENT '活动id(任务id)',
`claim_start_time` datetime DEFAULT NULL COMMENT '活动认领开始时间',
`claim_end_time` datetime DEFAULT NULL COMMENT '活动认领结束时间',
`executer` char(1) DEFAULT NULL COMMENT '执行人,0代表机构1代表个人2代表混合分配',
`create_role` char(1) DEFAULT NULL COMMENT '活动创建角色0总行管理员1: 零售 2对公 3运管 5 支行',
`group_id` varchar(100) DEFAULT NULL COMMENT '客群id',
`second_push_status` char(1) DEFAULT '0' COMMENT '活动是否二次推送过0未推送1已推送',
`distribute_type2` varchar(100) DEFAULT NULL COMMENT '第二优先级分配规则0手动指定1按照客户归属2按照地址归属',
`distribute_type3` varchar(100) DEFAULT NULL COMMENT '第三优先级分配规则0手动指定1按照客户归属2按照地址归属',
`task_type` varchar(100) DEFAULT NULL COMMENT '任务类型0营销任务1事务任务',
`check_target` varchar(100) DEFAULT NULL COMMENT '考核目标,存款营销,贷款营销,产品营销,贷前调查,贷后回访,预期催收,其他',
`task_index` varchar(100) DEFAULT NULL COMMENT '任务指标',
`reward` varchar(300) DEFAULT NULL COMMENT '奖励说明',
`feed_back` varchar(100) DEFAULT NULL COMMENT '反馈要求,无,签到签退,拍照,反馈记录',
`cust_type` char(1) DEFAULT NULL COMMENT '客户类型 0个人1商户2企业',
`distribute_cont` varchar(100) DEFAULT NULL COMMENT '規則1内容',
`distribute_cont2` varchar(100) DEFAULT NULL COMMENT '規則2内容',
`distribute_cont3` varchar(100) DEFAULT NULL COMMENT '規則3内容',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=24 DEFAULT CHARSET=utf8 COMMENT='二次分配活动表';
insert into sys_campaign_group(campaign_id ,group_id )
select distinct campaign_id ,group_id from sys_campaign_group_customer;
ALTER TABLE ibs.sys_campaign ADD distribute_cont3 varchar(100) NULL COMMENT '';
ALTER TABLE ibs.sys_campaign ADD distribute_cont2 varchar(100) NULL COMMENT '';
ALTER TABLE ibs.sys_campaign ADD distribute_cont varchar(100) NULL COMMENT '';
ALTER TABLE ibs.sys_campaign MODIFY COLUMN distribute_type2 varchar(200) CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '';
ALTER TABLE ibs.sys_campaign MODIFY COLUMN distribute_type3 varchar(200) CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '';
-- 何
ALTER TABLE ibs.relation_rule ADD add_source varchar(100) NULL COMMENT '地址来源';
ALTER TABLE ibs.relation_rule ADD add_source_id varchar(100) NULL COMMENT '地址来源码值';
ALTER TABLE ibs.cust_tab_list_info ADD is_start varchar(1) NULL COMMENT '0停用1启动';
ALTER TABLE ibs.cust_tab_list_info MODIFY COLUMN comput_type varchar(1) COMMENT '加工类型: 0手动执行1 天2周 3月4年';
--各个客户表都要965以外的其余行社
ALTER TABLE ibs.cust_info_retail_965 ADD record_status char(1) NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_merchant_965 ADD record_status char(1) NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_business_965 ADD record_status char(1) CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_retail_807 ADD record_status char(1) NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_merchant_807 ADD record_status char(1) NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_business_807 ADD record_status char(1) CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_retail_831 ADD record_status char(1) NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_merchant_831 ADD record_status char(1) NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_business_831 ADD record_status char(1) CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_retail_931 ADD record_status char(1) NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_merchant_931 ADD record_status char(1) NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
ALTER TABLE ibs.cust_info_business_931 ADD record_status char(1) CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '建档标识,新入客户表的客户状态为未建档';
-- ibs.family_member definition
CREATE TABLE `family_member` (
`id_card` varchar(18) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '身份证号',
`name` varchar(50) COLLATE utf8mb4_unicode_ci NOT NULL COMMENT '姓名',
`father_card` varchar(18) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '父亲身份证',
`mother_card` varchar(18) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '母亲身份证',
`spouse_card` varchar(18) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '配偶身份证',
`family_id` varchar(100) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '家庭id',
`gender` char(1) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '性别M男F女',
`age` int(11) DEFAULT NULL COMMENT '年龄',
`is_delete` char(1) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '0未删除1逻辑删除',
`bs_id` varchar(500) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '兄弟姐妹唯一id',
`spouse_family_id` varchar(100) COLLATE utf8mb4_unicode_ci DEFAULT NULL COMMENT '配偶家庭id女性出嫁后此字段填充男方家庭id男方结婚后也要写入女方家庭id',
`create_time` datetime DEFAULT NULL,
`create_by` varchar(100) CHARACTER SET utf8 DEFAULT NULL,
`update_by` varchar(100) CHARACTER SET utf8 DEFAULT NULL,
`update_time` datetime DEFAULT NULL,
`birth_date` varchar(100) COLLATE utf8mb4_unicode_ci DEFAULT NULL,
`id` int(11) NOT NULL AUTO_INCREMENT,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=112 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci ROW_FORMAT=DYNAMIC;
INSERT INTO ibs.sys_dict_type
(dict_id, dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark)
VALUES(null, '地址来源码值', 'address_source', '0', 'admin', '2024-10-25 10:52:38', '', NULL, NULL);
INSERT INTO ibs.sys_dict_type
(dict_id, dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark)
VALUES(null, '亲属关系码值', 'family_relation', '0', 'admin', '2024-10-25 10:52:38', '', NULL, NULL);
INSERT INTO ibs.sys_dict_type
(dict_id, dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark)
VALUES(null, '对公经营状态', 'reg_status', '0', 'admin', '2024-10-25 10:52:38', '', NULL, NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'信用卡开卡','0_gh_xykkk','ral_rules',NULL,'default','N','0','admin','2024-10-25 10:55:21','9650702','2024-11-21 10:03:41',NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(1,'信用卡销卡','1_gh_xykxk','ral_rules',NULL,'default','N','0','admin','2024-10-25 10:55:54','9650702','2024-11-20 16:23:07',NULL),
(0,'家庭地址','0_dz_jtdz','ral_rules',NULL,'default','N','0','admin','2024-10-25 10:56:33','9650702','2024-11-21 10:03:44',NULL),
(0,'信用卡-企业开卡','0_gh_xykkk','ral_rules',NULL,'default','N','0','9650702','2024-11-20 16:23:59','9650702','2024-11-21 10:05:16',NULL),
(0,'信用卡-企业销卡','0_gh_xykxk','ral_rules',NULL,'default','N','0','9650702','2024-11-20 16:24:21','9650702','2024-11-21 10:05:21',NULL),
(0,'注册地址','2_dz_zcdz','ral_rules',NULL,'default','N','0','9650702','2024-11-20 16:24:43','9650702','2024-11-21 10:04:03',NULL),
(0,'经营地址','2_dz_jydz','ral_rules',NULL,'default','N','0','9650702','2024-11-20 16:25:01','9650702','2024-11-21 10:04:10',NULL),
(0,'商户-行用卡销卡','1_gh_xykxk','ral_rules',NULL,'default','N','0','9650702','2024-11-20 16:25:26','9650702','2024-11-21 10:04:44',NULL),
(0,'行用卡开卡-商户','1_gh_xykkk','ral_rules',NULL,'default','N','0','9650702','2024-11-20 16:25:45','9650702','2024-11-21 10:04:51',NULL),
(0,'注册地址','1_dz_zcdz','ral_rules',NULL,'default','N','0','9650702','2024-11-20 16:26:00','9650702','2024-11-21 14:18:29',NULL),
(0,'经营地址','1_dz_btdz','ral_rules',NULL,'default','N','0','9650702','2024-11-20 16:26:25','9650702','2024-11-21 14:19:54',NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'工作地址','0_dz_gzdz','ral_rules',NULL,'default','N','0','9650702','2024-11-21 14:20:51','',NULL,NULL),
(0,'户籍地址','0_dz_hjdz','ral_rules',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'核心','0_hx','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'大信贷','0_dxd','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'EICC','0_eicc','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'ECIF','0_ecif','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'手工导入','0_sgdr','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'核心','1_hx','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'大信贷','1_dxd','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'EICC','1_eicc','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'ECIF','1_ecif','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'手工导入','1_sgdr','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'新华社','1_xhs','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'金综','1_jz','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'核心','2_hx','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'大信贷','2_dxd','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'EICC','2_eicc','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'ECIF','2_ecif','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'手工导入','2_sgdr','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'新华社','2_xhs','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'金综','2_jz','address_source',NULL,'default','N','0','9650702','2024-11-21 14:21:10','',NULL,NULL),
(0,'外高祖母','m,m,m,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'小姑子','h,ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾伯祖父','f,f,f,f,bb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外甥女','ss,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'女婿','h,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'舅祖母/妗婆','f,m,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外曾孙','s,d,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'叔祖母','f,f,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾祖姑母/太姑婆','f,f,f,f,bb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'女儿','h,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高祖姑丈/老太姑婆公','f,f,f,f,ss,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'公公','h,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高祖母/老太奶奶','f,f,f,f,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姑夫','f,f,bs,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'嫂子','bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂外姑丈/堂外姑婆公','m,f,f,bb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'婆婆','h,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'妹夫','ss,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'侄子','bb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'表妹夫','f,ss,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'大伯子','h,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高伯祖母/老太婆','f,f,f,f,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂叔祖母','f,f,f,sb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高祖父的妻子(高祖母)','f,f,f,f,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂外叔祖母/堂外婶婆','m,f,f,sb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'大姑子','h,bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'小叔子','h,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'哥哥','bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾外孙女','d,d,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'堂姐夫','f,bb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'祖姑母/姑婆','f,f,ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'妻子的伯祖父','w,f,f,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姐夫/表妹夫','m,sb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'襟兄','w,bs,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表叔','f,f,ss,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表婶','f,f,ss,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾祖姑母/太姑婆','f,f,f,f,sb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'孙女婿','d,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'弟弟','sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'姐姐','bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'祖姑丈/姑婆公','f,f,ss,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾祖姑丈/太姑婆公','f,f,f,f,sb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外曾婆','h,m,m,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'祖姑丈/姑婆公','f,f,f,bb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姨夫','m,f,bs,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姑','f,f,ss,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'妹妹','ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外甥','sb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高叔祖母/老太婆','f,f,f,f,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'女儿','d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'伯祖父','f,f,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂婶','f,f,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外婆','h,m,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'父亲','f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表舅','m,f,bs,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'丈夫','h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外姑丈/外姑婆公','m,f,bs,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'儿媳','w,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'母亲','m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'表妗','m,f,ss,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'弟媳','sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'岳父','w,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'叔祖父','f,f,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'儿子','s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'祖姑母/姑婆','f,f,bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姨','m,f,bs,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'妻子','w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾叔祖父','f,f,f,f,sb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'岳母','w,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'女婿','w,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姐/表妹','m,sb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂外姑丈/堂外姑婆公','m,f,f,sb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表伯','f,f,bs,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姑夫','f,f,ss,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表哥/表弟','m,sb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂妹/妹妹','f,sb,w,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'舅母/舅妈','m,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姨','m,f,ss,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾孙媳妇','s,s,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'祖父','f,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'大外祖母/外太婆/太姥姥','m,f,f,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表哥/表弟','m,ss,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂弟/弟弟','f,sb,w,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'祖母/奶奶','f,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姑','f,f,bs,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外伯祖母/外姆婆','m,f,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'祖姑丈/姑婆公','f,f,bs,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾孙','s,s,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'孙媳妇','s,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'母亲','f,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂伯祖母','f,f,f,bb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾叔祖母','f,f,f,f,sb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姨夫','m,f,ss,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'叔岳父','w,f,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾伯祖母','f,f,f,f,bb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外叔祖母/外婶婆','m,f,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂伯祖父','f,f,f,bb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外姑丈/外姑婆公','m,f,ss,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高伯祖母/老太婆','f,f,f,f,f,bb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'曾伯祖母','f,f,f,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外祖父/外公/姥爷','m,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'父亲/爸爸','m,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表嫂/表弟妇','m,sb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姐夫/表妹夫','m,ss,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表舅','m,f,ss,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外祖母','m,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表甥女','m,mb,s,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'伯岳父','w,f,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'祖姑母/姑婆','f,f,f,bb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'大外祖父/外太公/太姥爷','m,f,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姐夫/表妹夫','m,bb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'大外祖母/外太婆/太姥姥','m,f,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾祖姑母/太姑婆','f,f,f,ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外舅祖母/外妗婆','m,m,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高祖姑丈/老太姑婆公','f,f,f,f,f,bb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'舅舅','m,mb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂外伯祖父/堂外伯公','m,f,f,bb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表舅','m,m,mb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高叔祖父/老太公','f,f,f,f,f,sb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'曾祖姑母/太姑婆','f,f,f,bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'姑丈/姑夫','f,ss,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾叔祖父','f,f,f,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表嫂/表弟妇','m,bb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高祖父','f,f,f,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高祖母/老太奶奶','f,f,f,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂外姑母/堂外姑婆','m,f,f,bb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表弟','f,ss,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'孙女','d,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'高祖姑母/老太姑婆','f,f,f,f,f,sb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'外舅祖父/外舅公','m,m,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾伯祖父','f,f,f,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'女婿','d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂伯','f,bb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾祖母/太奶奶','f,f,f,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾祖姑丈/太姑婆公','f,f,f,bs,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'岳曾祖父','w,f,f,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外甥','d,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姨','m,bs,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表妹','f,ss,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'曾祖姑丈/太姑婆公','f,f,f,ss,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'堂外姑母/堂外姑婆','m,f,f,sb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'表姐/表妹','m,bs,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'曾祖姑丈/太姑婆公','f,f,f,f,bb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'姨夫','m,bs,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'伯母','f,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:15','',NULL,NULL),
(0,'外曾祖母','m,m,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'太岳母','w,f,f,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂外叔祖父/堂外叔公','m,f,f,sb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表嫂','f,bs,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'堂妹夫','f,sb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表嫂/表弟妇','m,ss,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'姑母/姑姑','f,ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'岳祖父','w,f,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'外舅祖母/外妗婆','m,m,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表姐/表妹','m,bb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'婶婶','f,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'太岳母','w,f,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'外舅祖父/外舅公','m,m,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表姐/表妹','m,ss,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'高伯祖父/老太公','f,f,f,f,f,bb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'祖姑母/姑婆','f,f,f,sb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'姨丈/姨夫','m,ss,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'叔岳母','w,f,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'舅妈','m,mb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'高祖姑母/老太姑婆','f,f,f,f,f,bb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表舅','m,mb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂叔祖父','f,f,f,sb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'伯伯','f,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'高叔祖母/老太婆','f,f,f,f,f,sb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'孙女','s,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂叔','f,sb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'曾叔祖母','f,f,f,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'舅母/舅妈','m,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表姐夫/表妹夫','m,bs,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'姑姑','f,bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'叔叔','f,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'孙子','s,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表哥/表弟','m,bb,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂妹','f,sb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'儿媳','s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'伯岳母','w,f,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'高祖姑母/老太姑婆','f,f,f,f,ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'小姨子','w,ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'襟弟','w,ss,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'大妗','w,bb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'高祖姑母/老太姑婆','f,f,f,f,bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'大姨子','w,bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'小舅子','w,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'高叔祖父/老太公','f,f,f,f,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'高伯祖父/老太公','f,f,f,f,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'大舅子','w,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表姐夫','f,bs,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂弟妇/弟妹','f,sb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'外姑母/外姑婆','m,f,bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'孙媳妇的丈夫(即自己)','s,s,w,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'外叔祖父/外叔公','m,f,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'外甥女','d,s,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'高祖姑丈/老太姑婆公','f,f,f,f,f,sb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'外伯祖父/外伯公','m,f,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'阿姨','m,bs','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表弟妇','f,ss,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'舅祖父/舅公','f,m,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂外伯祖母/堂外姆婆','m,f,f,bb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'祖姑丈/姑婆公','f,f,f,sb,d,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'姨母/姨姨','m,ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'曾祖母/太奶奶','f,f,m','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'舅祖母/妗婆','f,m,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表嫂/表弟妇','m,bs,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂姐/堂姊','f,bb,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'舅祖父/舅公','f,m,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'祖母/奶奶','f,f,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表姆','f,f,bs,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'妈妈的弟弟','m,sb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'小妗','w,sb,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'外姑母/外姑婆','m,f,ss','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'姐夫','bs,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'外高祖母的丈夫(外高祖父)','m,m,m,m,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂嫂/嫂嫂','f,bb,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表姐','f,bs,d','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'曾祖父','f,f,f','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'高祖姑丈/老太姑婆公','f,f,f,f,bs,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'堂侄','f,bb,s,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'舅父/大舅','m,bb','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表兄/表哥','f,bs,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'侄女','bs,s','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'姑丈/姑夫','f,bs,h','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'表妗','m,f,bs,s,w','family_relation',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'变更','1','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'变更中','2','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'吊销已注销','3','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'存续(在营、开业,在册)','4','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'已注销','5','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'歇业','6','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'正常','7','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'注销','8','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'其他','9','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'吊销','10','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'吊销未注销','11','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'在业','12','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
INSERT INTO ibs.sys_dict_data (dict_sort,dict_label,dict_value,dict_type,css_class,list_class,is_default,status,create_by,create_time,update_by,update_time,remark) VALUES
(0,'废止','13','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'撤销','14','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'注销中','15','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'吊销已注销','16','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'存续','17','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'迁出','18','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'备案','19','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'开业','20','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL),
(0,'空','21','reg_status',NULL,NULL,'N','0','admin','2025-03-12 10:50:16','',NULL,NULL);
----吴
-- ibs.task_visit_log definition
CREATE TABLE `task_visit_log` (
`id` bigint(21) NOT NULL AUTO_INCREMENT COMMENT '主键',
`cust_id` varchar(255) DEFAULT NULL COMMENT '客户号',
`nick_name` varchar(255) DEFAULT NULL COMMENT '柜员名称',
`cust_feedback` varchar(10) DEFAULT NULL COMMENT '客户意向',
`visit_result` varchar(10) DEFAULT NULL COMMENT '营销结果',
`remark` varchar(255) DEFAULT NULL COMMENT '备注',
`create_by` varchar(32) DEFAULT NULL COMMENT '创建人',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8 COMMENT='任务走访记录表';
-- ibs.task_visit_error_log definition
CREATE TABLE `task_visit_error_log` (
`id` bigint(21) NOT NULL AUTO_INCREMENT COMMENT '主键',
`cust_id` varchar(255) DEFAULT NULL COMMENT '客户号',
`task_id` varchar(255) DEFAULT NULL COMMENT '任务id',
`address_error_flag` varchar(1) DEFAULT NULL COMMENT '地址是否错误',
`contact_error_flag` varchar(1) DEFAULT NULL COMMENT '联系方式是否错误',
`create_by` varchar(32) DEFAULT NULL COMMENT '创建人',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8 COMMENT='任务走访无法触达';

0
doc/0324sql Normal file
View File

178
doc/0417更新sql.txt Normal file
View File

@@ -0,0 +1,178 @@
-- zy
CREATE TABLE `sys_campaign_group_customer_supplement` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT 'id',
`cust_id` varchar(100) DEFAULT NULL COMMENT '客户号',
`campaign_id` varchar(100) DEFAULT NULL COMMENT '活动id',
`group_id` varchar(100) DEFAULT NULL COMMENT '分群id',
`dept_id` bigint(20) DEFAULT NULL COMMENT '部门id',
`user_id` bigint(20) DEFAULT NULL COMMENT '用户id',
`create_by` varchar(100) DEFAULT NULL COMMENT '创建者',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`update_by` varchar(100) DEFAULT NULL COMMENT '更新者',
`update_time` datetime DEFAULT NULL COMMENT '更新时间',
`remark` varchar(500) DEFAULT NULL COMMENT '备注',
`del_flag` char(1) DEFAULT '0' COMMENT '删除标志(0代表存在2代表删除)',
`grid_id` bigint(20) DEFAULT NULL COMMENT '网格id',
`list_type` char(1) DEFAULT NULL COMMENT '0推荐营销清单1我的营销清单出版需求设计的字段现在暂时不用',
`push_status` char(1) DEFAULT '0' COMMENT '推送状态(0代表未推送1代表推送成功2代表推送失败)',
`org_claim_status` char(1) DEFAULT '0' COMMENT '机构认领状态(0待认领1已认领)',
`org_distribute_status` char(1) DEFAULT '0' COMMENT '机构分配状态(0待分配1已分配)',
`cust_claim_status` char(1) DEFAULT '0' COMMENT '客户经理认领状态(0待认领1已认领)',
`create_role` char(1) DEFAULT NULL COMMENT '记录创建角色0总行管理员1零售2对公3运管5支行',
`grid_name` varchar(100) DEFAULT NULL COMMENT '一级网格名称',
`grid_name2` varchar(100) DEFAULT NULL COMMENT '二级网格名称',
`outlets` varchar(100) DEFAULT NULL COMMENT '客户经理所在网点',
`cust_idc` varchar(100) DEFAULT NULL COMMENT '客户身份证号',
`second_push_status` char(1) DEFAULT '0' COMMENT '活动是否二次推送过0未推送1已推送',
`cust_phone` varchar(100) DEFAULT NULL COMMENT '客户电话',
`social_credit_code` varchar(100) DEFAULT NULL COMMENT '统一社会信用识别码(只有企业和商户有)',
`outlets_id` varchar(30) DEFAULT NULL COMMENT '客户经理所在网点ID(若客户经理不属于网点,则无值)',
`push_user_level` varchar(10) DEFAULT NULL COMMENT '推送客户经理级别head 总行 branch支行',
`push_status_branch` varchar(1) DEFAULT NULL COMMENT '支行推送状态 0 未推送1成功2失败',
PRIMARY KEY (`id`),
KEY `sys_campaign_group_customer_supplement_cust_id_IDX` (`cust_id`) USING BTREE,
KEY `sys_campaign_group_customer_supplement_campaign_id_IDX` (`campaign_id`) USING BTREE
) ENGINE=InnoDB AUTO_INCREMENT=3610 DEFAULT CHARSET=utf8 ROW_FORMAT=DYNAMIC COMMENT='活动分群客户关联关系表-跑批结果表-补充客户经理、机构'
ALTER TABLE sys_menu ADD is_link varchar(1) DEFAULT '0' NULL COMMENT '是否可以直接访问';
CREATE TABLE `admin_region_index_965` (
`id` bigint(21) NOT NULL AUTO_INCREMENT COMMENT '主键',
`create_time` date DEFAULT NULL COMMENT '创建日期',
`level` int(11) DEFAULT NULL COMMENT '行政区划等级',
`code` varchar(255) DEFAULT NULL COMMENT '行政区划编码',
`item_name` varchar(255) DEFAULT NULL COMMENT '指标名称',
`item_val` varchar(255) DEFAULT NULL COMMENT '指标值',
`dept_id` bigint(21) DEFAULT NULL COMMENT '归属机构',
`ops_dept` varchar(1) DEFAULT NULL COMMENT '归属部室',
`item_idx` varchar(10) DEFAULT NULL COMMENT '指标码值',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8 COMMENT='行政区划热力指标';
ALTER TABLE draw_shape ADD create_by varchar(100) NULL COMMENT '创建者';
update draw_shape set create_by = update_by;
INSERT INTO sys_dict_type ( dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark) VALUES
('行政区划数据码值', 'admin_region_data_metric', '0', 'admin', '2025-04-01 11:01:29', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '建档率', '1001', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '授信率', '1002', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '合同签约率', '1003', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '信用卡覆盖率', '1004', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, 'ETC覆盖率', '1005', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '丰收互联覆盖率', '1006', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '收单覆盖率', '1007', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣电费覆盖率', '1008', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贷款黑名单占比', '1009', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '五级不良贷款占比(人)', '1010', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '五级不良贷款占比(金额)', '1011', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '合同签约率', '2001', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '签发承兑汇票率', '2002', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贴现业务率', '2003', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '保函业务率', '2004', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '有效代发工资率', '2005', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣电费率', '2006', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣水费率', '2007', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣税费率', '2008', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '票据宝签约率', '2009', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '财资宝签约率', '2010', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '收付宝签约率', '2011', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贸融宝签约率', '2012', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '数字生态产品签约率', '2013', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '开户率', '2014', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '国际结算业务率', '2015', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '远期结算汇业务率', '2016', 'admin_region_data_metric', NULL, 'default', 'N', '0', 'admin', '2025-03-24 20:21:30', '', NULL, NULL);
-- zlb
CREATE TABLE `draw_layer_audit_965` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`shape_id` varchar(100) DEFAULT NULL COMMENT '图形id',
`shape_name` varchar(100) DEFAULT NULL COMMENT '图形名称锚点编号。同客户编号,即证件类型',
`layer_id` varchar(100) DEFAULT NULL COMMENT '图层id',
`layer_name` varchar(100) DEFAULT NULL COMMENT '图层名称',
`dept_id` varchar(100) DEFAULT NULL COMMENT '支行机构号',
`dept_name` varchar(100) NOT NULL COMMENT '支行名称',
`user_name` varchar(100) DEFAULT NULL COMMENT '客户经理柜员号',
`nick_name` varchar(100) NOT NULL COMMENT '客户经理名称(申请者、创建者)',
`ops_dept` varchar(10) NOT NULL COMMENT '部室归属',
`delete_status` int(11) DEFAULT '0' COMMENT '删除状态0为正常1为已删除',
`update_time` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '更新时间',
`create_time` datetime DEFAULT CURRENT_TIMESTAMP COMMENT '申请时间',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='区域审批表';
ALTER TABLE draw_shape ADD audit_status varchar(10) DEFAULT '0' NOT NULL COMMENT '审批状态0待审批1审批通过2拒绝';
ALTER TABLE draw_shape ADD audit_remark varchar(100) NULL COMMENT '审批意见';
ALTER TABLE sys_group_customer MODIFY COLUMN push_status char(1) CHARACTER SET utf8 COLLATE utf8_general_ci DEFAULT '1' NULL COMMENT '导入状态(1代表导入成功2代表导入失败缺乏必填项或地址电话不全)';
--szq
CREATE TABLE `campaign_count` (
`dt` varchar(10) DEFAULT NULL COMMENT '统计日期',
`dept_id` varchar(10) DEFAULT NULL COMMENT '行社机构号',
`dept_name` varchar(10) DEFAULT NULL COMMENT '行社名称',
`user_id` varchar(10) DEFAULT NULL COMMENT '用户id',
`user_name` varchar(10) DEFAULT NULL COMMENT '用户姓名',
`create_camp_num_year` int(10) DEFAULT NULL COMMENT '创建的总任务数--年',
`push_camp_num_year` int(10) DEFAULT NULL COMMENT '推送给我的总任务数--年',
`other_camp_num_year` int(10) DEFAULT NULL COMMENT '其他总任务数--年',
`create_camp_num_month` int(10) DEFAULT NULL COMMENT '创建的总任务数--月',
`push_camp_num_month` int(10) DEFAULT NULL COMMENT '推送给我的总任务数--月',
`other_camp_num_month` int(10) DEFAULT NULL COMMENT '其他总任务数--月',
`create_camp_num_week` int(10) DEFAULT NULL COMMENT '创建的总任务数--周',
`push_camp_num_week` int(10) DEFAULT NULL COMMENT '推送给我的总任务数--周',
`other_camp_num_week` int(10) DEFAULT NULL COMMENT '其他总任务数--周',
`sum_type` char(2) DEFAULT NULL COMMENT '统计层级 0总行 1零售 2公司 3运管 5支行 -1客户经理',
`cust_type` char(1) DEFAULT NULL COMMENT '客户类型 0个人1商户2企业'
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='走访任务统计卡片'
CREATE TABLE `visit_info` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT 'id',
`campaign_id` varchar(100) DEFAULT NULL COMMENT '任务id',
`vis_name` varchar(100) DEFAULT NULL COMMENT '走访客户经理姓名',
`vis_id` varchar(100) DEFAULT NULL COMMENT '走访客户经理id',
`dept_id` varchar(100) DEFAULT NULL COMMENT '走访客户经理部门',
`vis_time` datetime DEFAULT NULL COMMENT '走访时间',
`cust_name` varchar(100) DEFAULT NULL COMMENT '走访客户名称',
`cust_idc` varchar(100) DEFAULT NULL COMMENT '客户证件号',
`social_credit_code` varchar(100) DEFAULT NULL COMMENT '企业(商户)统信码',
`create_by` varchar(100) DEFAULT NULL COMMENT '创建者',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`update_by` varchar(100) DEFAULT NULL COMMENT '更新者',
`update_time` datetime DEFAULT NULL COMMENT '更新时间',
`remark` varchar(500) DEFAULT NULL COMMENT '走访备注',
`cust_type` char(1) DEFAULT NULL COMMENT '客户类型 0个人1商户2企业',
`dept_name` varchar(100) DEFAULT NULL COMMENT '部门名称',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1232 DEFAULT CHARSET=utf8 COMMENT='走访名单表'
CREATE TABLE `visit_campaign_count` (
`id` int(11) NOT NULL AUTO_INCREMENT COMMENT 'id',
`campaign_id` varchar(100) DEFAULT NULL COMMENT '任务id',
`cust_num` bigint(20) DEFAULT NULL COMMENT '活动客户数',
`push_success_num` bigint(20) DEFAULT NULL COMMENT '推送成功客户数',
`allocate_rate` varchar(100) DEFAULT NULL COMMENT '机构分配率',
`issued_num` varchar(100) DEFAULT NULL COMMENT '客户认领率',
`claim_num` bigint(20) DEFAULT NULL COMMENT '认领客户数',
`valid_visit_num` bigint(20) DEFAULT NULL COMMENT '有效待走访客户数',
`visit_rate` varchar(100) DEFAULT NULL COMMENT '走访率',
`loan_sign_rate` varchar(100) DEFAULT NULL COMMENT '贷款合同签约率',
`increase_deposit_amount` varchar(100) DEFAULT NULL COMMENT '活期存款提升金额',
`push_client_id` varchar(100) DEFAULT NULL COMMENT '推送的客户经理',
`cust_type` char(1) DEFAULT NULL COMMENT '客户类型 0个人1商户2企业',
`dispatch_num` bigint(20) DEFAULT NULL COMMENT '已下发客户数',
`dept_id` bigint(20) DEFAULT NULL COMMENT '机构号',
`campaign_create_time` varchar(100) DEFAULT NULL COMMENT '活动创建时间',
`start_time` varchar(100) DEFAULT NULL COMMENT '活动开始时间',
`end_time` varchar(100) DEFAULT NULL COMMENT '活动结束时间',
`claim_ddline` varchar(100) DEFAULT NULL COMMENT '活动认领时限',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=537 DEFAULT CHARSET=utf8 ROW_FORMAT=DYNAMIC COMMENT='走访任务统计'

371
doc/0515更新sql.txt Normal file

File diff suppressed because one or more lines are too long

295
doc/2.2.3需求slq Normal file
View File

@@ -0,0 +1,295 @@
-- zy
INSERT INTO sys_dict_type
( dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark)
VALUES('自定义名单网格热力图-公司指标', 'gridshapecountindex_gs', '0', 'admin', '2025-06-20 16:15:28', 'admin', '2025-06-20 16:16:18', NULL);
INSERT INTO sys_dict_type
( dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark)
VALUES('自定义名单网格热力图-零售指标', 'gridshapecountindex_ls', '0', 'admin', '2025-06-20 16:16:08', '', NULL, NULL);
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '入格客户数', 'cust_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '活期存款余额', 'hq_cur_balance', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '保证金存款余额', 'bz_cur_balance', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贷款余额', 'loan_balance_cny', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贴现余额', 'finance_prod_711_balance', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '承兑汇票余额', 'finance_prod_716_balance', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贷款年日均', 'loan_year_dailyaverage', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '合同签约率', 'htqy_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '签发承兑汇票率', 'qfcd_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贴现业务率', 'tx_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '保函业务率', 'bh_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '有效代发工资率', 'yxdfgz_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣电费率', 'dkdf_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣水费率', 'dksf_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣税费率', 'dkshf_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '票据宝签约率', 'pjb_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '财资宝签约率', 'czb_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '收付宝签约率', 'sfb_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贸融宝签约率', 'mrb_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '数字生态产品签约率', 'szst_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '开户率', 'kh_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '国际结算业务率', 'gjjsyw_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '远期结算汇业务率', 'yqjsh_rat', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '合同签约数', 'htqy_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '签发承兑汇票数', 'qfcd_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贴现业务数', 'tx_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '保函业务数', 'bh_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '有效代发工资数', 'yxdfgz_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '月均代发工资笔数', 'ustr_count_per_m', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '月均代发工资金额(元)', 'ustr_bal_m', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣电费数', 'dkdf_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣水费数', 'dksf_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣税费数', 'dkshf_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '票据宝签约数', 'pjb_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '财资宝签约数', 'czb_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '收付宝签约数', 'sfb_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贸融宝签约数', 'mrb_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '数字生态产品签约数', 'szst_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '开户数', 'kh_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '国际结算业务数', 'gjjsyw_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '远期结算汇业务数', 'yqjsh_num', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近365天已走访人数', 'zf_365cnt', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近180天已走访人数', 'zf_180cnt', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近90天已走访人数', 'zf_90cnt', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近30天已走访人数', 'zf_30cnt', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', '', NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近365天走访率', 'zf_365rt', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近180天走访率', 'zf_180rt', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近90天走访率', 'zf_90rt', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近30天走访率', 'zf_30rt', 'gridshapecountindex_gs', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '入格客户数', 'cust_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '活期存款余额', 'cur_bal_d', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '定期存款余额', 'cur_bal_t', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贷款余额', 'bal_loan', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '五级不良贷款余额', 'cur_bal_5_bad', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '活期存款年日均', 'cur_d_ave', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '定期存款年日均', 'cur_t_ave', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贷款年日均', 'loan_ave', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '建档率', 'ph_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '授信率', 'sx_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '合同签约率', 'yxht_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '信用卡覆盖率', 'xyk_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '丰收互联覆盖率', 'fshl_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '收单覆盖率', 'sd_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, 'ETC覆盖率', 'etc_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣电费覆盖率', 'dian_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贷款黑名单占比', 'black_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '五级不良贷款占比(人)', 'bad_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '五级不良贷款占比(金额)', 'bad_bal_rat', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '建档客户数', 'ph_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '授信客户数', 'sx_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '合同签约客户数', 'yxht_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '持有信用卡客户数', 'xyk_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '开通丰收互联客户数', 'fshl_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '收单客户数', 'sd_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, 'ETC客户数', 'etc_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '代扣电费客户数', 'dian_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '贷款黑名单客户数', 'black_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '五级不良贷款客户数', 'bad_num', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近365天已走访人数', 'zf_365cnt', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近180天已走访人数', 'zf_180cnt', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近90天已走访人数', 'zf_90cnt', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近30天已走访人数', 'zf_30cnt', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近365天走访率', 'zf_365rt', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近180天走访率', 'zf_180rt', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近90天走访率', 'zf_90rt', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
INSERT INTO sys_dict_data ( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) VALUES( 0, '近30天走访率', 'zf_30rt', 'gridshapecountindex_ls', '', '', 'N', '0', 'admin', '2025-03-12 10:50:15', NULL, NULL, '');
ALTER TABLE sys_campaign_group_customer ADD cust_name varchar(100) NULL COMMENT '客戶姓名';
ALTER TABLE sys_campaign_group_customer ADD cust_isn varchar(100) NULL COMMENT '客戶内碼';
ALTER TABLE sys_campaign_group_customer ADD lp_name varchar(100) NULL COMMENT '法人姓名';
ALTER TABLE sys_campaign ADD `related_model_id` varchar(100) NULL COMMENT '关联反馈模板uuid 默认模板-1';
CREATE TABLE `lowcode_visst_feedback_model` (
`id` bigint(21) NOT NULL AUTO_INCREMENT COMMENT '主键',
`uuid` varchar(100) DEFAULT NULL COMMENT '主键',
`dept_id` bigint(21) DEFAULT NULL COMMENT '机构号',
`model_name` varchar(200) DEFAULT NULL COMMENT '模板名字',
`model_detal` json DEFAULT NULL COMMENT '模板内容',
`belong_outlet_id` varchar(500) DEFAULT NULL COMMENT '归属网点',
`belong_outlet_name` varchar(500) DEFAULT NULL COMMENT '归属网点',
`CREATED_BY` varchar(32) DEFAULT NULL COMMENT '创建人',
`CREATED_TIME` datetime DEFAULT NULL COMMENT '创建时间',
`UPDATED_BY` varchar(32) DEFAULT NULL COMMENT '更新人',
`UPDATED_TIME` datetime DEFAULT NULL COMMENT '更新时间',
`model_type` varchar(2) DEFAULT NULL COMMENT '模板类型 0零售1公司2运管',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8 COMMENT='走访反馈自定义模板编辑表';
INSERT INTO sys_dict_type
( dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark)
VALUES( '外部系统链接', 'external_url', '0', 'admin', '2025-07-03 18:07:27', '', NULL, NULL);
INSERT INTO sys_dict_data
( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark)
VALUES(0, 'product_manual', '数智支行操作手册V1.0.docx', 'product_manual_szzh', NULL, 'default', 'N', '0', 'admin', '2025-06-26 19:28:33', '', NULL, NULL);
INSERT INTO sys_dict_data
( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark)
VALUES(0, '965-系统A', 'http://xxxxx/', 'external_url', NULL, 'default', 'N', '0', 'admin', '2025-07-03 18:08:44', '', NULL, NULL);
INSERT INTO sys_dict_data
( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark)
VALUES(1, '965-系统B', 'http://xxxx', 'external_url', NULL, 'default', 'N', '0', 'admin', '2025-07-03 18:09:09', '', NULL, NULL);
INSERT INTO sys_dict_data
( dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark)
VALUES( 0, '932-系统C', 'HTTPS://1213', 'external_url', NULL, 'default', 'N', '0', 'admin', '2025-07-03 18:35:28', '', NULL, NULL);
INSERT INTO sys_dict_type
(dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark)
VALUES( '数智支行操作手册名称', 'product_manual_szzh', '0', 'admin', '2025-06-26 19:27:31', '', NULL, NULL);
-- ibs.grid_region_transfer definition
CREATE TABLE `grid_region_transfer` (
`id` bigint(21) NOT NULL AUTO_INCREMENT COMMENT 'id',
`status` varchar(10) DEFAULT NULL COMMENT '状态 0支行审批 1总行审批 2审批通过 -1审批拒绝',
`cust_id` varchar(100) DEFAULT NULL COMMENT '客户号',
`cust_name` varchar(100) DEFAULT NULL COMMENT '客户名称',
`cust_type` varchar(100) DEFAULT NULL,
`ops_dept` varchar(10) DEFAULT NULL COMMENT '部室',
`prev_grid_id` bigint(21) DEFAULT NULL COMMENT '原网格',
`prev_grid_name` varchar(255) DEFAULT NULL COMMENT '原网格名称',
`prev_user` varchar(100) DEFAULT NULL COMMENT '原客户经理',
`prev_branch_id` bigint(21) DEFAULT NULL COMMENT '原支行',
`prev_branch_name` varchar(100) DEFAULT NULL COMMENT '原支行名称',
`next_grid_id` bigint(21) DEFAULT NULL COMMENT '移交网格',
`next_grid_name` varchar(255) DEFAULT NULL COMMENT '移交网格名称',
`next_branch_ids` varchar(255) DEFAULT NULL COMMENT '移交支行',
`next_branch_name` varchar(255) DEFAULT NULL COMMENT '移交支行名称',
`next_users` varchar(255) DEFAULT NULL COMMENT '移交客户经理',
`approve_branch_user` varchar(255) DEFAULT NULL COMMENT '审批支行管理员',
`approve_branch_result` varchar(1) DEFAULT NULL COMMENT '审批支行结果',
`approve_head_user` varchar(255) DEFAULT NULL COMMENT '审批总行部室管理员',
`approve_head_result` varchar(1) DEFAULT NULL COMMENT '审批总行结果',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
`create_by` varchar(100) DEFAULT NULL COMMENT '创建者',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8 COMMENT='行政网格移交表';
ALTER TABLE ibs.grid_region_cust_user_965 ADD region_name varchar(100) NULL;
ALTER TABLE ibs.grid_region_cust_user_965 ADD top_grid_duty_type varchar(100) NULL;
ALTER TABLE ibs.grid_region_cust_user_965 ADD sec_grid_duty_type varchar(100) NULL;
-- ibs.task_visit_cust_address definition
CREATE TABLE `task_visit_cust_address` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`cust_id` varchar(50) NOT NULL,
`province` varchar(50) DEFAULT NULL,
`city` varchar(50) DEFAULT NULL,
`county` varchar(50) DEFAULT NULL,
`detail_address` text,
`lng` decimal(15,8) DEFAULT NULL,
`lat` decimal(15,8) DEFAULT NULL,
`user_name` varchar(50) DEFAULT NULL,
`update_time` datetime DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=2 DEFAULT CHARSET=utf8 COMMENT='走访地址采集';
-- ibs.task_visit_image definition
CREATE TABLE `task_visit_image` (
`file_id` varchar(100) NOT NULL COMMENT 'uuid',
`record_id` varchar(100) NOT NULL COMMENT '任务走访id',
`sign_type` varchar(1) NOT NULL COMMENT '打卡类型 0签到 1签退',
`create_time` datetime DEFAULT NULL COMMENT '创建时间',
PRIMARY KEY (`file_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='走访打卡图片';
-- ibs.task_visit_record definition
CREATE TABLE `task_visit_record` (
`id` varchar(100) NOT NULL COMMENT 'id',
`campaign_id` varchar(100) NOT NULL COMMENT '任务id',
`campaign_name` varchar(100) NOT NULL COMMENT '任务名称',
`cust_id` varchar(100) NOT NULL COMMENT '客户号',
`cust_name` varchar(100) NOT NULL COMMENT '客户名称',
`user_id` bigint(20) DEFAULT NULL,
`nick_name` varchar(100) NOT NULL COMMENT '客户经理名称',
`user_name` varchar(100) NOT NULL COMMENT '客户经理柜员号',
`sign_id` varchar(100) DEFAULT NULL,
`latest_sign` varchar(100) DEFAULT NULL,
`duration` double DEFAULT '0',
`feedback_id` varchar(100) DEFAULT NULL,
`feedback_type` varchar(100) DEFAULT NULL COMMENT '反馈模板类型 0对私 1对公 2自定义',
`feedback_template_id` varchar(100) DEFAULT NULL,
`cust_type` varchar(100) DEFAULT NULL,
`visit_type` varchar(100) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='任务走访记录';
-- ibs.task_visit_sign definition
CREATE TABLE `task_visit_sign` (
`id` varchar(100) NOT NULL COMMENT 'id',
`record_id` varchar(100) DEFAULT NULL COMMENT '走访记录id',
`sign_in_time` datetime DEFAULT NULL COMMENT '签到时间',
`sign_in_address` text COMMENT '签到地址',
`sign_in_lng` decimal(15,8) DEFAULT NULL COMMENT '签到经度',
`sign_in_lat` decimal(15,8) DEFAULT NULL COMMENT '签到纬度',
`sign_out_time` datetime DEFAULT NULL COMMENT '签退时间',
`sign_out_address` text COMMENT '签退地址',
`sign_out_lng` decimal(15,8) DEFAULT NULL COMMENT '签退经度',
`sign_out_lat` decimal(15,8) DEFAULT NULL COMMENT '签退纬度',
`sign_out_remark` text,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='走访任务打卡记录';
-- ibs.visit_feedback_private definition
CREATE TABLE `visit_feedback_private` (
`id` varchar(100) NOT NULL COMMENT 'uuid',
`client_suggestion` text COMMENT '客户反馈意见',
`client_label` text COMMENT '客户标签',
`intend_product` text COMMENT '意向产品',
`other_intend` text COMMENT '其他意向',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='走访反馈对私';
-- ibs.visit_feedback_public definition
CREATE TABLE `visit_feedback_public` (
`id` varchar(100) NOT NULL COMMENT 'uuid',
`client_suggestion` text COMMENT '客户意见',
`client_label` text COMMENT '客户标签',
`status_flag` varchar(1) DEFAULT NULL COMMENT '是否经营',
`address_consist` varchar(1) DEFAULT NULL COMMENT '地址是否一致',
`address` text COMMENT '地址',
`scope_consist` varchar(1) DEFAULT NULL COMMENT '经营范围是否一致',
`scope` text COMMENT '经营范围',
`relate_person` text COMMENT '关联人',
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='走访反馈对公';
-- ibs.oss_file_data definition
CREATE TABLE `oss_file_data` (
`file_id` varchar(255) NOT NULL COMMENT 'uuid',
`file_name` varchar(255) NOT NULL COMMENT '文件名',
`original_file_name` varchar(100) DEFAULT NULL,
`content_type` varchar(255) DEFAULT NULL COMMENT '文件类型',
`file_size` double DEFAULT NULL,
`file_enum` varchar(100) DEFAULT NULL,
`user_name` varchar(100) DEFAULT NULL,
`file_url` varchar(255) NOT NULL COMMENT '文件url',
`create_time` datetime DEFAULT NULL,
PRIMARY KEY (`file_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
CREATE TABLE `qywx_org` (
`org_id` varchar(100) DEFAULT NULL COMMENT '机构id',
`app_id` varchar(100) DEFAULT NULL,
`agent_id` varchar(100) DEFAULT NULL,
`secret` varchar(100) DEFAULT NULL
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='企业微信机构参数表'

143
doc/v2.2.2_mysql.txt Normal file
View File

@@ -0,0 +1,143 @@
INSERT INTO sys_dict_type ( dict_name, dict_type, status, create_by, create_time, update_by, update_time, remark) VALUES('地图拓客货币币种码值', 'cust_map_cur_metric', '0', 'admin', '2025-05-23 10:06:15', '', NULL, NULL);
INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, css_class, list_class, is_default, status, create_by, create_time, update_by, update_time, remark) values
(0, '人民币元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '加元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '哥伦比亚比索', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '德国马克', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '挪威马克', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '新加坡元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '日元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '欧元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '法国法郎', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '港元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '澳大利亚元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '瑞典克朗', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '瑞士法郎', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '美元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '英镑', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '阿富汗尼', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '韩元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '新台币', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL),
(0, '新西兰元', '101', 'cust_map_cur_metric', NULL, 'default', 'N', '0', 'admin', '2025-05-23 10:14:00', '', NULL, NULL);
-- dept_address definition
CREATE TABLE `dept_address` (
`dept_id` bigint(21) NOT NULL COMMENT '部门id',
`address` longtext,
`city` varchar(100) DEFAULT NULL,
`lng` decimal(15,8) DEFAULT NULL,
`lat` decimal(15,8) DEFAULT NULL,
PRIMARY KEY (`dept_id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='机构地址表';
CREATE TABLE cust_map_favorite(
id bigint(21) NOT NULL COMMENT '主键' ,
user_name VARCHAR(100) COMMENT '用户名' ,
cust_name VARCHAR(100) COMMENT '企业名称' ,
lp_name VARCHAR(100) COMMENT '法人姓名' ,
phone_number VARCHAR(100) COMMENT '联系方式' ,
regist_capi_show VARCHAR(100) COMMENT '注册资本展示字段' ,
province VARCHAR(100) COMMENT '省' ,
city VARCHAR(100) COMMENT '市' ,
address_detail longtext COMMENT '详细地址' ,
longitude DECIMAL(15,15) COMMENT '经度' ,
latitude DECIMAL(15,15) COMMENT '纬度' ,
start_date DATE COMMENT '成立年限' ,
PRIMARY KEY (id)
) COMMENT = '地图拓客收藏表';
INSERT INTO dept_address (dept_id,address,city,lng,lat) VALUES
(965000,'临海市大洋街道河阳路299号','台州市',121.19534176,28.88832500),
(965010,'临海市大洋街道河阳路299号','台州市',121.19534176,28.88832500),
(965013,'临海市凯歌路2号','台州市',121.15229963,28.86509170),
(965020,'临海市古城街道巾山中路2号','台州市',121.14417311,28.85059030),
(965022,'临海市古城街道洪池路108号、110号、112号','台州市',121.13400420,28.85616354),
(965030,'临海市大洋街道柏叶中路291号','台州市',121.18192853,28.87585265),
(965035,'临海市大田街道东方大道659号','台州市',121.20797193,28.91396531),
(965036,'临海市大洋街道绿化村','台州市',121.16425365,28.88920773),
(965040,'临海市江南街道江南大道4号','台州市',121.14258149,28.82589609),
(965041,'临海市江南街道小溪村1-98号','台州市',121.13226023,28.78969755);
INSERT INTO dept_address (dept_id,address,city,lng,lat) VALUES
(965042,'临海市古城街道两水村','台州市',121.16166680,28.84179629),
(965050,'临海市大田街道奋进东街258号','台州市',121.21702020,28.91170836),
(965052,'临海市大田街道奋进西街119号','台州市',121.20810766,28.91187499),
(965060,'临海市汛桥镇汛汇路2号','台州市',121.18481972,28.79844536),
(965070,'临海市东塍镇川津路427号812','台州市',121.26984057,28.93071358),
(965071,'临海市东塍镇屈家村2157A','台州市',121.26016734,28.94013888),
(965072,'临海市东塍镇康一村371号','台州市',121.40748541,28.93156402),
(965080,'临海市邵家渡街道邵临东路54号','台州市',121.22261494,28.86553519),
(965081,'临海市邵家渡街道中台村265号','台州市',121.20895872,28.82085263),
(965090,'临海市小芝镇溪滨北路1号','台州市',121.46179992,28.85924349);
INSERT INTO dept_address (dept_id,address,city,lng,lat) VALUES
(965100,'临海市杜桥镇滨海路599号','台州市',121.50550545,28.75783738),
(965102,'临海市杜桥镇西岸村4-82号','台州市',121.53366274,28.73910159),
(965104,'临海市杜桥镇汾东村15-14、15-15号','台州市',121.48521237,28.74923323),
(965108,'临海市杜桥镇杜下浦村','台州市',121.54213682,28.72408230),
(965109,'临海市杜桥镇下街路耀达商城16幢','台州市',121.51490541,28.76573292),
(965110,'浙江省临海市上盘镇西大路10号','台州市',121.58828484,28.75916566),
(965111,'浙江省临海市上盘镇银山街267号','台州市',121.60305280,28.75354870),
(965112,'浙江省临海市台州湾经济技术开发区乐安路77、79、81、83号','台州市',121.64550133,28.72767696),
(965120,'临海市桃渚镇东洋大道北7号','台州市',121.59241345,28.82726747),
(965121,'临海市桃渚镇连盘南路124号','台州市',121.58664399,28.78455584);
INSERT INTO dept_address (dept_id,address,city,lng,lat) VALUES
(965122,'临海市桃渚镇顺南路119号','台州市',121.60391437,28.83248647),
(965123,'临海市桃渚镇项庄村','台州市',121.62403138,28.82529239),
(965124,'临海市桃渚镇城外村桃江路61号','台州市',121.54135916,28.83171938),
(965130,'临海市尤溪镇义城路205号','台州市',121.11074788,28.74381794),
(965140,'临海市涌泉镇灵泉街171号','台州市',121.32395548,28.76260117),
(965141,'临海市涌泉镇后泾村','台州市',121.35571399,28.72437942),
(965142,'临海市涌泉镇管岙村1-92号','台州市',121.25998355,28.78789657),
(965150,'临海市沿江镇水洋大道49号','台州市',121.24849270,28.74755964),
(965151,'临海市沿江镇西岑村4-291A','台州市',121.30993131,28.73750480),
(965152,'临海市沿江镇下岙村83号','台州市',121.30750795,28.70469465);
INSERT INTO dept_address (dept_id,address,city,lng,lat) VALUES
(965153,'临海市沿江镇长甸三村49号','台州市',121.28051118,28.74876826),
(965160,'河头镇人民路82号','台州市',121.10915626,28.99917355),
(965161,'河头镇兰桥村26-1号','台州市',121.14503737,29.01422584),
(965170,'临海市括苍镇塍园路28号','台州市',120.99303455,28.86399880),
(965171,'临海市括苍镇小海门村3-197A','台州市',120.98924397,28.87119176),
(965180,'临海市永丰镇留贤村1-188号','台州市',121.07890061,28.89838696),
(965182,'临海市永丰镇赤缪一村赤缪街115号','台州市',121.07668503,28.89874271),
(965183,'临海市永丰镇更楼村3-68号','台州市',121.04637306,28.88508833),
(965190,'浙江省临海市白水洋镇黄沙大道81号','台州市',120.91519961,28.90253586),
(965191,'浙江省临海市白水洋镇永安路170号','台州市',120.90808171,28.90108097);
INSERT INTO dept_address (dept_id,address,city,lng,lat) VALUES
(965192,'浙江省临海市白水洋镇中和路117号','台州市',120.96164309,28.95953814),
(965193,'浙江省临海市白水洋镇店前村12E','台州市',120.94016855,28.95268686),
(965194,'浙江省临海市白水洋镇黄坦村','台州市',120.91435125,28.90211277),
(965850,'临海市汇溪镇两头门村甬临路3号','台州市',121.22307505,28.95837869),
(965870,'临海市古城街道鹿城路170号','台州市',121.13738389,28.84895560),
(965871,'临海市古城街道赤城路50-20号','台州市',121.12452133,28.85063894),
(965872,'临海市古城街道巾山西路59号','台州市',121.12246636,28.84882874),
(965880,'临海市大洋街道大洋西路309号','台州市',121.15621300,28.86242371),
(965881,'临海市大洋街道东方大道120号','台州市',121.20797193,28.91396531),
(965890,'临海市杜桥镇府前街372号','台州市',121.50395605,28.76635382);
INSERT INTO dept_address (dept_id,address,city,lng,lat) VALUES
(965891,'临海市杜桥镇解放街269号','台州市',121.50254679,28.76962042),
(965892,'临海市杜桥镇三房村2-145号','台州市',121.56718993,28.75758802),
(965893,'临海市杜桥镇溪口村2-105号','台州市',121.42106787,28.78712796);
ALTER TABLE visit_trajectory_965 ADD head_id BIGINT NULL;
ALTER TABLE visit_trajectory_965 ADD branch_id BIGINT NULL;
ALTER TABLE visit_trajectory_965 ADD outlet_id BIGINT NULL;
ALTER TABLE visit_trajectory_965 ADD user_name VARCHAR(50) NULL;
--szq
ALTER TABLE ibs.grid_shape_count_lingshou_965 ADD zf_365cnt varchar(100) NULL COMMENT '近365天已走访人数';
ALTER TABLE ibs.grid_shape_count_lingshou_965 ADD zf_180cnt varchar(100) NULL COMMENT '近180天已走访人数';
ALTER TABLE ibs.grid_shape_count_lingshou_965 ADD zf_90cnt varchar(100) NULL COMMENT '近90天已走访人数';
ALTER TABLE ibs.grid_shape_count_lingshou_965 ADD zf_30cnt varchar(100) NULL COMMENT '近30天已走访人数';
ALTER TABLE ibs.grid_shape_count_lingshou_965 ADD zf_365rt varchar(100) NULL COMMENT '近365天走访率';
ALTER TABLE ibs.grid_shape_count_lingshou_965 ADD zf_180rt varchar(100) NULL COMMENT '近180天走访率';
ALTER TABLE ibs.grid_shape_count_lingshou_965 ADD zf_90rt varchar(100) NULL COMMENT '近90天走访率';
ALTER TABLE ibs.grid_shape_count_lingshou_965 ADD zf_30rt varchar(100) NULL COMMENT '近30天走访率';
ALTER TABLE ibs.grid_shape_cust_lingshou_965 ADD is_365zf varchar(100) NULL COMMENT '近365天有无走访';
ALTER TABLE ibs.grid_shape_cust_lingshou_965 ADD is_180zf varchar(100) NULL COMMENT '近180天有无走访';
ALTER TABLE ibs.grid_shape_cust_lingshou_965 ADD is_90zf varchar(100) NULL COMMENT '近90天有无走访';
ALTER TABLE ibs.grid_shape_cust_lingshou_965 ADD is_30zf varchar(100) NULL COMMENT '近30天有无走访';

Binary file not shown.

33
loan-rate-pricing/pom.xml Normal file
View File

@@ -0,0 +1,33 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi</artifactId>
<version>3.8.8</version>
</parent>
<artifactId>loan-rate-pricing</artifactId>
<properties>
<maven.compiler.source>8</maven.compiler.source>
<maven.compiler.target>8</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
<dependencies>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot</artifactId>
</dependency>
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-common</artifactId>
</dependency>
</dependencies>
</project>

View File

@@ -0,0 +1,57 @@
package com.ruoyi.loanratepricing.controller;
import com.ruoyi.common.annotation.Anonymous;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.R;
import com.ruoyi.loanratepricing.domain.dto.FinalRateAdjustDTO;
import com.ruoyi.loanratepricing.domain.dto.FinalRateSubmitDTO;
import com.ruoyi.loanratepricing.domain.dto.OptInvokeDTO;
import com.ruoyi.loanratepricing.domain.entity.LoanPricingApply;
import com.ruoyi.loanratepricing.domain.vo.FinalRateAdjustVO;
import com.ruoyi.loanratepricing.service.RatePricingService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import javax.annotation.Resource;
/**
* @Author 吴凯程
* @Date 2025/11/10
**/
@Api(tags = "莲都利率测算")
@RestController
@RequestMapping("/rate/pricing")
public class LoanRatePricingController extends BaseController {
@Resource
private RatePricingService ratePricingService;
@ApiOperation("发起利率定价申请,或加载利率定价申请")
@Anonymous
@PostMapping("/load")
public R<LoanPricingApply> loadRatePricingApply(@RequestBody OptInvokeDTO optInvokeDTO) {
return R.ok(ratePricingService.loadRatePricingApply(optInvokeDTO));
}
@Anonymous
@ApiOperation("测算最终利率")
@PostMapping("/invoke")
public R<FinalRateAdjustVO> invokeFinalRate(@RequestBody FinalRateAdjustDTO finalRateAdjustDTO) {
return R.ok(ratePricingService.invokeFinalRate(finalRateAdjustDTO));
}
@Anonymous
@ApiOperation("提交利率定价申请")
@PostMapping("/submit")
public R<String> submitFinalRate(@RequestBody FinalRateSubmitDTO finalRateSubmitDTO) {
return R.ok(ratePricingService.submitFinalRate(finalRateSubmitDTO));
}
}

View File

@@ -0,0 +1,101 @@
package com.ruoyi.loanratepricing.controller;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.node.ObjectNode;
import com.ruoyi.common.annotation.Anonymous;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.loanratepricing.domain.entity.LoanPricingApply;
import com.ruoyi.loanratepricing.service.ModelService;
import com.ruoyi.loanratepricing.service.OptService;
import com.ruoyi.loanratepricing.service.RatePricingService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.core.io.ClassPathResource;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import java.io.InputStream;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
/**
* @Author 吴凯程
* @Date 2025/11/10
**/
@Api(tags = "莲都利率测算测试接口")
@RestController
@RequestMapping("/rate/pricing/mock")
public class LoanRatePricingMockController extends BaseController {
@Resource
private RatePricingService ratePricingService;
@Resource
private OptService optService;
@Resource
private ModelService modelService;
@ApiOperation("发起利率定价流程")
@Anonymous
@PostMapping("/submit/application")
public AjaxResult submitApplication() {
ObjectMapper objectMapper = new ObjectMapper();
ObjectNode objectNode = objectMapper.createObjectNode();
LocalDateTime now = LocalDateTime.now();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyyMMddHHmmss");
String formattedDateTime = now.format(formatter);
objectNode.put("applicationId", Long.parseLong(formattedDateTime));
objectNode.put("midEntEleDdc", "0");
objectNode.put("midEntWaterDdc", "0");
objectNode.put("midPerEleDdc", "1");
objectNode.put("midPerQuickPay", "1");
return new AjaxResult(0, "success", objectNode);
}
@Anonymous
@ApiOperation("提交利率测算结果")
@PostMapping("/submit/result")
public AjaxResult submitRatePricingResult(@RequestBody LoanPricingApply loanPricingApply) {
return new AjaxResult(0, "success", null);
}
@Anonymous
@ApiOperation("查询议价池")
@GetMapping("/pool/balance")
public AjaxResult queryPoolBalance(@RequestParam String ownerId) {
ObjectNode jsonNodes = loadJsonFromResource("data/pool_balance.json");
return new AjaxResult(0, "success", jsonNodes);
}
@Anonymous
@ApiOperation("查询利率测算记录")
@GetMapping("/application")
public AjaxResult queryApplication(@RequestParam Long id) {
LoanPricingApply loanPricingApply = ratePricingService.queryLoanPricingApplyFromRedis(id);
return new AjaxResult(0, "success", loanPricingApply);
}
@Anonymous
@ApiOperation("调用模型获取测算利率")
@PostMapping("/invokeModel")
public AjaxResult invokeModel() {
ObjectNode jsonNodes = loadJsonFromResource("data/model_output.json");
return new AjaxResult(10000, "success", jsonNodes);
}
private ObjectNode loadJsonFromResource(String resourcePath){
ClassPathResource classPathResource = new ClassPathResource(resourcePath);
try (InputStream inputStream = classPathResource.getInputStream();){
ObjectMapper objectMapper = new ObjectMapper();
return objectMapper.readValue(inputStream, ObjectNode.class);
} catch (Exception e) {
throw new RuntimeException(e);
}
}
}

View File

@@ -0,0 +1,76 @@
package com.ruoyi.loanratepricing.controller;
import com.alibaba.fastjson2.JSONObject;
import com.ruoyi.common.annotation.Anonymous;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.R;
import com.ruoyi.loanratepricing.domain.dto.ModelInvokeDTO;
import com.ruoyi.loanratepricing.domain.dto.OptInvokeDTO;
import com.ruoyi.loanratepricing.domain.entity.LoanPricingApply;
import com.ruoyi.loanratepricing.domain.entity.ModelOutputFields;
import com.ruoyi.loanratepricing.domain.vo.OptPoolBalance;
import com.ruoyi.loanratepricing.service.ModelService;
import com.ruoyi.loanratepricing.service.OptService;
import com.ruoyi.loanratepricing.service.RatePricingService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
/**
* @Author 吴凯程
* @Date 2025/11/10
**/
@Api(tags = "莲都利率测算接口测试")
@RestController
@RequestMapping("/rate/pricing/opt")
public class LoanRatePricingTestController extends BaseController {
@Resource
private RatePricingService ratePricingService;
@Resource
private OptService optService;
@Resource
private ModelService modelService;
@ApiOperation("发起利率定价流程")
@Anonymous
@PostMapping("/submit/application")
public R<JSONObject> submitApplication(@RequestBody OptInvokeDTO optInvokeDTO) {
return R.ok(optService.submitApplication(optInvokeDTO));
}
@Anonymous
@ApiOperation("提交利率测算结果")
@PostMapping("/submit/result")
public R<String> submitRatePricingResult(@RequestBody LoanPricingApply loanPricingApply) {
return R.ok(optService.submitRatePricingResult(loanPricingApply));
}
@Anonymous
@ApiOperation("查询议价池")
@GetMapping("/pool/balance")
public R<OptPoolBalance> queryPoolBalance(@RequestParam String userCode) {
return R.ok(optService.queryPoolBalance(userCode));
}
@Anonymous
@ApiOperation("查询利率测算记录")
@GetMapping("/application")
public R<LoanPricingApply> queryApplication(@RequestParam String id) {
return R.ok(optService.queryLoanPricingApply(id));
}
@Anonymous
@ApiOperation("调用模型获取测算利率")
@PostMapping("/invokeModel")
public R<ModelOutputFields> invokeModel(@RequestBody ModelInvokeDTO modelInvokeDTO) {
return R.ok(modelService.invokeModel(modelInvokeDTO));
}
}

View File

@@ -0,0 +1,27 @@
package com.ruoyi.loanratepricing.domain;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Configuration;
/**
* @Author 吴凯程
* @Date 2025/12/23
**/
@Data
@Configuration
@ConfigurationProperties(prefix = "rate-pricing")
public class RatePricingProperties {
private String oaUrl;
private String modelUrl;
private String applicationSubmitUrl;
private String pricingResultUrl;
private String poolBalanceUrl;
private String getApplicationUrl;
}

View File

@@ -0,0 +1,20 @@
package com.ruoyi.loanratepricing.domain.dto;
import lombok.Data;
import java.math.BigDecimal;
/**
* @Author 吴凯程
* @Date 2025/12/24
**/
@Data
public class FinalRateAdjustDTO {
private String applicationId;
private BigDecimal finalRate;
}

View File

@@ -0,0 +1,28 @@
package com.ruoyi.loanratepricing.domain.dto;
import lombok.Data;
/**
* @Author 吴凯程
* @Date 2025/12/24
**/
@Data
public class FinalRateSubmitDTO {
private String applicationId;
private String finalRate;
private String branchUsage;
private String outletUsage;
private String managerUsage;
private String profitAmt;
// 审批状态
private String approvalStatus; // 审批状态 0不需要审批 1需要审批
private String approvalLevel; // 审批层级 0不需要审批 1网点 2支行
}

View File

@@ -0,0 +1,135 @@
package com.ruoyi.loanratepricing.domain.dto;
import lombok.Data;
import java.math.BigDecimal;
/**
* 贷款定价申请信息实体类
* 包含申请信息、定价结果、客户信息、各类BP因子等
*/
@Data
public class LoanPricingApplySubmitDTO {
// 申请基本信息
private Long applicationId; // 申请编号
private String orgCode; // 申请机构代码
private String orgName; // 申请机构名称
private String applyUserCode; // 申请人ID
private String applyUserName; // 申请人姓名
// 定价结果
private String baseLoanRate; // 基础利率
private String finalRate; // 最终利率
private String minRateBranch; // 支行最低利率
private String minRateProduct; // 最低利率
private String calculateRate; // 测算利率
private String totalBp; // 浮动BP合计
// 客户基础信息
private String custType; // 客户类型(个人/企业)
private String custIsn; // 客户内码
private String custName; // 客户名称
private String idType; // 证件类型
private String idNo; // 证件号
private String guarType;
private String loanType;
private String loanRate;
// 忠诚度因子BP
private String isKeyClient; // 个人核心用户
private String isFirstLoan; // 我行首贷客户
private String faithDay; // 用信天数
private String custAge; // 客户年龄
private String bpFirstLoan; // BP_首贷
private String bpAgeLoan; // BP_贷龄
private String bpAge; // BP_年龄
private String totalBpLoyalty; // TOTAL_BP_忠诚度
// 贡献度因子BP - 存款相关
private String perAvg; // 借款个人年日均
private String perSp; // 借款个人特殊类存款
private String perFmyAvg; // 配偶_子女年日均
private String perFmySp; // 配偶_子女特殊类存款
private String perEntAvg; // 个人对应企业年日均
private String perEntSp; // 个人对应企业特殊类存款
private String entAvg; // 企业年日均
private String entSp; // 企业特殊类存款
private String entPerAvg; // 企业法人年日均
private String entPerSp; // 企业法人特殊类存款
private String entPerFmyAvg; // 企业法人配偶年日均
private String entPerFmySp; // 企业法人配偶特殊类存款
private String entFinAvg; // 企业财务年日均
private String entFinSp; // 企业财务特殊类存款
private String balanceAvg; // 存款年日均合计
private String loanAvg; // 贷款年日均
private String derivationRate; // 派生率
private String totalBpContribution; // TOTAL_BP_贡献度
// 贡献度因子BP - 中间业务
private String midPerCard; // 中间业务_个人_信用卡
private String midPerPass; // 中间业务_个人_一码通
private String midPerHarvest; // 中间业务_个人_丰收互联
private String midPerEffect; // 中间业务_个人_有效客户
private String midPerQuickPay; // 中间业务_个人_快捷支付
private String midPerEleDdc; // 中间业务_个人_电费代扣
private String midPerCitizencard; // 中间业务_个人_市民卡
private String midEntConnect; // 中间业务_企业_企业互联
private String midEntEffect; // 中间业务_企业_有效价值客户
private String midEntPublicFund; // 中间业务_企业_职工缴纳公积金
private String midEntEleDdc; // 中间业务_企业_电费代扣
private String midEntWaterDdc; // 中间业务_企业_水费代扣
private String midEntTax; // 中间业务_企业_税务代扣
private String bpMid; // BP_中间业务
// 关联度因子BP
private String payroll; // 代发工资户数
private String invLoanAmount; // 存量贷款余额
private String bpPayroll; // BP_代发工资
// 企业客户关联度
private String isCleanEnt; // 净身企业
private String hasSettleAcct; // 开立基本结算账户
private String isManufacturing; // 制造业企业
private String isAgriGuar; // 省农担担保贷款
private String isTaxA; // 是否纳税信用等级A级
private String isAgriLeading; // 是否县级及以上农业龙头企业
private String isInclusiveFinance;
private String bpEntType; // BP_企业客户类别
private String totalBpRelevance; // TOTAL_BP_关联度
// 贷款用途因子BP
private String applyAmt; // 申请金额(元)
private String bpLoanAmount; // BP_贷款额度
private String loanPurpose; // 贷款用途
private String bizProof; // 是否有经营佐证
private String bpLoanUse; // BP_贷款用途
// 抵押物质押因子BP
private String collType; // 抵质押类型
private String collThirdParty; // 抵质押物是否三方所有
private String bpCollateral; // BP_抵押物
// 风险度因子BP
private String greyCust; // 灰名单客户
private String prinOverdue; // 本金逾期
private String interestOverdue; // 利息逾期
private String cardOverdue; // 信用卡逾期
private String bpGreyOverdue; // BP_灰名单与逾期
private String totalBpRisk; // TOTAL_BP_风险度
// 审批状态
private String approvalStatus; // 审批状态
private String approvalLevel; // 审批层级
private BigDecimal branchBalance;
private BigDecimal outletBalance;
private BigDecimal managerBalance;
private BigDecimal branchUsage;
private BigDecimal outletUsage;
private BigDecimal managerUsage;
private BigDecimal profitAmt;
}

View File

@@ -0,0 +1,153 @@
package com.ruoyi.loanratepricing.domain.dto;
import lombok.Data;
/**
* @Author 吴凯程
* @Date 2025/12/23
**/
@Data
public class ModelInvokeDTO {
/**
* 业务方流水号(必填)
* 可使用时间戳,或自定义随机生成
*/
private String serialNum;
/**
* 机构编码(必填)
* 固定值931000
*/
private String orgCode;
/**
* 运行模式(必填)
* 固定值1:同步
*/
private String runType = "1";
/**
* 客户内码(必填)
*/
private String custIsn;
/**
* 客户类型(必填)
* 可选值:个人/企业
*/
private String custType;
/**
* 担保方式(必填)
* 可选值:信用,保证,抵押,质押
*/
private String guarType;
/**
* 中间业务_个人_快捷支付非必填
* 可选值true/false
*/
private String midPerQuickPay;
/**
* 中间业务_个人_电费代扣非必填
* 可选值true/false
*/
private String midPerEleDdc;
/**
* 中间业务_企业_电费代扣非必填
* 可选值true/false
*/
private String midEntEleDdc;
/**
* 中间业务_企业_水费代扣非必填
* 可选值true/false
*/
private String midEntWaterDdc;
/**
* 申请金额(必填)
* 单位:元
*/
private String applyAmt;
/**
* 净身企业(非必填)
* 可选值true/false
*/
private String isCleanEnt;
/**
* 开立基本结算账户(非必填)
* 可选值true/false
*/
private String hasSettleAcct;
/**
* 制造业企业(非必填)
* 可选值true/false
*/
private String isManufacturing;
/**
* 省农担担保贷款(非必填)
* 可选值true/false
*/
private String isAgriGuar;
/**
* 是否纳税信用等级A级非必填
* 可选值true/false
*/
private String isTaxA;
/**
* 是否县级及以上农业龙头企业(非必填)
* 可选值true/false
*/
private String isAgriLeading;
private String isInclusiveFinance;
/**
* 贷款用途(非必填)
* 可选值consumer/business
*/
private String loanPurpose;
/**
* 是否有经营佐证(非必填)
* 可选值true/false
*/
private String bizProof;
/**
* 抵质押类型(非必填)
* 可选值:抵押/质押
*/
private String collType;
/**
* 抵质押物是否三方所有(非必填)
* 可选值true/false
*/
private String collThirdParty;
// /**
// * 贷款利率(必填)
// */
// private String loanRate;
/**
* 客户名称(非必填)
*/
private String custName;
/**
* 证件类型(非必填)
*/
private String idType;
}

View File

@@ -0,0 +1,163 @@
package com.ruoyi.loanratepricing.domain.dto;
import lombok.Data;
/**
* @Author 吴凯程
* @Date 2025/12/23
**/
@Data
public class OptInvokeDTO {
private String applicationId;
/**
* 客户类型(个人/企业)
*/
private String custType;
/**
* 客户内码
*/
private String custIsn;
/**
* 客户名称
*/
private String custName;
/**
* 证件类型
*/
private String idType;
/**
* 证件号
*/
private String idNo;
/**
* 申请金额
*/
private String applyAmt;
/**
* 担保方式
*/
private String guarType;
/**
* 抵质押类型
*/
private String collType;
/**
* 抵质押物是否三方所有 0-否,1-是
*/
private String collThirdParty;
/**
* 贷款用途
*/
private String loanPurpose;
private String loanRate;
/**
* 是否有经营佐证 0-否,1-是
*/
private String bizProof;
/**
* 贷款产品ID
*/
private String loanProdId;
/**
* 贷款产品
*/
private String loanProd;
/**
* 当日办理业务
*/
private String todayBiz;
/**
* 是否净身企业 0-否,1-是
*/
private String isCleanEnt;
/**
* 是否制造业企业 0-否,1-是
*/
private String isManufacturing;
/**
* 是否省农担担保贷款 0-否,1-是
*/
private String isAgriGuar;
private String isInclusiveFinance;
/**
* 是否纳税信用等级A级 0-否,1-是
*/
private String isTaxA;
/**
* 是否县级及以上农业龙头企业 0-否,1-是
*/
private String isAgriLeading;
/**
* 中间业务_个人_快捷支付非必填
* 可选值true/false
*/
private String midPerQuickPay;
/**
* 中间业务_个人_电费代扣非必填
* 可选值true/false
*/
private String midPerEleDdc;
/**
* 中间业务_企业_电费代扣非必填
* 可选值true/false
*/
private String midEntEleDdc;
/**
* 中间业务_企业_水费代扣非必填
* 可选值true/false
*/
private String midEntWaterDdc;
/**
* 申请机构ID
*/
private String orgCode;
/**
* 申请机构名称
*/
private String orgName;
/**
* 申请人ID
*/
private String applyUserCode;
/**
* 申请人姓名
*/
private String applyUserName;
/**
* 是否开立基本结算账户 0-否,1-是
*/
private String hasSettleAcct;
}

View File

@@ -0,0 +1,135 @@
package com.ruoyi.loanratepricing.domain.entity;
import lombok.Data;
import java.math.BigDecimal;
/**
* 贷款定价申请信息实体类
* 包含申请信息、定价结果、客户信息、各类BP因子等
*/
@Data
public class LoanPricingApply {
// 申请基本信息
private String applicationId; // 申请编号
private String orgCode; // 申请机构代码
private String orgName; // 申请机构名称
private String applyUserCode; // 申请人ID
private String applyUserName; // 申请人姓名
// 定价结果
private String baseLoanRate; // 基础利率
private String finalRate; // 最终利率
private String minRateBranch; // 支行最低利率
private String minRateProduct; // 最低利率
private String calculateRate; // 测算利率
private String totalBp; // 浮动BP合计
// 客户基础信息
private String custType; // 客户类型(个人/企业)
private String custIsn; // 客户内码
private String custName; // 客户名称
private String idType; // 证件类型
private String idNo; // 证件号
private String guarType;
private String loanType;
private String loanRate;
// 忠诚度因子BP
private String isKeyClient; // 个人核心用户
private String isFirstLoan; // 我行首贷客户
private String faithDay; // 用信天数
private String custAge; // 客户年龄
private String bpFirstLoan; // BP_首贷
private String bpAgeLoan; // BP_贷龄
private String bpAge; // BP_年龄
private String totalBpLoyalty; // TOTAL_BP_忠诚度
// 贡献度因子BP - 存款相关
private String perAvg; // 借款个人年日均
private String perSp; // 借款个人特殊类存款
private String perFmyAvg; // 配偶_子女年日均
private String perFmySp; // 配偶_子女特殊类存款
private String perEntAvg; // 个人对应企业年日均
private String perEntSp; // 个人对应企业特殊类存款
private String entAvg; // 企业年日均
private String entSp; // 企业特殊类存款
private String entPerAvg; // 企业法人年日均
private String entPerSp; // 企业法人特殊类存款
private String entPerFmyAvg; // 企业法人配偶年日均
private String entPerFmySp; // 企业法人配偶特殊类存款
private String entFinAvg; // 企业财务年日均
private String entFinSp; // 企业财务特殊类存款
private String balanceAvg; // 存款年日均合计
private String loanAvg; // 贷款年日均
private String derivationRate; // 派生率
private String totalBpContribution; // TOTAL_BP_贡献度
// 贡献度因子BP - 中间业务
private String midPerCard; // 中间业务_个人_信用卡
private String midPerPass; // 中间业务_个人_一码通
private String midPerHarvest; // 中间业务_个人_丰收互联
private String midPerEffect; // 中间业务_个人_有效客户
private String midPerQuickPay; // 中间业务_个人_快捷支付
private String midPerEleDdc; // 中间业务_个人_电费代扣
private String midPerCitizencard; // 中间业务_个人_市民卡
private String midEntConnect; // 中间业务_企业_企业互联
private String midEntEffect; // 中间业务_企业_有效价值客户
private String midEntPublicFund; // 中间业务_企业_职工缴纳公积金
private String midEntEleDdc; // 中间业务_企业_电费代扣
private String midEntWaterDdc; // 中间业务_企业_水费代扣
private String midEntTax; // 中间业务_企业_税务代扣
private String bpMid; // BP_中间业务
// 关联度因子BP
private String payroll; // 代发工资户数
private String invLoanAmount; // 存量贷款余额
private String bpPayroll; // BP_代发工资
// 企业客户关联度
private String isCleanEnt; // 净身企业
private String hasSettleAcct; // 开立基本结算账户
private String isManufacturing; // 制造业企业
private String isAgriGuar; // 省农担担保贷款
private String isTaxA; // 是否纳税信用等级A级
private String isAgriLeading; // 是否县级及以上农业龙头企业
private String isInclusiveFinance;
private String bpEntType; // BP_企业客户类别
private String totalBpRelevance; // TOTAL_BP_关联度
// 贷款用途因子BP
private String applyAmt; // 申请金额(元)
private String bpLoanAmount; // BP_贷款额度
private String loanPurpose; // 贷款用途
private String bizProof; // 是否有经营佐证
private String bpLoanUse; // BP_贷款用途
// 抵押物质押因子BP
private String collType; // 抵质押类型
private String collThirdParty; // 抵质押物是否三方所有
private String bpCollateral; // BP_抵押物
// 风险度因子BP
private String greyCust; // 灰名单客户
private String prinOverdue; // 本金逾期
private String interestOverdue; // 利息逾期
private String cardOverdue; // 信用卡逾期
private String bpGreyOverdue; // BP_灰名单与逾期
private String totalBpRisk; // TOTAL_BP_风险度
// 审批状态
private String approvalStatus; // 审批状态
private String approvalLevel; // 审批层级
private BigDecimal branchBalance;
private BigDecimal outletBalance;
private BigDecimal managerBalance;
private BigDecimal branchUsage;
private BigDecimal outletUsage;
private BigDecimal managerUsage;
private BigDecimal profitAmt;
}

View File

@@ -0,0 +1,186 @@
package com.ruoyi.loanratepricing.domain.entity;
import lombok.Data;
/**
* @Author 吴凯程
* @Date 2025/12/24
**/
@Data
public class ModelOutputFields {
// 基础贷款信息
/** 贷款合同号 */
private String loanContractId;
/** 客户内码 */
private String custIsn;
/** 客户类型 */
private String custType;
/** 客户年龄 */
private String custAge;
/** 贷款金额 */
private String loanAmount;
/** 贷款利率 */
private String loanRate;
/** 贷款日期 */
private String loanDate;
/** 贷款类型 */
private String loanType;
/** 贷款用途 */
private String loanPurpose;
// 客户属性
/** 个人核心用户 */
private String isKeyClient;
/** 我行首贷客户 */
private String isFirstLoan;
/** 用信天数 */
private String faithDay;
// BP相关指标
/** BP_首贷 */
private String bpFirstLoan;
/** BP_贷龄 */
private String bpAgeLoan;
/** BP_年龄 */
private String bpAge;
/** TOTAL_BP_忠诚度 */
private String totalBpLoyalty;
// 存款相关指标
/** 借款个人年日均 */
private String perAvg;
/** 借款个人特殊类存款 */
private String perSp;
/** 配偶_子女年日均 */
private String perFmyAvg;
/** 配偶_子女特殊类存款 */
private String perFmySp;
/** 个人对应企业年日均 */
private String perEntAvg;
/** 个人对应企业特殊类存款 */
private String perEntSp;
/** 企业年日均 */
private String entAvg;
/** 企业特殊类存款 */
private String entSp;
/** 企业法人年日均 */
private String entPerAvg;
/** 企业法人特殊类存款 */
private String entPerSp;
/** 企业法人配偶年日均 */
private String entPerFmyAvg;
/** 企业法人配偶特殊类存款 */
private String entPerFmySp;
/** 企业财务年日均 */
private String entFinAvg;
/** 企业财务特殊类存款 */
private String entFinSp;
/** 存款年日均 */
private String balanceAvg;
/** 贷款年日均 */
private String loanAvg;
/** 派生率 */
private String derivationRate;
// 贡献度相关
/** TOTAL_BP_贡献度 */
private String totalBpContribution;
// 中间业务相关
/** 中间业务_个人_信用卡 */
private String midPerCard;
/** 中间业务_个人_一码通 */
private String midPerPass;
/** 中间业务_个人_丰收互联 */
private String midPerHarvest;
/** 中间业务_个人_有效客户 */
private String midPerEffect;
/** 中间业务_个人_快捷支付 */
private String midPerQuickPay;
/** 中间业务_个人_电费代扣 */
private String midPerEleDdc;
/** 中间业务_个人_市民卡 */
private String midPerCitizencard;
/** 中间业务_企业_企业互联 */
private String midEntConnect;
/** 中间业务_企业_有效价值客户 */
private String midEntEffect;
/** 中间业务_企业_职工缴纳公积金 */
private String midEntPublicFund;
/** 中间业务_企业_电费代扣 */
private String midEntEleDdc;
/** 中间业务_企业_水费代扣 */
private String midEntWaterDdc;
/** 中间业务_企业_税务代扣 */
private String midEntTax;
/** BP_中间业务 */
private String bpMid;
// 代发工资相关
/** 代发工资户数 */
private String payroll;
/** BP_代发工资 */
private String bpPayroll;
// 企业属性相关
/** 净身企业 */
private String isCleanEnt;
/** 开立基本结算账户 */
private String hasSettleAcct;
/** 制造业企业 */
private String isManufacturing;
/** 省农担担保贷款 */
private String isAgriGuar;
/** 纳税信用等级 */
private String isTaxA;
/** 县级(含)以上农业龙头企业和示范性专业合作社 */
private String isAgriLeading;
/** BP_企业客户类别 */
private String bpEntType;
// 关联度相关
/** TOTAL_BP_关联度 */
private String totalBpRelevance;
// 风控相关
/** 经营佐证 */
private String bizProof;
/** 抵质押物类型 */
private String collType;
/** 灰名单客户 */
private String greyCust;
/** 本金逾期 */
private String prinOverdue;
/** 利息逾期 */
private String interestOverdue;
/** 信用卡逾期 */
private String cardOverdue;
/** BP_贷款额度 */
private String bpLoanAmount;
/** BP_贷款用途 */
private String bpLoanUse;
/** BP_抵押物 */
private String bpCollateral;
/** BP_灰名单与逾期 */
private String bpGreyOverdue;
/** TOTAL_BP_风险度 */
private String totalBpRisk;
/** TOTAL_BP */
private String totalBp;
/** 抵质押物是否三方所有 */
private String collThirdParty;
/** 担保方式 */
private String guarType;
/** 存量贷款余额 */
private String invLoanAmount;
/** 测算利率 */
private String calculateRate;
private String baseLoanRate; // 基础利率
private String minRateBranch; // 支行最低利率
private String minRateProduct; // 最低利率
}

View File

@@ -0,0 +1,32 @@
package com.ruoyi.loanratepricing.domain.vo;
import lombok.Data;
import java.math.BigDecimal;
/**
* @Author 吴凯程
* @Date 2025/12/24
**/
@Data
public class FinalRateAdjustVO {
private String applicationId;
private BigDecimal branchBalance;
private BigDecimal outletBalance;
private BigDecimal managerBalance;
private BigDecimal branchUsage;
private BigDecimal outletUsage;
private BigDecimal managerUsage;
private BigDecimal profitAmt;
// 审批状态
private String approvalStatus; // 审批状态 0不需要审批 1需要审批
private String approvalLevel; // 审批层级 0不需要审批 1网点 2支行
}

View File

@@ -0,0 +1,20 @@
package com.ruoyi.loanratepricing.domain.vo;
import lombok.Data;
import java.math.BigDecimal;
/**
* @Author 吴凯程
* @Date 2025/12/24
**/
@Data
public class OptPoolBalance {
private BigDecimal branchBalance;
private BigDecimal outletBalance;
private BigDecimal managerBalance;
}

View File

@@ -0,0 +1,79 @@
package com.ruoyi.loanratepricing.service;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.alibaba.fastjson2.TypeReference;
import com.ruoyi.common.core.domain.entity.SysDictData;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.http.HttpUtils;
import com.ruoyi.loanratepricing.domain.RatePricingProperties;
import com.ruoyi.loanratepricing.domain.dto.ModelInvokeDTO;
import com.ruoyi.loanratepricing.domain.entity.ModelOutputFields;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.util.List;
import java.util.Map;
import java.util.Objects;
/**
* @Author 吴凯程
* @Date 2025/12/11
**/
@Service
@Slf4j
public class ModelService {
@Resource
private RatePricingProperties ratePricingProperties;
@Resource
private RedisCache redisCache;
public ModelOutputFields invokeModel(ModelInvokeDTO modelInvokeDTO) {
Map<String, String> requestBody = entityToMap(modelInvokeDTO);
JSONObject response = HttpUtils.doPostFormUrlEncoded(ratePricingProperties.getModelUrl(), requestBody, null, JSONObject.class);
log.info("------------------->调用模型返回结果:" + JSON.toJSONString(response));
if(Objects.nonNull(response) && response.containsKey("code") && response.getInteger("code") == 10000){
JSONObject mappingOutputFields = response.getJSONObject("data").getJSONObject("mappingOutputFields");
return JSON.parseObject(mappingOutputFields.toJSONString(), ModelOutputFields.class);
}else{
log.error("------------------->调用模型失败,失败原因为:" + response.getString("message"));
throw new ServiceException("调用模型失败");
}
}
/**
* 使用FastJSON将实体类转换为Map<String, String>
* @param obj 待转换的实体类对象
* @return 转换后的Map
*/
public static Map<String, String> entityToMap(Object obj) {
if (obj == null) {
return null;
}
// 先转为JSON字符串再转换为指定类型的Map
String jsonStr = JSON.toJSONString(obj);
return JSON.parseObject(jsonStr, new TypeReference<Map<String, String>>() {});
}
private void replaceIndicatorToVariableName(JSONObject jsonObject) {
List<SysDictData> variableNameList = redisCache.getCacheObject("sys_dict:model_indicator_metric");
variableNameList.forEach(sysDictData -> {
if (jsonObject.containsKey(sysDictData.getDictLabel())) {
jsonObject.put(sysDictData.getDictValue(), jsonObject.get(sysDictData.getDictLabel()));
jsonObject.remove(sysDictData.getDictLabel());
}
});
}
}

View File

@@ -0,0 +1,149 @@
package com.ruoyi.loanratepricing.service;
import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.bean.BeanUtils;
import com.ruoyi.common.utils.http.HttpUtils;
import com.ruoyi.loanratepricing.domain.RatePricingProperties;
import com.ruoyi.loanratepricing.domain.dto.LoanPricingApplySubmitDTO;
import com.ruoyi.loanratepricing.domain.dto.OptInvokeDTO;
import com.ruoyi.loanratepricing.domain.entity.LoanPricingApply;
import com.ruoyi.loanratepricing.domain.vo.OptPoolBalance;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.math.BigDecimal;
import java.util.Calendar;
import java.util.HashMap;
import java.util.Map;
import java.util.Objects;
/**
* @Author 吴凯程
* @Date 2025/12/23
**/
@Service
@Slf4j
public class OptService {
@Resource
private RatePricingProperties ratePricingProperties;
public JSONObject submitApplication(OptInvokeDTO optInvokeDTO) {
JSONObject json = (JSONObject) JSON.toJSON(optInvokeDTO);
JSONObject response = HttpUtils.doPostJson(ratePricingProperties.getOaUrl() + ratePricingProperties.getApplicationSubmitUrl(), json, null, JSONObject.class);
log.info("------------>发起利率定价申请:" + JSON.toJSONString(response));
if(Objects.nonNull(response) && response.containsKey("code") && response.getInteger("code") == 0){
return response.getJSONObject("data");
}else{
log.error("申请利率定价流程失败" + response.toJSONString());
throw new ServiceException("提交利率定价流程失败:" + response.toJSONString());
}
}
public String submitRatePricingResult(LoanPricingApply loanPricingApply) {
LoanPricingApplySubmitDTO loanPricingApplySubmitDTO = new LoanPricingApplySubmitDTO();
BeanUtils.copyProperties(loanPricingApply, loanPricingApplySubmitDTO);
loanPricingApplySubmitDTO.setApplicationId(Long.parseLong(loanPricingApply.getApplicationId()));
JSONObject json = (JSONObject) JSON.toJSON(loanPricingApplySubmitDTO);
JSONObject response = HttpUtils.doPostJson(ratePricingProperties.getOaUrl() + ratePricingProperties.getPricingResultUrl(), json, null, JSONObject.class);
log.info("------------>提交利率定价申请:" + JSON.toJSONString(response));
if(Objects.nonNull(response) && response.containsKey("code") && response.getInteger("code") == 0){
return "提交利率定价结果成功";
}else{
log.error("提交利率定价结果失败"+ response.toJSONString());
throw new ServiceException("提交利率定价结果失败"+ response.toJSONString());
}
}
public LoanPricingApply queryLoanPricingApply(String applicationId){
Map<String, String> requestParam = new HashMap<>();
requestParam.put("id", applicationId);
JSONObject response = HttpUtils.doGet(ratePricingProperties.getOaUrl() + ratePricingProperties.getGetApplicationUrl(), requestParam, null, JSONObject.class);
log.info("------------>查询利率定价申请信息:" + JSON.toJSONString(response));
if(Objects.nonNull(response) && response.containsKey("code") && response.getInteger("code") == 0){
JSONObject data = response.getJSONObject("data");
return JSON.parseObject(data.toJSONString(), LoanPricingApply.class);
}else{
log.error("查询利率定价申请信息失败"+ response.toJSONString());
throw new ServiceException("查询利率定价申请信息失败"+ response.toJSONString());
}
}
public OptPoolBalance queryPoolBalance(String userCode){
Map<String, String> requestParam = new HashMap<>();
requestParam.put("ownerId", userCode);
requestParam.put("year", getCurrentYear());
requestParam.put("quarter", getCurrentQuarter());
JSONObject response = HttpUtils.doGet(ratePricingProperties.getOaUrl() + ratePricingProperties.getPoolBalanceUrl(), requestParam, null, JSONObject.class);
log.info("------------>查询议价池:" + JSON.toJSONString(response));
if(Objects.nonNull(response) && response.containsKey("code") && response.getInteger("code") == 0){
OptPoolBalance optPoolBalance = new OptPoolBalance();
JSONObject data = response.getJSONObject("data");
if (Objects.isNull(data)){
log.error("查询议价池失败" + response.toJSONString());
return optPoolBalance;
}
if(data.containsKey("branch")){
JSONObject branch = data.getJSONObject("branch");
if(branch.containsKey("availableQuota")){
BigDecimal availableQuota = new BigDecimal(branch.getString("availableQuota"));
optPoolBalance.setBranchBalance(availableQuota);
}else{
optPoolBalance.setBranchBalance(BigDecimal.ZERO);
}
}else{
optPoolBalance.setBranchBalance(BigDecimal.ZERO);
}
if(data.containsKey("network")){
JSONObject network = data.getJSONObject("network");
if(network.containsKey("availableQuota")){
BigDecimal availableQuota = new BigDecimal(network.getString("availableQuota"));
optPoolBalance.setOutletBalance(availableQuota);
}else{
optPoolBalance.setOutletBalance(BigDecimal.ZERO);
}
}else{
optPoolBalance.setOutletBalance(BigDecimal.ZERO);
}
if(data.containsKey("manager")){
JSONObject manager = data.getJSONObject("manager");
if(manager.containsKey("availableQuota")){
BigDecimal availableQuota = new BigDecimal(manager.getString("availableQuota"));
optPoolBalance.setManagerBalance(availableQuota);
}else{
optPoolBalance.setManagerBalance(BigDecimal.ZERO);
}
}else{
optPoolBalance.setManagerBalance(BigDecimal.ZERO);
}
return optPoolBalance;
}else{
log.error("查询议价池失败" + response.toJSONString());
throw new ServiceException("查询议价池失败" + response.toJSONString());
}
}
private String getCurrentYear(){
Calendar calendar = Calendar.getInstance();
int year = calendar.get(Calendar.YEAR);
return Integer.toString(year);
}
private String getCurrentQuarter(){
Calendar calendar = Calendar.getInstance();
int quarter = (calendar.get(Calendar.MONTH) + 3) / 3;
return Integer.toString(quarter);
}
}

View File

@@ -0,0 +1,168 @@
package com.ruoyi.loanratepricing.service;
import com.alibaba.fastjson2.JSONObject;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.bean.BeanUtils;
import com.ruoyi.loanratepricing.domain.dto.FinalRateAdjustDTO;
import com.ruoyi.loanratepricing.domain.dto.FinalRateSubmitDTO;
import com.ruoyi.loanratepricing.domain.dto.ModelInvokeDTO;
import com.ruoyi.loanratepricing.domain.dto.OptInvokeDTO;
import com.ruoyi.loanratepricing.domain.entity.LoanPricingApply;
import com.ruoyi.loanratepricing.domain.entity.ModelOutputFields;
import com.ruoyi.loanratepricing.domain.vo.FinalRateAdjustVO;
import com.ruoyi.loanratepricing.domain.vo.OptPoolBalance;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.Objects;
/**
* @Author 吴凯程
* @Date 2025/12/23
**/
@Service
@Slf4j
public class RatePricingService {
@Resource
private RedisCache redisCache;
@Resource
private OptService optService;
@Resource
private ModelService modelService;
private static String APPLICATION_ID_PREFIX = "LOAN_RATE_PRICING_APPLICATION_";
/**
* 创建利率测算申请
* 1. 表单信息提交
* 2. 调用行社流程发起接口取得applicationId
* 3. 调用模型测算接口,获取大部分字段
* 4. 保存流程到redis
*
* @param optInvokeDTO
* @return
*/
public LoanPricingApply loadRatePricingApply(OptInvokeDTO optInvokeDTO){
LoanPricingApply loanPricingApply;
if (Objects.isNull(optInvokeDTO.getApplicationId())){
JSONObject response = optService.submitApplication(optInvokeDTO);
String applicationId = response.getString("applicationId");
ModelInvokeDTO modelInvokeDTO = new ModelInvokeDTO();
BeanUtils.copyProperties(optInvokeDTO, modelInvokeDTO);
modelInvokeDTO.setRunType("1");
modelInvokeDTO.setSerialNum(applicationId);
modelInvokeDTO.setMidEntEleDdc(response.getString("midEntEleDdc"));
modelInvokeDTO.setMidEntWaterDdc(response.getString("midEntWaterDdc"));
modelInvokeDTO.setMidPerEleDdc(response.getString("midPerEleDdc"));
modelInvokeDTO.setMidPerQuickPay(response.getString("midPerQuickPay"));
ModelOutputFields modelOutputFields = modelService.invokeModel(modelInvokeDTO);
loanPricingApply = new LoanPricingApply();
BeanUtils.copyProperties(optInvokeDTO, loanPricingApply);
BeanUtils.copyProperties(modelOutputFields, loanPricingApply);
log.info("--------------->applicationId:{}",applicationId);
loanPricingApply.setApplicationId(applicationId);
redisCache.setCacheObject(APPLICATION_ID_PREFIX + applicationId, loanPricingApply);
}else{
if (redisCache.hasKey(APPLICATION_ID_PREFIX + optInvokeDTO.getApplicationId())){
loanPricingApply = redisCache.getCacheObject(APPLICATION_ID_PREFIX + optInvokeDTO.getApplicationId());
log.info("--------------->通过redis查询记录:{}", loanPricingApply);
}else{
loanPricingApply = optService.queryLoanPricingApply(optInvokeDTO.getApplicationId());
}
}
OptPoolBalance optPoolBalance = optService.queryPoolBalance(loanPricingApply.getApplyUserCode());
BeanUtils.copyProperties(optPoolBalance, loanPricingApply);
log.info("--------------->获取记录:{}", loanPricingApply);
return loanPricingApply;
}
public FinalRateAdjustVO invokeFinalRate(FinalRateAdjustDTO finalRateAdjustDTO){
if (!redisCache.hasKey(APPLICATION_ID_PREFIX + finalRateAdjustDTO.getApplicationId())){
throw new ServiceException("利率定价申请信息不存在,请重新发起");
}
LoanPricingApply loanPricingApply = redisCache.getCacheObject(APPLICATION_ID_PREFIX + finalRateAdjustDTO.getApplicationId());
if (Objects.isNull(loanPricingApply.getMinRateBranch())){
throw new ServiceException("利率定价模型信息不存在,请重新发起");
}
FinalRateAdjustVO finalRateAdjustVO = new FinalRateAdjustVO();
OptPoolBalance optPoolBalance = optService.queryPoolBalance(loanPricingApply.getApplyUserCode());
BeanUtils.copyProperties(optPoolBalance, finalRateAdjustVO);
BigDecimal minRateBranch = new BigDecimal(loanPricingApply.getMinRateBranch());
if (finalRateAdjustDTO.getFinalRate().compareTo(minRateBranch) < 0){
BigDecimal interestAmt = new BigDecimal(loanPricingApply.getApplyAmt()).multiply(minRateBranch.subtract(finalRateAdjustDTO.getFinalRate()));
BigDecimal totalBalance = optPoolBalance.getBranchBalance().add(optPoolBalance.getOutletBalance()).add(optPoolBalance.getManagerBalance());
if (interestAmt.compareTo(totalBalance) > 0){
throw new ServiceException("总利息大于可用余额,无法进行定价");
}
if (optPoolBalance.getManagerBalance().compareTo(BigDecimal.ZERO) > 0 && interestAmt.compareTo(BigDecimal.ZERO) > 0){
finalRateAdjustVO.setApprovalStatus("0");
finalRateAdjustVO.setApprovalLevel("0");
BigDecimal managerUsage = interestAmt.compareTo(optPoolBalance.getManagerBalance()) > 0 ? optPoolBalance.getManagerBalance() : interestAmt;
finalRateAdjustVO.setManagerUsage(managerUsage);
interestAmt = interestAmt.subtract(managerUsage);
}
if (optPoolBalance.getOutletBalance().compareTo(BigDecimal.ZERO) > 0 && interestAmt.compareTo(BigDecimal.ZERO) > 0){
finalRateAdjustVO.setApprovalStatus("1");
finalRateAdjustVO.setApprovalLevel("1");
BigDecimal outletUsage = interestAmt.compareTo(optPoolBalance.getOutletBalance()) > 0 ? optPoolBalance.getOutletBalance() : interestAmt;
finalRateAdjustVO.setOutletUsage(outletUsage);
interestAmt = interestAmt.subtract(outletUsage);
}else{
finalRateAdjustVO.setOutletUsage(BigDecimal.ZERO);
}
if (optPoolBalance.getBranchBalance().compareTo(BigDecimal.ZERO) > 0 && interestAmt.compareTo(BigDecimal.ZERO) > 0){
finalRateAdjustVO.setApprovalStatus("1");
finalRateAdjustVO.setApprovalLevel("2");
BigDecimal branchUsage = interestAmt.compareTo(optPoolBalance.getBranchBalance()) > 0 ? optPoolBalance.getBranchBalance() : interestAmt;
finalRateAdjustVO.setBranchUsage(branchUsage);
interestAmt = interestAmt.subtract(branchUsage);
}else{
finalRateAdjustVO.setBranchUsage(BigDecimal.ZERO);
}
finalRateAdjustVO.setProfitAmt(BigDecimal.ZERO);
}else {
finalRateAdjustVO.setApprovalStatus("0");
finalRateAdjustVO.setApprovalLevel("0");
finalRateAdjustVO.setManagerUsage(BigDecimal.ZERO);
finalRateAdjustVO.setOutletUsage(BigDecimal.ZERO);
finalRateAdjustVO.setBranchUsage(BigDecimal.ZERO);
finalRateAdjustVO.setProfitAmt(new BigDecimal(loanPricingApply.getApplyAmt()).multiply(finalRateAdjustDTO.getFinalRate().subtract(minRateBranch)).divide(BigDecimal.valueOf(6), 4, RoundingMode.HALF_UP));
}
return finalRateAdjustVO;
}
public String submitFinalRate(FinalRateSubmitDTO finalRateSubmitDTO){
LoanPricingApply loanPricingApply;
if (redisCache.hasKey(APPLICATION_ID_PREFIX + finalRateSubmitDTO.getApplicationId())){
loanPricingApply = redisCache.getCacheObject(APPLICATION_ID_PREFIX + finalRateSubmitDTO.getApplicationId());
}else{
loanPricingApply = optService.queryLoanPricingApply(finalRateSubmitDTO.getApplicationId());
}
if (Objects.isNull(loanPricingApply.getMinRateBranch())){
throw new ServiceException("利率定价模型信息不存在,请重新发起");
}
BeanUtils.copyProperties(finalRateSubmitDTO, loanPricingApply);
redisCache.setCacheObject(APPLICATION_ID_PREFIX + loanPricingApply.getApplicationId(), loanPricingApply);
return optService.submitRatePricingResult(loanPricingApply);
}
public LoanPricingApply queryLoanPricingApplyFromRedis(Long applicationId){
if (redisCache.hasKey(APPLICATION_ID_PREFIX + applicationId)){
return redisCache.getCacheObject(APPLICATION_ID_PREFIX + applicationId);
}
return null;
}
}

View File

@@ -0,0 +1,94 @@
{
"traceId": "350626558347246735E7F4722CUZRWOMNRR53O0",
"cost": 2267,
"tokenId": "17364055486305E7F4722M8IPFWNL8TOBEB",
"mappingOutputFields": {
"custIsn": "C20250109001",
"custType": "企业",
"guarType": "省农担担保",
"custName": "浙江绿源农业发展有限公司",
"idType": "统一社会信用代码",
"loanRate": "4.35",
"isKeyClient": "1",
"isFirstLoan": "0",
"faithDay": "210",
"custAge": "6",
"bpFirstLoan": "12",
"bpAgeLoan": "6",
"bpAge": "4",
"totalBpLoyalty": "22",
"perAvg": "80000",
"perSp": "15000",
"perFmyAvg": "45000",
"perFmySp": "8000",
"perEntAvg": "250000",
"perEntSp": "60000",
"entAvg": "1200000",
"entSp": "250000",
"entPerAvg": "90000",
"entPerSp": "20000",
"entPerFmyAvg": "50000",
"entPerFmySp": "10000",
"entFinAvg": "70000",
"entFinSp": "15000",
"balanceAvg": "1843000",
"loanAvg": "950000",
"derivationRate": "1.94",
"totalBpContribution": "28",
"midPerCard": "1",
"midPerPass": "1",
"midPerHarvest": "1",
"midPerEffect": "0",
"midPerQuickPay": "0",
"midPerEleDdc": "0",
"midPerCitizencard": "1",
"midEntConnect": "1",
"midEntEffect": "1",
"midEntPublicFund": "0",
"midEntEleDdc": "0",
"midEntWaterDdc": "0",
"midEntTax": "1",
"bpMid": "15",
"payroll": "200",
"invLoanAmount": "6000000",
"bpPayroll": "10",
"isCleanEnt": "1",
"hasSettleAcct": "0",
"isManufacturing": "1",
"isAgriGuar": "0",
"isTaxA": "0",
"isAgriLeading": "0",
"bpEntType": "18",
"totalBpRelevance": "28",
"applyAmt": "1500000",
"bpLoanAmount": "8",
"loanPurpose": "农产品种植与加工",
"bizProof": "有",
"bpLoanUse": "10",
"collType": "农业设施抵押",
"collThirdParty": "1",
"bpCollateral": "12",
"greyCust": "1",
"prinOverdue": "无",
"interestOverdue": "无",
"cardOverdue": "无",
"bpGreyOverdue": "0",
"totalBpRisk": "0",
"totalBp": "50",
"calculateRate": "4.28",
"baseLoanRate": "3.85",
"minRateBranch": "3.78",
"minRateProduct": "3.70"
},
"extensionMap": {},
"reasonMessage": "Running successfully",
"bizTime": 1736405548630,
"outputFields": {},
"workflowCode": "TBKH",
"orgCode": "802000",
"bizId": "2025010914345",
"reasonCode": 200,
"workflowVersion": 14,
"callTime": 1736405548630,
"status": 1
}

View File

@@ -0,0 +1,47 @@
{
"branch": {
"poolNo": "BR2025Q4001",
"poolType": "PUBLIC",
"ownerId": "B0010001",
"ownerName": "北京市朝阳区支行",
"ownerType": "BRANCH",
"year": "2025",
"quarter": "4",
"status": "1",
"totalQuota": "10000000.00",
"usedQuota": "6528000.50",
"availableQuota": "3471999.50",
"frozenQuota": "0.00",
"usageRate": "65.28"
},
"network": {
"poolNo": "NW2025Q4008",
"poolType": "PRIVATE",
"ownerId": "N0080012",
"ownerName": "北京市朝阳区建国路网点",
"ownerType": "NETWORK",
"year": "2025",
"quarter": "4",
"status": "1",
"totalQuota": "2000000.00",
"usedQuota": "1268900.30",
"availableQuota": "731099.70",
"frozenQuota": "0.00",
"usageRate": "63.45"
},
"manager": {
"poolNo": "MG2025Q4099",
"poolType": "PRIVATE",
"ownerId": "M0990045",
"ownerName": "张三",
"ownerType": "MANAGER",
"year": "2025",
"quarter": "4",
"status": "1",
"totalQuota": "500000.00",
"usedQuota": "389600.80",
"availableQuota": "110399.20",
"frozenQuota": "0.00",
"usageRate": "77.92"
}
}

249
pom.xml Normal file
View File

@@ -0,0 +1,249 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi</artifactId>
<version>3.8.8</version>
<name>ruoyi</name>
<url>http://www.ruoyi.vip</url>
<description>若依管理系统</description>
<properties>
<ruoyi.version>3.8.8</ruoyi.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<java.version>1.8</java.version>
<maven-jar-plugin.version>3.1.1</maven-jar-plugin.version>
<spring-framework.version>5.3.33</spring-framework.version>
<spring-security.version>5.7.12</spring-security.version>
<druid.version>1.2.23</druid.version>
<bitwalker.version>1.21</bitwalker.version>
<swagger.version>3.0.0</swagger.version>
<kaptcha.version>2.3.3</kaptcha.version>
<pagehelper.boot.version>1.4.5</pagehelper.boot.version>
<fastjson.version>2.0.43</fastjson.version>
<oshi.version>6.4.0</oshi.version>
<commons.io.version>2.13.0</commons.io.version>
<poi.version>4.1.2</poi.version>
<velocity.version>2.3</velocity.version>
<jwt.version>0.9.1</jwt.version>
<easyexcel.version>3.3.3</easyexcel.version>
<websocket.version>2.7.12</websocket.version>
</properties>
<!-- 依赖声明 -->
<dependencyManagement>
<dependencies>
<!-- SpringFramework的依赖配置-->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-framework-bom</artifactId>
<version>${spring-framework.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!-- SpringSecurity的依赖配置-->
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-bom</artifactId>
<version>${spring-security.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!-- SpringBoot的依赖配置-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>2.5.14</version>
<type>pom</type>
<scope>import</scope>
</dependency>
<!-- <dependency>-->
<!-- <groupId>org.postgresql</groupId>-->
<!-- <artifactId>postgresql</artifactId>-->
<!-- <version>42.3.3</version>-->
<!-- </dependency>-->
<!-- 阿里数据库连接池 -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>${druid.version}</version>
</dependency>
<!-- 解析客户端操作系统、浏览器等 -->
<dependency>
<groupId>eu.bitwalker</groupId>
<artifactId>UserAgentUtils</artifactId>
<version>${bitwalker.version}</version>
</dependency>
<!-- pagehelper 分页插件 -->
<dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper-spring-boot-starter</artifactId>
<version>${pagehelper.boot.version}</version>
</dependency>
<!-- 获取系统信息 -->
<dependency>
<groupId>com.github.oshi</groupId>
<artifactId>oshi-core</artifactId>
<version>${oshi.version}</version>
</dependency>
<!-- Swagger3依赖 -->
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-boot-starter</artifactId>
<version>${swagger.version}</version>
<exclusions>
<exclusion>
<groupId>io.swagger</groupId>
<artifactId>swagger-models</artifactId>
</exclusion>
</exclusions>
</dependency>
<!-- io常用工具类 -->
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>${commons.io.version}</version>
</dependency>
<!-- excel工具 -->
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
<version>${poi.version}</version>
</dependency>
<!-- easyexcel -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>easyexcel</artifactId>
<version>${easyexcel.version}</version>
</dependency>
<!-- websocket -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-websocket</artifactId>
<version>${websocket.version}</version>
</dependency>
<!-- velocity代码生成使用模板 -->
<dependency>
<groupId>org.apache.velocity</groupId>
<artifactId>velocity-engine-core</artifactId>
<version>${velocity.version}</version>
</dependency>
<!-- 阿里JSON解析器 -->
<dependency>
<groupId>com.alibaba.fastjson2</groupId>
<artifactId>fastjson2</artifactId>
<version>${fastjson.version}</version>
</dependency>
<!-- Token生成与解析-->
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
<version>${jwt.version}</version>
</dependency>
<!-- 验证码 -->
<dependency>
<groupId>pro.fessional</groupId>
<artifactId>kaptcha</artifactId>
<version>${kaptcha.version}</version>
</dependency>
<!-- 定时任务-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-quartz</artifactId>
<version>${ruoyi.version}</version>
</dependency>
<!-- 代码生成-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-generator</artifactId>
<version>${ruoyi.version}</version>
</dependency>
<!-- 核心模块-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-framework</artifactId>
<version>${ruoyi.version}</version>
</dependency>
<!-- 系统模块-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-system</artifactId>
<version>${ruoyi.version}</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>5.3.28</version>
</dependency>
<!-- 通用工具-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-common</artifactId>
<version>${ruoyi.version}</version>
</dependency>
<!-- 利率测算-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>loan-rate-pricing</artifactId>
<version>${ruoyi.version}</version>
</dependency>
</dependencies>
</dependencyManagement>
<modules>
<module>ruoyi-admin</module>
<module>ruoyi-framework</module>
<module>ruoyi-system</module>
<module>ruoyi-quartz</module>
<module>ruoyi-generator</module>
<module>ruoyi-common</module>
<module>loan-rate-pricing</module>
</modules>
<packaging>pom</packaging>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.1</version>
<configuration>
<source>${java.version}</source>
<target>${java.version}</target>
<encoding>${project.build.sourceEncoding}</encoding>
</configuration>
</plugin>
</plugins>
</build>
</project>

111
ruoyi-admin/pom.xml Normal file
View File

@@ -0,0 +1,111 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>ruoyi</artifactId>
<groupId>com.ruoyi</groupId>
<version>3.8.8</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<packaging>jar</packaging>
<artifactId>ruoyi-admin</artifactId>
<description>
web服务入口
</description>
<dependencies>
<!-- spring-boot-devtools -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-devtools</artifactId>
<optional>true</optional> <!-- 表示依赖不会传递 -->
</dependency>
<!-- swagger3-->
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-boot-starter</artifactId>
</dependency>
<!-- 防止进入swagger页面报类型转换错误排除3.0.0中的引用手动增加1.6.2版本 -->
<dependency>
<groupId>io.swagger</groupId>
<artifactId>swagger-models</artifactId>
<version>1.6.2</version>
</dependency>
<!-- Mysql驱动包 -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
</dependency>
<!-- 核心模块-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-framework</artifactId>
</dependency>
<!-- 定时任务-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-quartz</artifactId>
</dependency>
<dependency>
<groupId>com.github.xiaoymin</groupId>
<artifactId>knife4j-spring-boot-starter</artifactId>
<version>2.0.3</version>
</dependency>
<!-- 代码生成-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>ruoyi-generator</artifactId>
</dependency>
<!-- 利率测算-->
<dependency>
<groupId>com.ruoyi</groupId>
<artifactId>loan-rate-pricing</artifactId>
<version>${ruoyi.version}</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>2.5.14</version>
<configuration>
<fork>true</fork> <!-- 如果没有该配置devtools不会生效 -->
</configuration>
<executions>
<execution>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId>
<version>3.1.0</version>
<configuration>
<failOnMissingWebXml>false</failOnMissingWebXml>
<warName>${project.artifactId}</warName>
</configuration>
</plugin>
</plugins>
<finalName>${project.artifactId}</finalName>
</build>
</project>

View File

@@ -0,0 +1,34 @@
package com.ruoyi;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.scheduling.annotation.EnableAsync;
/**
* 启动程序
*
* @author ruoyi
*/
@SpringBootApplication(exclude = { DataSourceAutoConfiguration.class })
@EnableAsync
@EnableCaching
public class RuoYiApplication
{
public static void main(String[] args)
{
// System.setProperty("spring.devtools.restart.enabled", "false");
SpringApplication.run(RuoYiApplication.class, args);
System.out.println("(♥◠‿◠)ノ゙ 若依启动成功 ლ(´ڡ`ლ)゙ \n" +
" .-------. ____ __ \n" +
" | _ _ \\ \\ \\ / / \n" +
" | ( ' ) | \\ _. / ' \n" +
" |(_ o _) / _( )_ .' \n" +
" | (_,_).' __ ___(_ o _)' \n" +
" | |\\ \\ | || |(_,_)' \n" +
" | | \\ `' /| `-' / \n" +
" | | \\ / \\ / \n" +
" ''-' `'-' `-..-' ");
}
}

View File

@@ -0,0 +1,18 @@
package com.ruoyi;
import org.springframework.boot.builder.SpringApplicationBuilder;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;
/**
* web容器中进行部署
*
* @author ruoyi
*/
public class RuoYiServletInitializer extends SpringBootServletInitializer
{
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application)
{
return application.sources(RuoYiApplication.class);
}
}

View File

@@ -0,0 +1,94 @@
package com.ruoyi.web.controller.common;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.util.concurrent.TimeUnit;
import javax.annotation.Resource;
import javax.imageio.ImageIO;
import javax.servlet.http.HttpServletResponse;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.FastByteArrayOutputStream;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;
import com.google.code.kaptcha.Producer;
import com.ruoyi.common.config.RuoYiConfig;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.constant.Constants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.utils.sign.Base64;
import com.ruoyi.common.utils.uuid.IdUtils;
import com.ruoyi.system.service.ISysConfigService;
/**
* 验证码操作处理
*
* @author ruoyi
*/
@RestController
public class CaptchaController
{
@Resource(name = "captchaProducer")
private Producer captchaProducer;
@Resource(name = "captchaProducerMath")
private Producer captchaProducerMath;
@Autowired
private RedisCache redisCache;
@Autowired
private ISysConfigService configService;
/**
* 生成验证码
*/
@GetMapping("/captchaImage")
public AjaxResult getCode(HttpServletResponse response) throws IOException
{
AjaxResult ajax = AjaxResult.success();
boolean captchaEnabled = configService.selectCaptchaEnabled();
ajax.put("captchaEnabled", captchaEnabled);
if (!captchaEnabled)
{
return ajax;
}
// 保存验证码信息
String uuid = IdUtils.simpleUUID();
String verifyKey = CacheConstants.CAPTCHA_CODE_KEY + uuid;
String capStr = null, code = null;
BufferedImage image = null;
// 生成验证码
String captchaType = RuoYiConfig.getCaptchaType();
if ("math".equals(captchaType))
{
String capText = captchaProducerMath.createText();
capStr = capText.substring(0, capText.lastIndexOf("@"));
code = capText.substring(capText.lastIndexOf("@") + 1);
image = captchaProducerMath.createImage(capStr);
}
else if ("char".equals(captchaType))
{
capStr = code = captchaProducer.createText();
image = captchaProducer.createImage(capStr);
}
redisCache.setCacheObject(verifyKey, code, Constants.CAPTCHA_EXPIRATION, TimeUnit.MINUTES);
// 转换流信息写出
FastByteArrayOutputStream os = new FastByteArrayOutputStream();
try
{
ImageIO.write(image, "jpg", os);
}
catch (IOException e)
{
return AjaxResult.error(e.getMessage());
}
ajax.put("uuid", uuid);
ajax.put("img", Base64.encode(os.toByteArray()));
return ajax;
}
}

View File

@@ -0,0 +1,163 @@
package com.ruoyi.web.controller.common;
import java.util.ArrayList;
import java.util.List;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import com.ruoyi.common.config.RuoYiConfig;
import com.ruoyi.common.constant.Constants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.file.FileUploadUtils;
import com.ruoyi.common.utils.file.FileUtils;
import com.ruoyi.framework.config.ServerConfig;
/**
* 通用请求处理
*
* @author ruoyi
*/
@RestController
@RequestMapping("/common")
public class CommonController
{
private static final Logger log = LoggerFactory.getLogger(CommonController.class);
@Autowired
private ServerConfig serverConfig;
private static final String FILE_DELIMETER = ",";
/**
* 通用下载请求
*
* @param fileName 文件名称
* @param delete 是否删除
*/
@GetMapping("/download")
public void fileDownload(String fileName, Boolean delete, HttpServletResponse response, HttpServletRequest request)
{
try
{
if (!FileUtils.checkAllowDownload(fileName))
{
throw new Exception(StringUtils.format("文件名称({})非法,不允许下载。 ", fileName));
}
String realFileName = System.currentTimeMillis() + fileName.substring(fileName.indexOf("_") + 1);
String filePath = RuoYiConfig.getDownloadPath() + fileName;
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE);
FileUtils.setAttachmentResponseHeader(response, realFileName);
FileUtils.writeBytes(filePath, response.getOutputStream());
if (delete)
{
FileUtils.deleteFile(filePath);
}
}
catch (Exception e)
{
log.error("下载文件失败", e);
}
}
/**
* 通用上传请求(单个)
*/
@PostMapping("/upload")
public AjaxResult uploadFile(MultipartFile file) throws Exception
{
try
{
// 上传文件路径
String filePath = RuoYiConfig.getUploadPath();
// 上传并返回新文件名称
String fileName = FileUploadUtils.upload(filePath, file);
String url = serverConfig.getUrl() + fileName;
AjaxResult ajax = AjaxResult.success();
ajax.put("url", url);
ajax.put("fileName", fileName);
ajax.put("newFileName", FileUtils.getName(fileName));
ajax.put("originalFilename", file.getOriginalFilename());
return ajax;
}
catch (Exception e)
{
return AjaxResult.error(e.getMessage());
}
}
/**
* 通用上传请求(多个)
*/
@PostMapping("/uploads")
public AjaxResult uploadFiles(List<MultipartFile> files) throws Exception
{
try
{
// 上传文件路径
String filePath = RuoYiConfig.getUploadPath();
List<String> urls = new ArrayList<String>();
List<String> fileNames = new ArrayList<String>();
List<String> newFileNames = new ArrayList<String>();
List<String> originalFilenames = new ArrayList<String>();
for (MultipartFile file : files)
{
// 上传并返回新文件名称
String fileName = FileUploadUtils.upload(filePath, file);
String url = serverConfig.getUrl() + fileName;
urls.add(url);
fileNames.add(fileName);
newFileNames.add(FileUtils.getName(fileName));
originalFilenames.add(file.getOriginalFilename());
}
AjaxResult ajax = AjaxResult.success();
ajax.put("urls", StringUtils.join(urls, FILE_DELIMETER));
ajax.put("fileNames", StringUtils.join(fileNames, FILE_DELIMETER));
ajax.put("newFileNames", StringUtils.join(newFileNames, FILE_DELIMETER));
ajax.put("originalFilenames", StringUtils.join(originalFilenames, FILE_DELIMETER));
return ajax;
}
catch (Exception e)
{
return AjaxResult.error(e.getMessage());
}
}
/**
* 本地资源通用下载
*/
@GetMapping("/download/resource")
public void resourceDownload(String resource, HttpServletRequest request, HttpServletResponse response)
throws Exception
{
try
{
if (!FileUtils.checkAllowDownload(resource))
{
throw new Exception(StringUtils.format("资源文件({})非法,不允许下载。 ", resource));
}
// 本地资源路径
String localPath = RuoYiConfig.getProfile();
// 数据库资源地址
String downloadPath = localPath + StringUtils.substringAfter(resource, Constants.RESOURCE_PREFIX);
// 下载名称
String downloadName = StringUtils.substringAfterLast(downloadPath, "/");
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE);
FileUtils.setAttachmentResponseHeader(response, downloadName);
FileUtils.writeBytes(downloadPath, response.getOutputStream());
}
catch (Exception e)
{
log.error("下载文件失败", e);
}
}
}

View File

@@ -0,0 +1,121 @@
package com.ruoyi.web.controller.monitor;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Properties;
import java.util.Set;
import java.util.TreeSet;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisCallback;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.system.domain.SysCache;
/**
* 缓存监控
*
* @author ruoyi
*/
@RestController
@RequestMapping("/monitor/cache")
public class CacheController
{
@Autowired
private RedisTemplate<String, String> redisTemplate;
private final static List<SysCache> caches = new ArrayList<SysCache>();
{
caches.add(new SysCache(CacheConstants.LOGIN_TOKEN_KEY, "用户信息"));
caches.add(new SysCache(CacheConstants.SYS_CONFIG_KEY, "配置信息"));
caches.add(new SysCache(CacheConstants.SYS_DICT_KEY, "数据字典"));
caches.add(new SysCache(CacheConstants.CAPTCHA_CODE_KEY, "验证码"));
caches.add(new SysCache(CacheConstants.REPEAT_SUBMIT_KEY, "防重提交"));
caches.add(new SysCache(CacheConstants.RATE_LIMIT_KEY, "限流处理"));
caches.add(new SysCache(CacheConstants.PWD_ERR_CNT_KEY, "密码错误次数"));
}
@PreAuthorize("@ss.hasPermi('monitor:cache:list')")
@GetMapping()
public AjaxResult getInfo() throws Exception
{
Properties info = (Properties) redisTemplate.execute((RedisCallback<Object>) connection -> connection.info());
Properties commandStats = (Properties) redisTemplate.execute((RedisCallback<Object>) connection -> connection.info("commandstats"));
Object dbSize = redisTemplate.execute((RedisCallback<Object>) connection -> connection.dbSize());
Map<String, Object> result = new HashMap<>(3);
result.put("info", info);
result.put("dbSize", dbSize);
List<Map<String, String>> pieList = new ArrayList<>();
commandStats.stringPropertyNames().forEach(key -> {
Map<String, String> data = new HashMap<>(2);
String property = commandStats.getProperty(key);
data.put("name", StringUtils.removeStart(key, "cmdstat_"));
data.put("value", StringUtils.substringBetween(property, "calls=", ",usec"));
pieList.add(data);
});
result.put("commandStats", pieList);
return AjaxResult.success(result);
}
@PreAuthorize("@ss.hasPermi('monitor:cache:list')")
@GetMapping("/getNames")
public AjaxResult cache()
{
return AjaxResult.success(caches);
}
@PreAuthorize("@ss.hasPermi('monitor:cache:list')")
@GetMapping("/getKeys/{cacheName}")
public AjaxResult getCacheKeys(@PathVariable String cacheName)
{
Set<String> cacheKeys = redisTemplate.keys(cacheName + "*");
return AjaxResult.success(new TreeSet<>(cacheKeys));
}
@PreAuthorize("@ss.hasPermi('monitor:cache:list')")
@GetMapping("/getValue/{cacheName}/{cacheKey}")
public AjaxResult getCacheValue(@PathVariable String cacheName, @PathVariable String cacheKey)
{
String cacheValue = redisTemplate.opsForValue().get(cacheKey);
SysCache sysCache = new SysCache(cacheName, cacheKey, cacheValue);
return AjaxResult.success(sysCache);
}
@PreAuthorize("@ss.hasPermi('monitor:cache:list')")
@DeleteMapping("/clearCacheName/{cacheName}")
public AjaxResult clearCacheName(@PathVariable String cacheName)
{
Collection<String> cacheKeys = redisTemplate.keys(cacheName + "*");
redisTemplate.delete(cacheKeys);
return AjaxResult.success();
}
@PreAuthorize("@ss.hasPermi('monitor:cache:list')")
@DeleteMapping("/clearCacheKey/{cacheKey}")
public AjaxResult clearCacheKey(@PathVariable String cacheKey)
{
redisTemplate.delete(cacheKey);
return AjaxResult.success();
}
@PreAuthorize("@ss.hasPermi('monitor:cache:list')")
@DeleteMapping("/clearCacheAll")
public AjaxResult clearCacheAll()
{
Collection<String> cacheKeys = redisTemplate.keys("*");
redisTemplate.delete(cacheKeys);
return AjaxResult.success();
}
}

View File

@@ -0,0 +1,27 @@
package com.ruoyi.web.controller.monitor;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.framework.web.domain.Server;
/**
* 服务器监控
*
* @author ruoyi
*/
@RestController
@RequestMapping("/monitor/server")
public class ServerController
{
@PreAuthorize("@ss.hasPermi('monitor:server:list')")
@GetMapping()
public AjaxResult getInfo() throws Exception
{
Server server = new Server();
server.copyTo();
return AjaxResult.success(server);
}
}

View File

@@ -0,0 +1,85 @@
package com.ruoyi.web.controller.monitor;
import java.util.List;
import javax.servlet.http.HttpServletResponse;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.framework.web.service.SysPasswordService;
import com.ruoyi.system.domain.SysLogininfor;
import com.ruoyi.system.service.ISysLogininforService;
/**
* 系统访问记录
*
* @author ruoyi
*/
@RestController
@RequestMapping("/monitor/logininfor")
public class SysLogininforController extends BaseController
{
@Autowired
private ISysLogininforService logininforService;
@Autowired
private SysPasswordService passwordService;
@PreAuthorize("@ss.hasPermi('monitor:logininfor:list')")
@GetMapping("/list")
public TableDataInfo list(SysLogininfor logininfor)
{
startPage();
List<SysLogininfor> list = logininforService.selectLogininforList(logininfor);
int a =1 ;
a +=1 ;
return getDataTable(list);
}
@Log(title = "登录日志", businessType = BusinessType.EXPORT)
@PreAuthorize("@ss.hasPermi('monitor:logininfor:export')")
@PostMapping("/export")
public void export(HttpServletResponse response, SysLogininfor logininfor)
{
List<SysLogininfor> list = logininforService.selectLogininforList(logininfor);
ExcelUtil<SysLogininfor> util = new ExcelUtil<SysLogininfor>(SysLogininfor.class);
util.exportExcel(response, list, "登录日志");
}
@PreAuthorize("@ss.hasPermi('monitor:logininfor:remove')")
@Log(title = "登录日志", businessType = BusinessType.DELETE)
@DeleteMapping("/{infoIds}")
public AjaxResult remove(@PathVariable Long[] infoIds)
{
return toAjax(logininforService.deleteLogininforByIds(infoIds));
}
@PreAuthorize("@ss.hasPermi('monitor:logininfor:remove')")
@Log(title = "登录日志", businessType = BusinessType.CLEAN)
@DeleteMapping("/clean")
public AjaxResult clean()
{
logininforService.cleanLogininfor();
return success();
}
@PreAuthorize("@ss.hasPermi('monitor:logininfor:unlock')")
@Log(title = "账户解锁", businessType = BusinessType.OTHER)
@GetMapping("/unlock/{userName}")
public AjaxResult unlock(@PathVariable("userName") String userName)
{
passwordService.clearLoginRecordCache(userName);
return success();
}
}

View File

@@ -0,0 +1,69 @@
package com.ruoyi.web.controller.monitor;
import java.util.List;
import javax.servlet.http.HttpServletResponse;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.system.domain.SysOperLog;
import com.ruoyi.system.service.ISysOperLogService;
/**
* 操作日志记录
*
* @author ruoyi
*/
@RestController
@RequestMapping("/monitor/operlog")
public class SysOperlogController extends BaseController
{
@Autowired
private ISysOperLogService operLogService;
@PreAuthorize("@ss.hasPermi('monitor:operlog:list')")
@GetMapping("/list")
public TableDataInfo list(SysOperLog operLog)
{
startPage();
List<SysOperLog> list = operLogService.selectOperLogList(operLog);
return getDataTable(list);
}
@Log(title = "操作日志", businessType = BusinessType.EXPORT)
@PreAuthorize("@ss.hasPermi('monitor:operlog:export')")
@PostMapping("/export")
public void export(HttpServletResponse response, SysOperLog operLog)
{
List<SysOperLog> list = operLogService.selectOperLogList(operLog);
ExcelUtil<SysOperLog> util = new ExcelUtil<SysOperLog>(SysOperLog.class);
util.exportExcel(response, list, "操作日志");
}
@Log(title = "操作日志", businessType = BusinessType.DELETE)
@PreAuthorize("@ss.hasPermi('monitor:operlog:remove')")
@DeleteMapping("/{operIds}")
public AjaxResult remove(@PathVariable Long[] operIds)
{
return toAjax(operLogService.deleteOperLogByIds(operIds));
}
@Log(title = "操作日志", businessType = BusinessType.CLEAN)
@PreAuthorize("@ss.hasPermi('monitor:operlog:remove')")
@DeleteMapping("/clean")
public AjaxResult clean()
{
operLogService.cleanOperLog();
return success();
}
}

View File

@@ -0,0 +1,83 @@
package com.ruoyi.web.controller.monitor;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.system.domain.SysUserOnline;
import com.ruoyi.system.service.ISysUserOnlineService;
/**
* 在线用户监控
*
* @author ruoyi
*/
@RestController
@RequestMapping("/monitor/online")
public class SysUserOnlineController extends BaseController
{
@Autowired
private ISysUserOnlineService userOnlineService;
@Autowired
private RedisCache redisCache;
@PreAuthorize("@ss.hasPermi('monitor:online:list')")
@GetMapping("/list")
public TableDataInfo list(String ipaddr, String userName)
{
Collection<String> keys = redisCache.keys(CacheConstants.LOGIN_TOKEN_KEY + "*");
List<SysUserOnline> userOnlineList = new ArrayList<SysUserOnline>();
for (String key : keys)
{
LoginUser user = redisCache.getCacheObject(key);
if (StringUtils.isNotEmpty(ipaddr) && StringUtils.isNotEmpty(userName))
{
userOnlineList.add(userOnlineService.selectOnlineByInfo(ipaddr, userName, user));
}
else if (StringUtils.isNotEmpty(ipaddr))
{
userOnlineList.add(userOnlineService.selectOnlineByIpaddr(ipaddr, user));
}
else if (StringUtils.isNotEmpty(userName) && StringUtils.isNotNull(user.getUser()))
{
userOnlineList.add(userOnlineService.selectOnlineByUserName(userName, user));
}
else
{
userOnlineList.add(userOnlineService.loginUserToUserOnline(user));
}
}
Collections.reverse(userOnlineList);
userOnlineList.removeAll(Collections.singleton(null));
return getDataTable(userOnlineList);
}
/**
* 强退用户
*/
@PreAuthorize("@ss.hasPermi('monitor:online:forceLogout')")
@Log(title = "在线用户", businessType = BusinessType.FORCE)
@DeleteMapping("/{tokenId}")
public AjaxResult forceLogout(@PathVariable String tokenId)
{
redisCache.deleteObject(CacheConstants.LOGIN_TOKEN_KEY + tokenId);
return success();
}
}

View File

@@ -0,0 +1,133 @@
package com.ruoyi.web.controller.system;
import java.util.List;
import javax.servlet.http.HttpServletResponse;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.system.domain.SysConfig;
import com.ruoyi.system.service.ISysConfigService;
/**
* 参数配置 信息操作处理
*
* @author ruoyi
*/
@RestController
@RequestMapping("/system/config")
public class SysConfigController extends BaseController
{
@Autowired
private ISysConfigService configService;
/**
* 获取参数配置列表
*/
@PreAuthorize("@ss.hasPermi('system:config:list')")
@GetMapping("/list")
public TableDataInfo list(SysConfig config)
{
startPage();
List<SysConfig> list = configService.selectConfigList(config);
return getDataTable(list);
}
@Log(title = "参数管理", businessType = BusinessType.EXPORT)
@PreAuthorize("@ss.hasPermi('system:config:export')")
@PostMapping("/export")
public void export(HttpServletResponse response, SysConfig config)
{
List<SysConfig> list = configService.selectConfigList(config);
ExcelUtil<SysConfig> util = new ExcelUtil<SysConfig>(SysConfig.class);
util.exportExcel(response, list, "参数数据");
}
/**
* 根据参数编号获取详细信息
*/
@PreAuthorize("@ss.hasPermi('system:config:query')")
@GetMapping(value = "/{configId}")
public AjaxResult getInfo(@PathVariable Long configId)
{
return success(configService.selectConfigById(configId));
}
/**
* 根据参数键名查询参数值
*/
@GetMapping(value = "/configKey/{configKey}")
public AjaxResult getConfigKey(@PathVariable String configKey)
{
return success(configService.selectConfigByKey(configKey));
}
/**
* 新增参数配置
*/
@PreAuthorize("@ss.hasPermi('system:config:add')")
@Log(title = "参数管理", businessType = BusinessType.INSERT)
@PostMapping
public AjaxResult add(@Validated @RequestBody SysConfig config)
{
if (!configService.checkConfigKeyUnique(config))
{
return error("新增参数'" + config.getConfigName() + "'失败,参数键名已存在");
}
config.setCreateBy(getUsername());
return toAjax(configService.insertConfig(config));
}
/**
* 修改参数配置
*/
@PreAuthorize("@ss.hasPermi('system:config:edit')")
@Log(title = "参数管理", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult edit(@Validated @RequestBody SysConfig config)
{
if (!configService.checkConfigKeyUnique(config))
{
return error("修改参数'" + config.getConfigName() + "'失败,参数键名已存在");
}
config.setUpdateBy(getUsername());
return toAjax(configService.updateConfig(config));
}
/**
* 删除参数配置
*/
@PreAuthorize("@ss.hasPermi('system:config:remove')")
@Log(title = "参数管理", businessType = BusinessType.DELETE)
@DeleteMapping("/{configIds}")
public AjaxResult remove(@PathVariable Long[] configIds)
{
configService.deleteConfigByIds(configIds);
return success();
}
/**
* 刷新参数缓存
*/
@PreAuthorize("@ss.hasPermi('system:config:remove')")
@Log(title = "参数管理", businessType = BusinessType.CLEAN)
@DeleteMapping("/refreshCache")
public AjaxResult refreshCache()
{
configService.resetConfigCache();
return success();
}
}

View File

@@ -0,0 +1,142 @@
package com.ruoyi.web.controller.system;
import java.util.List;
import io.swagger.annotations.ApiOperation;
import org.apache.commons.lang3.ArrayUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.constant.UserConstants;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysDept;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.system.service.ISysDeptService;
/**
* 部门信息
*
* @author ruoyi
*/
@RestController
@RequestMapping("/system/dept")
public class SysDeptController extends BaseController
{
@Autowired
private ISysDeptService deptService;
/**
* 获取部门列表
*/
@PreAuthorize("@ss.hasPermi('system:dept:list')")
@GetMapping("/list")
public AjaxResult list(SysDept dept)
{
List<SysDept> depts = deptService.selectDeptList(dept);
return success(depts);
}
@ApiOperation("获取总行部门列表")
@PreAuthorize("@ss.hasPermi('system:dept:list')")
@GetMapping("/headList")
public AjaxResult headList(){
List<SysDept> depts = deptService.selectHeadDeptList();
return success(depts);
}
/**
* 查询部门列表(排除节点)
*/
@PreAuthorize("@ss.hasPermi('system:dept:list')")
@GetMapping("/list/exclude/{deptId}")
public AjaxResult excludeChild(@PathVariable(value = "deptId", required = false) Long deptId)
{
List<SysDept> depts = deptService.selectDeptList(new SysDept());
depts.removeIf(d -> d.getDeptId().intValue() == deptId || ArrayUtils.contains(StringUtils.split(d.getAncestors(), ","), deptId + ""));
return success(depts);
}
/**
* 根据部门编号获取详细信息
*/
@PreAuthorize("@ss.hasPermi('system:dept:query')")
@GetMapping(value = "/{deptId}")
public AjaxResult getInfo(@PathVariable Long deptId)
{
deptService.checkDeptDataScope(deptId);
return success(deptService.selectDeptById(deptId));
}
/**
* 新增部门
*/
@PreAuthorize("@ss.hasPermi('system:dept:add')")
@Log(title = "部门管理", businessType = BusinessType.INSERT)
@PostMapping("/add")
public AjaxResult add(@Validated @RequestBody SysDept dept)
{
if (!deptService.checkDeptNameUnique(dept))
{
return error("新增部门'" + dept.getDeptName() + "'失败,部门名称已存在");
}
dept.setCreateBy(getUsername());
return toAjax(deptService.insertDept(dept));
}
/**
* 修改部门
*/
@PreAuthorize("@ss.hasPermi('system:dept:edit')")
@Log(title = "部门管理", businessType = BusinessType.UPDATE)
@PutMapping("/edit")
public AjaxResult edit(@Validated @RequestBody SysDept dept)
{
Long deptId = dept.getDeptId();
deptService.checkDeptDataScope(deptId);
if (!deptService.checkDeptNameUnique(dept))
{
return error("修改部门'" + dept.getDeptName() + "'失败,部门名称已存在");
}
else if (dept.getParentId().equals(deptId))
{
return error("修改部门'" + dept.getDeptName() + "'失败,上级部门不能是自己");
}
else if (StringUtils.equals(UserConstants.DEPT_DISABLE, dept.getStatus()) && deptService.selectNormalChildrenDeptById(deptId) > 0)
{
return error("该部门包含未停用的子部门!");
}
dept.setUpdateBy(getUsername());
return toAjax(deptService.updateDept(dept));
}
/**
* 删除部门
*/
@PreAuthorize("@ss.hasPermi('system:dept:remove')")
@Log(title = "部门管理", businessType = BusinessType.DELETE)
@DeleteMapping("/{deptId}")
public AjaxResult remove(@PathVariable Long deptId)
{
if (deptService.hasChildByDeptId(deptId))
{
return warn("存在下级部门,不允许删除");
}
if (deptService.checkDeptExistUser(deptId))
{
return warn("部门存在用户,不允许删除");
}
deptService.checkDeptDataScope(deptId);
return toAjax(deptService.deleteDeptById(deptId));
}
}

View File

@@ -0,0 +1,127 @@
package com.ruoyi.web.controller.system;
import java.util.ArrayList;
import java.util.List;
import javax.servlet.http.HttpServletResponse;
import com.ruoyi.common.core.domain.entity.SysDictType;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysDictData;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.system.service.ISysDictDataService;
import com.ruoyi.system.service.ISysDictTypeService;
/**
* 数据字典信息
*
* @author ruoyi
*/
@Api(tags = "字典数据接口")
@RestController
@RequestMapping("/system/dict/data")
public class SysDictDataController extends BaseController
{
@Autowired
private ISysDictDataService dictDataService;
@Autowired
private ISysDictTypeService dictTypeService;
@PreAuthorize("@ss.hasPermi('system:dict:list')")
@GetMapping("/list")
public TableDataInfo list(SysDictData dictData)
{
startPage();
List<SysDictData> list = dictDataService.selectDictDataList(dictData);
return getDataTable(list);
}
@Log(title = "字典数据", businessType = BusinessType.EXPORT)
@PreAuthorize("@ss.hasPermi('system:dict:export')")
@PostMapping("/export")
public void export(HttpServletResponse response, SysDictData dictData)
{
List<SysDictData> list = dictDataService.selectDictDataList(dictData);
ExcelUtil<SysDictData> util = new ExcelUtil<SysDictData>(SysDictData.class);
util.exportExcel(response, list, "字典数据");
}
/**
* 查询字典数据详细
*/
@PreAuthorize("@ss.hasPermi('system:dict:query')")
@GetMapping(value = "/{dictCode}")
public AjaxResult getInfo(@PathVariable Long dictCode)
{
return success(dictDataService.selectDictDataById(dictCode));
}
/**
* 根据字典类型查询字典数据信息
*/
@ApiOperation("根据字典类型查询字典数据信息")
@GetMapping(value = "/type/{dictType}")
public AjaxResult dictType(@PathVariable String dictType)
{
List<SysDictData> data = dictTypeService.selectDictDataByType(dictType);
if (StringUtils.isNull(data))
{
data = new ArrayList<>();
}
return success(data);
}
/**
* 新增字典类型
*/
@PreAuthorize("@ss.hasPermi('system:dict:add')")
@Log(title = "字典数据", businessType = BusinessType.INSERT)
@PostMapping
public AjaxResult add(@Validated @RequestBody SysDictData dict)
{
dict.setCreateBy(getUsername());
return toAjax(dictDataService.insertDictData(dict));
}
/**
* 修改保存字典类型
*/
@PreAuthorize("@ss.hasPermi('system:dict:edit')")
@Log(title = "字典数据", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult edit(@Validated @RequestBody SysDictData dict)
{
dict.setUpdateBy(getUsername());
return toAjax(dictDataService.updateDictData(dict));
}
/**
* 删除字典类型
*/
@PreAuthorize("@ss.hasPermi('system:dict:remove')")
@Log(title = "字典类型", businessType = BusinessType.DELETE)
@DeleteMapping("/{dictCodes}")
public AjaxResult remove(@PathVariable Long[] dictCodes)
{
dictDataService.deleteDictDataByIds(dictCodes);
return success();
}
}

View File

@@ -0,0 +1,131 @@
package com.ruoyi.web.controller.system;
import java.util.List;
import javax.servlet.http.HttpServletResponse;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysDictType;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.system.service.ISysDictTypeService;
/**
* 数据字典信息
*
* @author ruoyi
*/
@RestController
@RequestMapping("/system/dict/type")
public class SysDictTypeController extends BaseController
{
@Autowired
private ISysDictTypeService dictTypeService;
@PreAuthorize("@ss.hasPermi('system:dict:list')")
@GetMapping("/list")
public TableDataInfo list(SysDictType dictType)
{
startPage();
List<SysDictType> list = dictTypeService.selectDictTypeList(dictType);
return getDataTable(list);
}
@Log(title = "字典类型", businessType = BusinessType.EXPORT)
@PreAuthorize("@ss.hasPermi('system:dict:export')")
@PostMapping("/export")
public void export(HttpServletResponse response, SysDictType dictType)
{
List<SysDictType> list = dictTypeService.selectDictTypeList(dictType);
ExcelUtil<SysDictType> util = new ExcelUtil<SysDictType>(SysDictType.class);
util.exportExcel(response, list, "字典类型");
}
/**
* 查询字典类型详细
*/
@PreAuthorize("@ss.hasPermi('system:dict:query')")
@GetMapping(value = "/{dictId}")
public AjaxResult getInfo(@PathVariable Long dictId)
{
return success(dictTypeService.selectDictTypeById(dictId));
}
/**
* 新增字典类型
*/
@PreAuthorize("@ss.hasPermi('system:dict:add')")
@Log(title = "字典类型", businessType = BusinessType.INSERT)
@PostMapping
public AjaxResult add(@Validated @RequestBody SysDictType dict)
{
if (!dictTypeService.checkDictTypeUnique(dict))
{
return error("新增字典'" + dict.getDictName() + "'失败,字典类型已存在");
}
dict.setCreateBy(getUsername());
return toAjax(dictTypeService.insertDictType(dict));
}
/**
* 修改字典类型
*/
@PreAuthorize("@ss.hasPermi('system:dict:edit')")
@Log(title = "字典类型", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult edit(@Validated @RequestBody SysDictType dict)
{
if (!dictTypeService.checkDictTypeUnique(dict))
{
return error("修改字典'" + dict.getDictName() + "'失败,字典类型已存在");
}
dict.setUpdateBy(getUsername());
return toAjax(dictTypeService.updateDictType(dict));
}
/**
* 删除字典类型
*/
@PreAuthorize("@ss.hasPermi('system:dict:remove')")
@Log(title = "字典类型", businessType = BusinessType.DELETE)
@DeleteMapping("/{dictIds}")
public AjaxResult remove(@PathVariable Long[] dictIds)
{
dictTypeService.deleteDictTypeByIds(dictIds);
return success();
}
/**
* 刷新字典缓存
*/
@PreAuthorize("@ss.hasPermi('system:dict:remove')")
@Log(title = "字典类型", businessType = BusinessType.CLEAN)
@DeleteMapping("/refreshCache")
public AjaxResult refreshCache()
{
dictTypeService.resetDictCache();
return success();
}
/**
* 获取字典选择框列表
*/
@GetMapping("/optionselect")
public AjaxResult optionselect()
{
List<SysDictType> dictTypes = dictTypeService.selectDictTypeAll();
return success(dictTypes);
}
}

View File

@@ -0,0 +1,29 @@
package com.ruoyi.web.controller.system;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.config.RuoYiConfig;
import com.ruoyi.common.utils.StringUtils;
/**
* 首页
*
* @author ruoyi
*/
@RestController
public class SysIndexController
{
/** 系统基础配置 */
@Autowired
private RuoYiConfig ruoyiConfig;
/**
* 访问首页,提示语
*/
@RequestMapping("/")
public String index()
{
return StringUtils.format("欢迎使用{}后台管理框架当前版本v{},请通过前端地址访问。", ruoyiConfig.getName(), ruoyiConfig.getVersion());
}
}

View File

@@ -0,0 +1,226 @@
package com.ruoyi.web.controller.system;
import java.io.IOException;
import java.io.InputStream;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.List;
import java.util.Set;
import com.alibaba.fastjson2.JSONObject;
import com.ruoyi.common.constant.HttpStatus;
import com.ruoyi.common.core.domain.R;
import com.ruoyi.common.core.domain.entity.SysDictData;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.framework.web.service.TokenService;
import com.ruoyi.system.service.ISysLogininforService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import io.swagger.models.auth.In;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.core.io.InputStreamResource;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.http.ContentDisposition;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import com.ruoyi.common.constant.Constants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysMenu;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.core.domain.model.LoginBody;
import com.ruoyi.system.domain.SysLogininfor;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.framework.web.service.SysLoginService;
import com.ruoyi.framework.web.service.SysPermissionService;
import com.ruoyi.system.service.ISysMenuService;
import javax.annotation.Resource;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* 登录验证
*
* @author ruoyi
*/
@RestController
@Api("登录验证")
public class SysLoginController
{
@Autowired
private SysLoginService loginService;
@Autowired
private ISysMenuService menuService;
@Autowired
private SysPermissionService permissionService;
@Autowired
private TokenService tokenService;
@Autowired
private ISysLogininforService sysLogininforService;
@Resource
RedisCache redisCache;
@Value("${ruoyi.downloadProductManualPath}")
private String downloadProductManualPath;
@Value("${ruoyi.productManualfileName}")
private String productManualfileName;
/**
* 登录方法
*
* @param loginBody 登录信息
* @return 结果
*/
@PostMapping("/login")
@ApiOperation("登录")
public AjaxResult login(@RequestBody LoginBody loginBody)
{
AjaxResult ajax = AjaxResult.success();
// 生成令牌
String token = loginService.login(loginBody.getUsername(), loginBody.getPassword(), loginBody.getCode(),
loginBody.getUuid());
ajax.put(Constants.TOKEN, token);
return ajax;
}
@PostMapping("/isFirstLogin")
@ApiOperation("用户首次登录")
public AjaxResult isFirstLogin(@RequestBody LoginBody loginBody)
{
AjaxResult ajax = AjaxResult.success();
String username = loginBody.getUsername();
List<SysLogininfor> loginRecords = sysLogininforService.selectLogininforList(new SysLogininfor(){{setUserName(username);}});
if(loginRecords == null || loginRecords.isEmpty()){
return AjaxResult.success("用户首次登录");
}else {
return AjaxResult.success("用户已有登录记录");
}
}
// @PostMapping("/loginBi")
@ApiOperation("登录BI")
public AjaxResult loginBi(HttpServletRequest request, HttpServletResponse response)
{
AjaxResult ajax = AjaxResult.success();
LoginUser biLoginUser = tokenService.getBiLoginUser(request);
if(StringUtils.isNotNull(biLoginUser)) {
ajax.put(Constants.JWT_USERID2, biLoginUser.getUserId().toString());
ajax.put(Constants.RESULT,"success");
}else {
ajax.put(Constants.RESULT, "error");
}
return ajax;
}
/**
* 获取用户信息
*
* @return 用户信息
*/
@GetMapping("getInfo")
public AjaxResult getInfo()
{
SysUser user = SecurityUtils.getLoginUser().getUser();
// 角色集合
Set<String> roles = permissionService.getRolePermission(user);
// 权限集合
Set<String> permissions = permissionService.getMenuPermission(user);
AjaxResult ajax = AjaxResult.success();
ajax.put("user", user);
ajax.put("roles", roles);
ajax.put("permissions", permissions);
return ajax;
}
/**
* 获取路由信息
*
* @return 路由信息
*/
@GetMapping("getRouters")
@ApiOperation("获取路由信息")
public AjaxResult getRouters()
{
Long userId = SecurityUtils.getUserId();
List<SysMenu> menus = menuService.selectMenuTreeByUserId(userId);
return AjaxResult.success(menuService.buildMenus(menus));
}
@PostMapping("/countMenu")
@ApiOperation("统计菜单访问")
@ApiImplicitParams({
@ApiImplicitParam(name = "menuId", value = "菜单id", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "menuName", value = "菜单名称", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "component", value = "菜单路由", dataType = "String", dataTypeClass = String.class)
})
public AjaxResult countMenu(Long menuId,String menuName,String component)
{
return AjaxResult.success(menuService.insertCount(menuId,menuName,component));
}
@GetMapping("/downloadProductManual")
@ApiOperation("下载产品手册")
public ResponseEntity<?> downloadProductManual() {
// String directoryPath = "C:\\Users\\ZJRCU\\Downloads";
// String fileName = "product_manual_szzh.docx";
Path filePath = Paths.get(downloadProductManualPath, productManualfileName);
// 验证文件是否存在且是.doc文件
if (!Files.exists(filePath) || Files.isDirectory(filePath)) {
return ResponseEntity.status(HttpStatus.NOT_FOUND).body("文件不存在");
}
List<SysDictData> sysDictTypeArrayList = new ArrayList<SysDictData>(redisCache.getCacheObject("sys_dict:product_manual_szzh"));
String docName = "数智支行操作手册.docx";
if(sysDictTypeArrayList.size() > 0){
docName = sysDictTypeArrayList.get(0).getDictLabel();
}
try {
// 设置响应头
ContentDisposition contentDisposition = ContentDisposition
.attachment()
.filename(docName)
.build();
// 打开文件输入流
InputStream inputStream = Files.newInputStream(filePath);
return ResponseEntity.ok()
.headers(headers -> headers.setContentDisposition(contentDisposition))
.contentType(MediaType.APPLICATION_OCTET_STREAM)
.contentLength(Files.size(filePath))
.body(new InputStreamResource(inputStream));
} catch (IOException e) {
return ResponseEntity.status(HttpStatus.BAD_REQUEST)
.body("下载文件时出错: " + e.getMessage());
}
}
}

View File

@@ -0,0 +1,152 @@
package com.ruoyi.web.controller.system;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Collectors;
import com.ruoyi.common.core.domain.model.LoginUser;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.constant.UserConstants;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysMenu;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.system.service.ISysMenuService;
/**
* 菜单信息
*
* @author ruoyi
*/
@RestController
@RequestMapping("/system/menu")
public class SysMenuController extends BaseController
{
@Autowired
private ISysMenuService menuService;
/**
* 获取菜单列表
*/
@ApiOperation("获取菜单列表")
@PreAuthorize("@ss.hasPermi('system:menu:list')")
@GetMapping("/list")
public AjaxResult list(SysMenu menu)
{
List<SysMenu> menus = menuService.selectMenuList(menu, getUserId());
return success(menus);
}
/**
* 根据菜单编号获取详细信息
*/
@PreAuthorize("@ss.hasPermi('system:menu:query')")
@GetMapping(value = "/{menuId}")
public AjaxResult getInfo(@PathVariable Long menuId)
{
return success(menuService.selectMenuById(menuId));
}
/**
* 获取菜单下拉树列表
*/
@GetMapping("/treeselect")
public AjaxResult treeselect(SysMenu menu)
{
List<SysMenu> menus = menuService.selectMenuList(menu, getUserId());
return success(menuService.buildMenuTreeSelect(menus));
}
/**
* 加载对应角色菜单列表树
*/
@GetMapping(value = "/roleMenuTreeselect/{roleId}")
public AjaxResult roleMenuTreeselect(@PathVariable("roleId") Long roleId)
{
List<SysMenu> menus = menuService.selectMenuList(getUserId());
AjaxResult ajax = AjaxResult.success();
ajax.put("checkedKeys", menuService.selectMenuListByRoleId(roleId));
ajax.put("menus", menuService.buildMenuTreeSelect(menus));
return ajax;
}
/**
* 新增菜单
*/
@ApiOperation("新增菜单")
@PreAuthorize("@ss.hasPermi('system:menu:add')")
@Log(title = "菜单管理", businessType = BusinessType.INSERT)
@PostMapping
public AjaxResult add(@Validated @RequestBody SysMenu menu)
{
if (!menuService.checkMenuNameUnique(menu))
{
return error("新增菜单'" + menu.getMenuName() + "'失败,菜单名称已存在");
}
else if (UserConstants.YES_FRAME.equals(menu.getIsFrame()) && !StringUtils.ishttp(menu.getPath()))
{
return error("新增菜单'" + menu.getMenuName() + "'失败地址必须以http(s)://开头");
}
menu.setCreateBy(getUsername());
return toAjax(menuService.insertMenu(menu));
}
/**
* 修改菜单
*/
@ApiOperation("修改菜单")
@PreAuthorize("@ss.hasPermi('system:menu:edit')")
@Log(title = "菜单管理", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult edit(@Validated @RequestBody SysMenu menu)
{
if (!menuService.checkMenuNameUnique(menu))
{
return error("修改菜单'" + menu.getMenuName() + "'失败,菜单名称已存在");
}
else if (UserConstants.YES_FRAME.equals(menu.getIsFrame()) && !StringUtils.ishttp(menu.getPath()))
{
return error("修改菜单'" + menu.getMenuName() + "'失败地址必须以http(s)://开头");
}
else if (menu.getMenuId().equals(menu.getParentId()))
{
return error("修改菜单'" + menu.getMenuName() + "'失败,上级菜单不能选择自己");
}
menu.setUpdateBy(getUsername());
return toAjax(menuService.updateMenu(menu));
}
/**
* 删除菜单
*/
@PreAuthorize("@ss.hasPermi('system:menu:remove')")
@Log(title = "菜单管理", businessType = BusinessType.DELETE)
@DeleteMapping("/{menuId}")
public AjaxResult remove(@PathVariable("menuId") Long menuId)
{
if (menuService.hasChildByMenuId(menuId))
{
return warn("存在子菜单,不允许删除");
}
if (menuService.checkMenuExistRole(menuId))
{
return warn("菜单已分配,不允许删除");
}
return toAjax(menuService.deleteMenuById(menuId));
}
}

View File

@@ -0,0 +1,91 @@
package com.ruoyi.web.controller.system;
import java.util.List;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.system.domain.SysNotice;
import com.ruoyi.system.service.ISysNoticeService;
/**
* 公告 信息操作处理
*
* @author ruoyi
*/
@RestController
@RequestMapping("/system/notice")
public class SysNoticeController extends BaseController
{
@Autowired
private ISysNoticeService noticeService;
/**
* 获取通知公告列表
*/
@PreAuthorize("@ss.hasPermi('system:notice:list')")
@GetMapping("/list")
public TableDataInfo list(SysNotice notice)
{
startPage();
List<SysNotice> list = noticeService.selectNoticeList(notice);
return getDataTable(list);
}
/**
* 根据通知公告编号获取详细信息
*/
@PreAuthorize("@ss.hasPermi('system:notice:query')")
@GetMapping(value = "/{noticeId}")
public AjaxResult getInfo(@PathVariable Long noticeId)
{
return success(noticeService.selectNoticeById(noticeId));
}
/**
* 新增通知公告
*/
@PreAuthorize("@ss.hasPermi('system:notice:add')")
@Log(title = "通知公告", businessType = BusinessType.INSERT)
@PostMapping
public AjaxResult add(@Validated @RequestBody SysNotice notice)
{
notice.setCreateBy(getUsername());
return toAjax(noticeService.insertNotice(notice));
}
/**
* 修改通知公告
*/
@PreAuthorize("@ss.hasPermi('system:notice:edit')")
@Log(title = "通知公告", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult edit(@Validated @RequestBody SysNotice notice)
{
notice.setUpdateBy(getUsername());
return toAjax(noticeService.updateNotice(notice));
}
/**
* 删除通知公告
*/
@PreAuthorize("@ss.hasPermi('system:notice:remove')")
@Log(title = "通知公告", businessType = BusinessType.DELETE)
@DeleteMapping("/{noticeIds}")
public AjaxResult remove(@PathVariable Long[] noticeIds)
{
return toAjax(noticeService.deleteNoticeByIds(noticeIds));
}
}

View File

@@ -0,0 +1,135 @@
package com.ruoyi.web.controller.system;
import java.util.List;
import javax.servlet.http.HttpServletResponse;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.system.domain.SysPost;
import com.ruoyi.system.service.ISysPostService;
/**
* 岗位信息操作处理
*
* @author ruoyi
*/
@Api(tags = "岗位接口")
@RestController
@RequestMapping("/system/post")
public class SysPostController extends BaseController
{
@Autowired
private ISysPostService postService;
/**
* 获取岗位列表
*/
@PreAuthorize("@ss.hasPermi('system:post:list')")
@GetMapping("/list")
public TableDataInfo list(SysPost post)
{
startPage();
List<SysPost> list = postService.selectPostList(post);
return getDataTable(list);
}
@Log(title = "岗位管理", businessType = BusinessType.EXPORT)
@PreAuthorize("@ss.hasPermi('system:post:export')")
@PostMapping("/export")
public void export(HttpServletResponse response, SysPost post)
{
List<SysPost> list = postService.selectPostList(post);
ExcelUtil<SysPost> util = new ExcelUtil<SysPost>(SysPost.class);
util.exportExcel(response, list, "岗位数据");
}
/**
* 根据岗位编号获取详细信息
*/
@PreAuthorize("@ss.hasPermi('system:post:query')")
@GetMapping(value = "/{postId}")
public AjaxResult getInfo(@PathVariable Long postId)
{
return success(postService.selectPostById(postId));
}
/**
* 新增岗位
*/
@ApiOperation("新增岗位")
@PreAuthorize("@ss.hasPermi('system:post:add')")
@Log(title = "岗位管理", businessType = BusinessType.INSERT)
@PostMapping
public AjaxResult add(@Validated @RequestBody SysPost post)
{
if (!postService.checkPostNameUnique(post))
{
return error("新增岗位'" + post.getPostName() + "'失败,岗位名称已存在");
}
else if (!postService.checkPostCodeUnique(post))
{
return error("新增岗位'" + post.getPostName() + "'失败,岗位编码已存在");
}
post.setCreateBy(getUsername());
return toAjax(postService.insertPost(post));
}
/**
* 修改岗位
*/
@PreAuthorize("@ss.hasPermi('system:post:edit')")
@Log(title = "岗位管理", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult edit(@Validated @RequestBody SysPost post)
{
if (!postService.checkPostNameUnique(post))
{
return error("修改岗位'" + post.getPostName() + "'失败,岗位名称已存在");
}
else if (!postService.checkPostCodeUnique(post))
{
return error("修改岗位'" + post.getPostName() + "'失败,岗位编码已存在");
}
post.setUpdateBy(getUsername());
return toAjax(postService.updatePost(post));
}
/**
* 删除岗位
*/
@PreAuthorize("@ss.hasPermi('system:post:remove')")
@Log(title = "岗位管理", businessType = BusinessType.DELETE)
@DeleteMapping("/{postIds}")
public AjaxResult remove(@PathVariable Long[] postIds)
{
return toAjax(postService.deletePostByIds(postIds));
}
/**
* 获取岗位选择框列表(根据权限)
*/
@ApiOperation("根据管理权限获取岗位选择框列表")
@GetMapping("/optionselect")
public AjaxResult optionselect()
{
List<SysPost> posts = postService.selectPostList(new SysPost());
return success(posts);
}
}

View File

@@ -0,0 +1,154 @@
package com.ruoyi.web.controller.system;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.config.RuoYiConfig;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.file.FileUploadUtils;
import com.ruoyi.common.utils.file.MimeTypeUtils;
import com.ruoyi.framework.web.service.TokenService;
import com.ruoyi.system.service.ISysUserService;
import java.util.regex.Pattern;
/**
* 个人信息 业务处理
*
* @author ruoyi
*/
@RestController
@RequestMapping("/system/user/profile")
@Api(tags = "个人信息")
public class SysProfileController extends BaseController
{
@Autowired
private ISysUserService userService;
@Autowired
private TokenService tokenService;
/**
* 个人信息
*/
@GetMapping
public AjaxResult profile()
{
LoginUser loginUser = getLoginUser();
SysUser user = loginUser.getUser();
AjaxResult ajax = AjaxResult.success(user);
ajax.put("roleGroup", userService.selectUserRoleGroup(loginUser.getUsername()));
ajax.put("postGroup", userService.selectUserPostGroup(loginUser.getUsername()));
return ajax;
}
/**
* 修改用户
*/
@Log(title = "个人信息", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult updateProfile(@RequestBody SysUser user)
{
LoginUser loginUser = getLoginUser();
SysUser currentUser = loginUser.getUser();
currentUser.setNickName(user.getNickName());
currentUser.setEmail(user.getEmail());
currentUser.setPhonenumber(user.getPhonenumber());
currentUser.setSex(user.getSex());
if (StringUtils.isNotEmpty(user.getPhonenumber()) && !userService.checkPhoneUnique(currentUser))
{
return error("修改用户'" + loginUser.getUsername() + "'失败,手机号码已存在");
}
if (StringUtils.isNotEmpty(user.getEmail()) && !userService.checkEmailUnique(currentUser))
{
return error("修改用户'" + loginUser.getUsername() + "'失败,邮箱账号已存在");
}
if (userService.updateUserProfile(currentUser) > 0)
{
// 更新缓存用户信息
tokenService.setLoginUser(loginUser);
return success();
}
return error("修改个人信息异常,请联系管理员");
}
/**
* 重置密码
*/
@Log(title = "个人信息", businessType = BusinessType.UPDATE)
@PutMapping("/updatePwd")
public AjaxResult updatePwd(String oldPassword, String newPassword)
{
LoginUser loginUser = getLoginUser();
String userName = loginUser.getUsername();
String password = loginUser.getPassword();
if (!SecurityUtils.matchesPassword(oldPassword, password))
{
return error("修改密码失败,旧密码错误");
}
if (SecurityUtils.matchesPassword(newPassword, password))
{
return error("新密码不能与旧密码相同");
}
if (newPassword.contains(getUsername()))
{
return error("新密码不能包含柜员号!");
}
Pattern PASSWORD_PATTERN = Pattern.compile("^(?:(?=.*[A-Z])(?=.*[a-z])(?=.*\\d)|(?=.*[A-Z])(?=.*[a-z])(?=.*[@#$%^&+=!])|(?=.*[A-Z])(?=.*\\d)(?=.*[@#$%^&+=!])|(?=.*[a-z])(?=.*\\d)(?=.*[@#$%^&+=!])).{8,}$");
if ( !PASSWORD_PATTERN.matcher(newPassword).matches())
{
return error("新密码长度需大于等于8位,且包含大小写、数字、特殊字符中的至少三种!");
}
newPassword = SecurityUtils.encryptPassword(newPassword);
if (userService.resetUserPwd(userName, newPassword) > 0)
{
// 更新缓存用户密码
loginUser.getUser().setPassword(newPassword);
tokenService.setLoginUser(loginUser);
return success();
}
return error("修改密码异常,请联系管理员");
}
/**
* 头像上传
*/
@Log(title = "用户头像", businessType = BusinessType.UPDATE)
@PostMapping("/avatar")
public AjaxResult avatar(@RequestParam("avatarfile") MultipartFile file) throws Exception
{
if (!file.isEmpty())
{
LoginUser loginUser = getLoginUser();
String avatar = FileUploadUtils.upload(RuoYiConfig.getAvatarPath(), file, MimeTypeUtils.IMAGE_EXTENSION);
if (userService.updateUserAvatar(loginUser.getUsername(), avatar))
{
AjaxResult ajax = AjaxResult.success();
ajax.put("imgUrl", avatar);
// 更新缓存用户头像
loginUser.getUser().setAvatar(avatar);
tokenService.setLoginUser(loginUser);
return ajax;
}
}
return error("上传图片异常,请联系管理员");
}
}

View File

@@ -0,0 +1,38 @@
package com.ruoyi.web.controller.system;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.model.RegisterBody;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.framework.web.service.SysRegisterService;
import com.ruoyi.system.service.ISysConfigService;
/**
* 注册验证
*
* @author ruoyi
*/
@RestController
public class SysRegisterController extends BaseController
{
@Autowired
private SysRegisterService registerService;
@Autowired
private ISysConfigService configService;
@PostMapping("/register")
public AjaxResult register(@RequestBody RegisterBody user)
{
if (!("true".equals(configService.selectConfigByKey("sys.account.registerUser"))))
{
return error("当前系统没有开启注册功能!");
}
String msg = registerService.register(user);
return StringUtils.isEmpty(msg) ? success() : error(msg);
}
}

View File

@@ -0,0 +1,295 @@
package com.ruoyi.web.controller.system;
import java.lang.reflect.Array;
import java.util.List;
import javax.servlet.http.HttpServletResponse;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysDept;
import com.ruoyi.common.core.domain.entity.SysRole;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.framework.web.service.SysPermissionService;
import com.ruoyi.framework.web.service.TokenService;
import com.ruoyi.system.domain.SysUserRole;
import com.ruoyi.system.service.ISysDeptService;
import com.ruoyi.system.service.ISysRoleService;
import com.ruoyi.system.service.ISysUserService;
/**
* 角色信息
*
* @author ruoyi
*/
@RestController
@RequestMapping("/system/role")
@Api("角色信息管理")
public class SysRoleController extends BaseController
{
@Autowired
private ISysRoleService roleService;
@Autowired
private TokenService tokenService;
@Autowired
private SysPermissionService permissionService;
@Autowired
private ISysUserService userService;
@Autowired
private ISysDeptService deptService;
@PreAuthorize("@ss.hasPermi('system:role:list')")
@GetMapping("/list")
@ApiOperation("获取角色列表")
public TableDataInfo list(SysRole role)
{
startPage();
List<SysRole> list = roleService.selectRoleList(role);
return getDataTable(list);
}
@Log(title = "角色管理", businessType = BusinessType.EXPORT)
@PreAuthorize("@ss.hasPermi('system:role:export')")
@PostMapping("/export")
public void export(HttpServletResponse response, SysRole role)
{
List<SysRole> list = roleService.selectRoleList(role);
ExcelUtil<SysRole> util = new ExcelUtil<SysRole>(SysRole.class);
util.exportExcel(response, list, "角色数据");
}
/**
* 根据角色编号获取详细信息
*/
@PreAuthorize("@ss.hasPermi('system:role:query')")
@GetMapping(value = "/{roleId}")
public AjaxResult getInfo(@PathVariable Long roleId)
{
roleService.checkRoleDataScope(roleId);
return success(roleService.selectRoleById(roleId));
}
/**
* 新增角色
*/
@PreAuthorize("@ss.hasPermi('system:role:add')")
@Log(title = "角色管理", businessType = BusinessType.INSERT)
@PostMapping
@ApiOperation("新增角色")
@ApiImplicitParams({
@ApiImplicitParam(name = "roleName", value = "角色名称", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "roleKey", value = "权限字符", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "description", value = "角色描述", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "status", value = "角色状态,0是启用,1是停用", dataType = "Integer", dataTypeClass = Integer.class),
@ApiImplicitParam(name = "roleSort", value = "角色顺序", dataType = "Integer", dataTypeClass = Integer.class),
@ApiImplicitParam(name = "menuIds", value = "菜单数组", dataType = "Integer[]", dataTypeClass = Array.class)
})
public AjaxResult add(@Validated @RequestBody SysRole role)
{
if (!roleService.checkRoleNameUnique(role))
{
return error("新增角色'" + role.getRoleName() + "'失败,角色名称已存在");
}
else if (!roleService.checkRoleKeyUnique(role))
{
return error("新增角色'" + role.getRoleName() + "'失败,角色权限已存在");
}
role.setCreateBy(getUsername());
return toAjax(roleService.insertRole(role));
}
/**
* 修改保存角色
*/
@PreAuthorize("@ss.hasPermi('system:role:edit')")
@Log(title = "角色管理", businessType = BusinessType.UPDATE)
@PutMapping
@ApiOperation("修改角色")
@ApiImplicitParams({
@ApiImplicitParam(name = "roleName", value = "角色名称", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "roleKey", value = "权限字符", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "description", value = "角色描述", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "status", value = "角色状态,0是启用,1是停用", dataType = "Integer", dataTypeClass = Integer.class),
@ApiImplicitParam(name = "roleSort", value = "角色顺序", dataType = "Integer", dataTypeClass = Integer.class),
@ApiImplicitParam(name = "menuIds", value = "菜单数组", dataType = "Integer[]", dataTypeClass = Array.class)
})
public AjaxResult edit(@Validated @RequestBody SysRole role)
{
roleService.checkRoleAllowed(role);
roleService.checkRoleDataScope(role.getRoleId());
if (!roleService.checkRoleNameUnique(role))
{
return error("修改角色'" + role.getRoleName() + "'失败,角色名称已存在");
}
else if (!roleService.checkRoleKeyUnique(role))
{
return error("修改角色'" + role.getRoleName() + "'失败,角色权限已存在");
}
role.setUpdateBy(getUsername());
if (roleService.updateRole(role) > 0)
{
// 更新缓存用户权限
LoginUser loginUser = getLoginUser();
if (StringUtils.isNotNull(loginUser.getUser()) && !loginUser.getUser().isAdmin())
{
loginUser.setPermissions(permissionService.getMenuPermission(loginUser.getUser()));
loginUser.setUser(userService.selectUserByUserName(loginUser.getUser().getUserName()));
tokenService.setLoginUser(loginUser);
}
return success();
}
return error("修改角色'" + role.getRoleName() + "'失败,请联系管理员");
}
/**
* 修改保存数据权限
*/
@PreAuthorize("@ss.hasPermi('system:role:edit')")
@Log(title = "角色管理", businessType = BusinessType.UPDATE)
@PutMapping("/dataScope")
public AjaxResult dataScope(@RequestBody SysRole role)
{
roleService.checkRoleAllowed(role);
roleService.checkRoleDataScope(role.getRoleId());
return toAjax(roleService.authDataScope(role));
}
/**
* 状态修改
*/
@PreAuthorize("@ss.hasPermi('system:role:edit')")
@Log(title = "角色管理", businessType = BusinessType.UPDATE)
@PutMapping("/changeStatus")
@ApiOperation("启用停用角色")
@ApiImplicitParams({
@ApiImplicitParam(name = "roleId", value = "角色id", dataType = "Integer", dataTypeClass = Integer.class),
@ApiImplicitParam(name = "status", value = "角色状态,0是启用,1是停用", dataType = "Integer", dataTypeClass = Integer.class),
})
public AjaxResult changeStatus(@RequestBody SysRole role)
{
roleService.checkRoleAllowed(role);
roleService.checkRoleDataScope(role.getRoleId());
role.setUpdateBy(getUsername());
return toAjax(roleService.updateRoleStatus(role));
}
/**
* 删除角色
*/
@PreAuthorize("@ss.hasPermi('system:role:remove')")
@Log(title = "角色管理", businessType = BusinessType.DELETE)
@DeleteMapping("/{roleIds}")
@ApiOperation("删除角色")
public AjaxResult remove(@PathVariable Long[] roleIds)
{
return toAjax(roleService.deleteRoleByIds(roleIds));
}
/**
* 获取角色选择框列表
*/
@PreAuthorize("@ss.hasPermi('system:role:query')")
@GetMapping("/optionselect")
public AjaxResult optionselect()
{
return success(roleService.selectRoleAll());
}
/**
* 查询已分配用户角色列表
*/
@PreAuthorize("@ss.hasPermi('system:role:list')")
@GetMapping("/authUser/allocatedList")
public TableDataInfo allocatedList(SysUser user)
{
startPage();
List<SysUser> list = userService.selectAllocatedList(user);
return getDataTable(list);
}
/**
* 查询未分配用户角色列表
*/
@PreAuthorize("@ss.hasPermi('system:role:list')")
@GetMapping("/authUser/unallocatedList")
public TableDataInfo unallocatedList(SysUser user)
{
startPage();
List<SysUser> list = userService.selectUnallocatedList(user);
return getDataTable(list);
}
/**
* 取消授权用户
*/
@PreAuthorize("@ss.hasPermi('system:role:edit')")
@Log(title = "角色管理", businessType = BusinessType.GRANT)
@PutMapping("/authUser/cancel")
public AjaxResult cancelAuthUser(@RequestBody SysUserRole userRole)
{
return toAjax(roleService.deleteAuthUser(userRole));
}
/**
* 批量取消授权用户
*/
@PreAuthorize("@ss.hasPermi('system:role:edit')")
@Log(title = "角色管理", businessType = BusinessType.GRANT)
@PutMapping("/authUser/cancelAll")
public AjaxResult cancelAuthUserAll(Long roleId, Long[] userIds)
{
return toAjax(roleService.deleteAuthUsers(roleId, userIds));
}
/**
* 批量选择用户授权
*/
@PreAuthorize("@ss.hasPermi('system:role:edit')")
@Log(title = "角色管理", businessType = BusinessType.GRANT)
@PutMapping("/authUser/selectAll")
public AjaxResult selectAuthUserAll(Long roleId, Long[] userIds)
{
roleService.checkRoleDataScope(roleId);
return toAjax(roleService.insertAuthUsers(roleId, userIds));
}
/**
* 获取对应角色部门树列表
*/
@PreAuthorize("@ss.hasPermi('system:role:query')")
@GetMapping(value = "/deptTree/{roleId}")
public AjaxResult deptTree(@PathVariable("roleId") Long roleId)
{
AjaxResult ajax = AjaxResult.success();
ajax.put("checkedKeys", deptService.selectDeptListByRoleId(roleId));
ajax.put("depts", deptService.selectDeptTreeList(new SysDept()));
return ajax;
}
}

View File

@@ -0,0 +1,351 @@
package com.ruoyi.web.controller.system;
import com.ruoyi.common.annotation.Log;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.SysDept;
import com.ruoyi.common.core.domain.entity.SysRole;
import com.ruoyi.common.core.domain.entity.SysUser;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.poi.ExcelUtil;
import com.ruoyi.system.domain.vo.FindUserVo;
import com.ruoyi.system.domain.vo.TreeUserVo;
import com.ruoyi.system.domain.vo.UserInfoVo;
import com.ruoyi.system.service.ISysDeptService;
import com.ruoyi.system.service.ISysPostService;
import com.ruoyi.system.service.ISysRoleService;
import com.ruoyi.system.service.ISysUserService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.commons.lang3.ArrayUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import javax.servlet.http.HttpServletResponse;
import java.util.List;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
/**
* 用户信息
*
* @author ruoyi
*/
@Api(tags = "用户管理")
@RestController
@RequestMapping("/system/user")
public class SysUserController extends BaseController
{
@Autowired
private ISysUserService userService;
@Autowired
private ISysRoleService roleService;
@Autowired
private ISysDeptService deptService;
@Autowired
private ISysPostService postService;
/**
* 获取用户列表
*/
@ApiOperation("根据条件获取用户列表")
@PreAuthorize("@ss.hasPermi('system:user:list')")
@GetMapping("/list")
public TableDataInfo list(SysUser user)
{
startPage();
List<SysUser> list = userService.selectUserList(user);
return getDataTable(list);
}
@Log(title = "用户管理", businessType = BusinessType.EXPORT)
@PreAuthorize("@ss.hasPermi('system:user:export')")
@PostMapping("/export")
public void export(HttpServletResponse response, SysUser user)
{
List<SysUser> list = userService.selectUserList(user);
ExcelUtil<SysUser> util = new ExcelUtil<SysUser>(SysUser.class);
util.exportExcel(response, list, "用户数据");
}
@Log(title = "用户管理", businessType = BusinessType.IMPORT)
@PreAuthorize("@ss.hasPermi('system:user:import')")
@PostMapping("/importData")
public AjaxResult importData(MultipartFile file, boolean updateSupport) throws Exception
{
ExcelUtil<SysUser> util = new ExcelUtil<SysUser>(SysUser.class);
List<SysUser> userList = util.importExcel(file.getInputStream());
String operName = getUsername();
String message = userService.importUser(userList, updateSupport, operName);
return success(message);
}
@PostMapping("/importTemplate")
public void importTemplate(HttpServletResponse response)
{
ExcelUtil<SysUser> util = new ExcelUtil<SysUser>(SysUser.class);
util.importTemplateExcel(response, "用户数据");
}
/**
* 根据用户编号获取详细信息
*/
@ApiOperation("根据用户编号获取详细信息")
@PreAuthorize("@ss.hasPermi('system:user:query')")
@GetMapping(value = { "/", "/{userId}" })
public AjaxResult getInfo(@PathVariable(value = "userId", required = false) Long userId)
{
userService.checkUserDataScope(userId);
AjaxResult ajax = AjaxResult.success();
List<SysRole> roles = roleService.selectRoleAll();
ajax.put("roles", SysUser.isAdmin(userId) ? roles : roles.stream().filter(r -> !r.isAdmin()).collect(Collectors.toList()));
ajax.put("posts", postService.selectPostAll(userId));
if (StringUtils.isNotNull(userId))
{
SysUser sysUser = userService.selectUserById(userId);
ajax.put(AjaxResult.DATA_TAG, sysUser);
ajax.put("postIds", postService.selectPostListByUserId(userId));
ajax.put("roleIds", sysUser.getRoles().stream().map(SysRole::getRoleId).collect(Collectors.toList()));
}
return ajax;
}
/**
* 新增用户
*/
@PreAuthorize("@ss.hasPermi('system:user:add')")
@Log(title = "用户管理", businessType = BusinessType.INSERT)
@PostMapping
public AjaxResult add(@Validated @RequestBody SysUser user)
{
deptService.checkDeptDataScope(user.getDeptId());
roleService.checkRoleDataScope(user.getRoleIds());
if (!userService.checkUserNameUnique(user))
{
return error("新增用户'" + user.getUserName() + "'失败,登录账号已存在");
}
else if (StringUtils.isNotEmpty(user.getPhonenumber()) && !userService.checkPhoneUnique(user))
{
return error("新增用户'" + user.getUserName() + "'失败,手机号码已存在");
}
else if (StringUtils.isNotEmpty(user.getEmail()) && !userService.checkEmailUnique(user))
{
return error("新增用户'" + user.getUserName() + "'失败,邮箱账号已存在");
}
Pattern PASSWORD_PATTERN = Pattern.compile("^(?:(?=.*[A-Z])(?=.*[a-z])(?=.*\\d)|(?=.*[A-Z])(?=.*[a-z])(?=.*[@#$%^&+=!])|(?=.*[A-Z])(?=.*\\d)(?=.*[@#$%^&+=!])|(?=.*[a-z])(?=.*\\d)(?=.*[@#$%^&+=!])).{8,}$");
if ( StringUtils.isNotEmpty(user.getPassword()) && !PASSWORD_PATTERN.matcher(user.getPassword()).matches())
{
return error("新密码长度需大于等于8位,且包含大小写、数字、特殊字符中的至少三种!");
}
user.setCreateBy(getUsername());
user.setPassword(SecurityUtils.encryptPassword(user.getPassword()));
return toAjax(userService.insertUser(user));
}
/**
* 修改用户
*/
@PreAuthorize("@ss.hasPermi('system:user:edit')")
@Log(title = "用户管理", businessType = BusinessType.UPDATE)
@PutMapping
public AjaxResult edit(@Validated @RequestBody SysUser user)
{
Long[] a ={user.getRoleId()};
user.setRoleIds(a);
if (StringUtils.isNotEmpty(user.getPassword())){
Pattern PASSWORD_PATTERN = Pattern.compile("^(?:(?=.*[A-Z])(?=.*[a-z])(?=.*\\d)|(?=.*[A-Z])(?=.*[a-z])(?=.*[@#$%^&+=!])|(?=.*[A-Z])(?=.*\\d)(?=.*[@#$%^&+=!])|(?=.*[a-z])(?=.*\\d)(?=.*[@#$%^&+=!])).{8,}$");
if ( StringUtils.isNotEmpty(user.getPassword()) && !PASSWORD_PATTERN.matcher(user.getPassword()).matches())
{
return error("新密码长度需大于等于8位,且包含大小写、数字、特殊字符中的至少三种!");
}
user.setPassword(SecurityUtils.encryptPassword(user.getPassword()));
}
userService.checkUserAllowed(user);
userService.checkUserDataScope(user.getUserId());
deptService.checkDeptDataScope(user.getDeptId());
roleService.checkRoleDataScope(user.getRoleIds());
if (!userService.checkUserNameUnique(user))
{
return error("修改用户'" + user.getUserName() + "'失败,登录账号已存在");
}
else if (StringUtils.isNotEmpty(user.getPhonenumber()) && !userService.checkPhoneUnique(user))
{
return error("修改用户'" + user.getUserName() + "'失败,手机号码已存在");
}
else if (StringUtils.isNotEmpty(user.getEmail()) && !userService.checkEmailUnique(user))
{
return error("修改用户'" + user.getUserName() + "'失败,邮箱账号已存在");
}
user.setUpdateBy(getUsername());
return toAjax(userService.updateUser(user));
}
/**
* 删除用户
*/
@PreAuthorize("@ss.hasPermi('system:user:remove')")
@Log(title = "用户管理", businessType = BusinessType.DELETE)
@DeleteMapping("/{userIds}")
public AjaxResult remove(@PathVariable Long[] userIds)
{
if (ArrayUtils.contains(userIds, getUserId()))
{
return error("当前用户不能删除");
}
return toAjax(userService.deleteUserByIds(userIds));
}
/**
* 重置密码
*/
@PreAuthorize("@ss.hasPermi('system:user:resetPwd')")
@Log(title = "用户管理", businessType = BusinessType.UPDATE)
@PutMapping("/resetPwd")
public AjaxResult resetPwd(@RequestBody SysUser user)
{
userService.checkUserAllowed(user);
userService.checkUserDataScope(user.getUserId());
Pattern PASSWORD_PATTERN = Pattern.compile("^(?:(?=.*[A-Z])(?=.*[a-z])(?=.*\\d)|(?=.*[A-Z])(?=.*[a-z])(?=.*[@#$%^&+=!])|(?=.*[A-Z])(?=.*\\d)(?=.*[@#$%^&+=!])|(?=.*[a-z])(?=.*\\d)(?=.*[@#$%^&+=!])).{8,}$");
if ( !PASSWORD_PATTERN.matcher(user.getPassword()).matches())
{
return error("新密码长度需大于等于8位,且包含大小写、数字、特殊字符中的至少三种!");
}
user.setPassword(SecurityUtils.encryptPassword(user.getPassword()));
user.setUpdateBy(getUsername());
return toAjax(userService.resetPwd(user));
}
/**
* 状态修改
*/
@PreAuthorize("@ss.hasPermi('system:user:edit')")
@Log(title = "用户管理", businessType = BusinessType.UPDATE)
@PutMapping("/changeStatus")
public AjaxResult changeStatus(@RequestBody SysUser user)
{
userService.checkUserAllowed(user);
userService.checkUserDataScope(user.getUserId());
user.setUpdateBy(getUsername());
return toAjax(userService.updateUserStatus(user));
}
/**
* 根据用户编号获取授权角色
*/
@PreAuthorize("@ss.hasPermi('system:user:query')")
@GetMapping("/authRole/{userId}")
public AjaxResult authRole(@PathVariable("userId") Long userId)
{
AjaxResult ajax = AjaxResult.success();
SysUser user = userService.selectUserById(userId);
List<SysRole> roles = roleService.selectRolesByUserId(userId);
ajax.put("user", user);
ajax.put("roles", SysUser.isAdmin(userId) ? roles : roles.stream().filter(r -> !r.isAdmin()).collect(Collectors.toList()));
return ajax;
}
/**
* 用户授权角色
*/
@PreAuthorize("@ss.hasPermi('system:user:edit')")
@Log(title = "用户管理", businessType = BusinessType.GRANT)
@PutMapping("/authRole")
public AjaxResult insertAuthRole(Long userId, Long[] roleIds)
{
userService.checkUserDataScope(userId);
roleService.checkRoleDataScope(roleIds);
userService.insertUserAuth(userId, roleIds);
return success();
}
/**
* 获取部门树列表
*/
//@PreAuthorize("@ss.hasPermi('system:user:list')")
@GetMapping("/deptTree")
public AjaxResult deptTree(SysDept dept)
{
return success(deptService.selectDeptTreeList(dept));
}
/**
* 获取部门树列表
*/
//@PreAuthorize("@ss.hasPermi('system:user:list')")
@GetMapping("/deptTree/all")
public AjaxResult allDeptTree()
{
return success(deptService.selectAllDeptTreeList());
}
/**
* 客户经理获取部门树列表
*/
//@PreAuthorize("@ss.hasPermi('system:user:list')")
@GetMapping("/deptTreeByManager")
public AjaxResult deptTreeByManager(SysDept dept)
{
return success(deptService.selectDeptTreeListByManager(dept));
}
/**
* 获取部门树列表
*/
@GetMapping("/deptTree/top")
public AjaxResult deptTreeForTopGrid(SysDept dept) {
return success(deptService.selectDeptTreeListForTopGrid(dept));
}
@ApiOperation("获取机构下客户经理")
@GetMapping("/treeUser")
@ResponseBody
public List<TreeUserVo> treeUser(Long deptid)
{
return userService.selectTreeUser(deptid);
}
@ApiOperation("获取全行下客户经理")
@GetMapping("/allTreeUser")
@ResponseBody
public List<TreeUserVo> allTreeUser()
{
return userService.selectAllTreeUser();
}
@ApiOperation("模糊查询客户经理")
@GetMapping("/findUser")
@ResponseBody
public List<FindUserVo> findUser(String input)
{
return userService.findUser(input);
}
@ApiOperation("模糊查询客户经理")
@GetMapping("/findUserDeptTree")
@ResponseBody
public List<FindUserVo> findUserDeptTree(String input)
{
return userService.findUserDeptTree(input);
}
@GetMapping("/getDeptName")
public AjaxResult deptTreeGetUser() {
UserInfoVo vo = new UserInfoVo();
vo.setUserName(SecurityUtils.getLoginUser().getUsername());
vo.setDeptId(SecurityUtils.getLoginUser().getDeptId());
vo.setDeptName(userService.getDeptName(SecurityUtils.getLoginUser().getDeptId()));
return success(vo);
}
}

View File

@@ -0,0 +1,183 @@
package com.ruoyi.web.controller.tool;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.ruoyi.common.core.controller.BaseController;
import com.ruoyi.common.core.domain.R;
import com.ruoyi.common.utils.StringUtils;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import io.swagger.annotations.ApiOperation;
/**
* swagger 用户测试方法
*
* @author ruoyi
*/
@RestController
@RequestMapping("/test/user")
public class TestController extends BaseController
{
private final static Map<Integer, UserEntity> users = new LinkedHashMap<Integer, UserEntity>();
{
users.put(1, new UserEntity(1, "admin", "admin123", "15888888888"));
users.put(2, new UserEntity(2, "ry", "admin123", "15666666666"));
}
@ApiOperation("获取用户列表")
@GetMapping("/list")
public R<List<UserEntity>> userList()
{
List<UserEntity> userList = new ArrayList<UserEntity>(users.values());
return R.ok(userList);
}
@ApiOperation("获取用户详细")
@ApiImplicitParam(name = "userId", value = "用户ID", required = true, dataType = "int", paramType = "path", dataTypeClass = Integer.class)
@GetMapping("/{userId}")
public R<UserEntity> getUser(@PathVariable Integer userId)
{
if (!users.isEmpty() && users.containsKey(userId))
{
return R.ok(users.get(userId));
}
else
{
return R.fail("用户不存在");
}
}
@ApiOperation("新增用户")
@ApiImplicitParams({
@ApiImplicitParam(name = "userId", value = "用户id", dataType = "Integer", dataTypeClass = Integer.class),
@ApiImplicitParam(name = "username", value = "用户名称", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "password", value = "用户密码", dataType = "String", dataTypeClass = String.class),
@ApiImplicitParam(name = "mobile", value = "用户手机", dataType = "String", dataTypeClass = String.class)
})
@PostMapping("/save")
public R<String> save(UserEntity user)
{
if (StringUtils.isNull(user) || StringUtils.isNull(user.getUserId()))
{
return R.fail("用户ID不能为空");
}
users.put(user.getUserId(), user);
return R.ok();
}
@ApiOperation("更新用户")
@PutMapping("/update")
public R<String> update(@RequestBody UserEntity user)
{
if (StringUtils.isNull(user) || StringUtils.isNull(user.getUserId()))
{
return R.fail("用户ID不能为空");
}
if (users.isEmpty() || !users.containsKey(user.getUserId()))
{
return R.fail("用户不存在");
}
users.remove(user.getUserId());
users.put(user.getUserId(), user);
return R.ok();
}
@ApiOperation("删除用户信息")
@ApiImplicitParam(name = "userId", value = "用户ID", required = true, dataType = "int", paramType = "path", dataTypeClass = Integer.class)
@DeleteMapping("/{userId}")
public R<String> delete(@PathVariable Integer userId)
{
if (!users.isEmpty() && users.containsKey(userId))
{
users.remove(userId);
return R.ok();
}
else
{
return R.fail("用户不存在");
}
}
}
@ApiModel(value = "UserEntity", description = "用户实体")
class UserEntity
{
@ApiModelProperty("用户ID")
private Integer userId;
@ApiModelProperty("用户名称")
private String username;
@ApiModelProperty("用户密码")
private String password;
@ApiModelProperty("用户手机")
private String mobile;
public UserEntity()
{
}
public UserEntity(Integer userId, String username, String password, String mobile)
{
this.userId = userId;
this.username = username;
this.password = password;
this.mobile = mobile;
}
public Integer getUserId()
{
return userId;
}
public void setUserId(Integer userId)
{
this.userId = userId;
}
public String getUsername()
{
return username;
}
public void setUsername(String username)
{
this.username = username;
}
public String getPassword()
{
return password;
}
public void setPassword(String password)
{
this.password = password;
}
public String getMobile()
{
return mobile;
}
public void setMobile(String mobile)
{
this.mobile = mobile;
}
}

View File

@@ -0,0 +1,125 @@
package com.ruoyi.web.core.config;
import java.util.ArrayList;
import java.util.List;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import com.ruoyi.common.config.RuoYiConfig;
import io.swagger.annotations.ApiOperation;
import io.swagger.models.auth.In;
import springfox.documentation.builders.ApiInfoBuilder;
import springfox.documentation.builders.PathSelectors;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.service.ApiKey;
import springfox.documentation.service.AuthorizationScope;
import springfox.documentation.service.Contact;
import springfox.documentation.service.SecurityReference;
import springfox.documentation.service.SecurityScheme;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spi.service.contexts.SecurityContext;
import springfox.documentation.spring.web.plugins.Docket;
/**
* Swagger2的接口配置
*
* @author ruoyi
*/
@Configuration
public class SwaggerConfig
{
/** 系统基础配置 */
@Autowired
private RuoYiConfig ruoyiConfig;
/** 是否开启swagger */
@Value("${swagger.enabled}")
private boolean enabled;
/** 设置请求的统一前缀 */
@Value("${swagger.pathMapping}")
private String pathMapping;
/**
* 创建API
*/
@Bean
public Docket createRestApi()
{
return new Docket(DocumentationType.OAS_30)
// 是否启用Swagger
.enable(enabled)
// 用来创建该API的基本信息展示在文档的页面中自定义展示的信息
.apiInfo(apiInfo())
// 设置哪些接口暴露给Swagger展示
.select()
// 扫描所有有注解的api用这种方式更灵活
.apis(RequestHandlerSelectors.withMethodAnnotation(ApiOperation.class))
// 扫描指定包中的swagger注解
// .apis(RequestHandlerSelectors.basePackage("com.ruoyi.project.tool.swagger"))
// 扫描所有 .apis(RequestHandlerSelectors.any())
.paths(PathSelectors.any())
.build()
/* 设置安全模式swagger可以设置访问token */
.securitySchemes(securitySchemes())
.securityContexts(securityContexts())
.pathMapping(pathMapping);
}
/**
* 安全模式这里指定token通过Authorization头请求头传递
*/
private List<SecurityScheme> securitySchemes()
{
List<SecurityScheme> apiKeyList = new ArrayList<SecurityScheme>();
apiKeyList.add(new ApiKey("Authorization", "Authorization", In.HEADER.toValue()));
return apiKeyList;
}
/**
* 安全上下文
*/
private List<SecurityContext> securityContexts()
{
List<SecurityContext> securityContexts = new ArrayList<>();
securityContexts.add(
SecurityContext.builder()
.securityReferences(defaultAuth())
.operationSelector(o -> o.requestMappingPattern().matches("/.*"))
.build());
return securityContexts;
}
/**
* 默认的安全上引用
*/
private List<SecurityReference> defaultAuth()
{
AuthorizationScope authorizationScope = new AuthorizationScope("global", "accessEverything");
AuthorizationScope[] authorizationScopes = new AuthorizationScope[1];
authorizationScopes[0] = authorizationScope;
List<SecurityReference> securityReferences = new ArrayList<>();
securityReferences.add(new SecurityReference("Authorization", authorizationScopes));
return securityReferences;
}
/**
* 添加摘要信息
*/
private ApiInfo apiInfo()
{
// 用ApiInfoBuilder进行定制
return new ApiInfoBuilder()
// 设置标题
.title("标题若依管理系统_接口文档")
// 描述
.description("描述:用于管理集团旗下公司的人员信息,具体包括XXX,XXX模块...")
// 作者信息
.contact(new Contact(ruoyiConfig.getName(), null, null))
// 版本
.version("版本号:" + ruoyiConfig.getVersion())
.build();
}
}

View File

@@ -0,0 +1 @@
restart.include.json=/com.alibaba.fastjson2.*.jar

View File

@@ -0,0 +1,121 @@
# 开发环境配置
server:
# 服务器的HTTP端口默认为8080
port: 8080
servlet:
# 应用的访问路径
context-path: /
tomcat:
# tomcat的URI编码
uri-encoding: UTF-8
# 连接数满后的排队数默认为100
accept-count: 1000
threads:
# tomcat最大线程数默认为200
max: 800
# Tomcat启动初始化的线程数默认值10
min-spare: 100
spring:
datasource:
type: com.alibaba.druid.pool.DruidDataSource
driverClassName: com.mysql.cj.jdbc.Driver
druid:
# 主库数据源
master:
url: jdbc:mysql://158.234.199.250:3306/ibs_pre?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&allowMultiQueries=true
username: db2icm
password: Kfcx@1234
# 从库数据源
slave:
# 从数据源开关/默认关闭
enabled: false
url:
username:
password:
# 初始连接数
initialSize: 5
# 最小连接池数量
minIdle: 10
# 最大连接池数量
maxActive: 20
# 配置获取连接等待超时的时间
maxWait: 60000
# 配置连接超时时间
connectTimeout: 30000
# 配置网络超时时间
socketTimeout: 60000
# 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒
timeBetweenEvictionRunsMillis: 60000
# 配置一个连接在池中最小生存的时间,单位是毫秒
minEvictableIdleTimeMillis: 300000
# 配置一个连接在池中最大生存的时间,单位是毫秒
maxEvictableIdleTimeMillis: 900000
# 配置检测连接是否有效
validationQuery: SELECT 1 FROM DUAL
testWhileIdle: true
testOnBorrow: false
testOnReturn: false
webStatFilter:
enabled: true
statViewServlet:
enabled: true
# 设置白名单,不填则允许所有访问
allow:
url-pattern: /druid/*
# 控制台管理用户名和密码
login-username: ruoyi
login-password: 123456
filter:
stat:
enabled: true
# 慢SQL记录
log-slow-sql: true
slow-sql-millis: 1000
merge-sql: true
wall:
config:
multi-statement-allow: true
redis:
# 地址
host: r-kz640f6b20dac724.redis.rds.ops.dc-tst-zj96596.com
# 端口默认为6379
port: 6379
# 数据库索引
database: 0
# 密码
password: ibs_pre:Kfcx@1234
# 连接超时时间
timeout: 10s
lettuce:
pool:
# 连接池中的最小空闲连接
min-idle: 0
# 连接池中的最大空闲连接
max-idle: 8
# 连接池的最大数据库连接数
max-active: 8
# #连接池最大阻塞等待时间(使用负值表示没有限制)
max-wait: -1ms
# Swagger配置
swagger:
# 是否开启swagger
enabled: true
# 请求前缀
pathMapping: /
baidu:
ak: L7KaAZUYPVSD40nYT09rWWgIdZKUesiX
geocoding-url: http://158.234.96.76:5001/geocoding/v3
place-search-url: http://158.234.96.76:5001/place/v2/search
qxhy:
url: http://158.234.196.4:5002
bi:
url: http://158.220.52.42:9388/bi
sysFlag: pre_dev
qingtian:
ip: http://64.154.7.178:8000

View File

@@ -0,0 +1,114 @@
# 开发环境配置
server:
# 服务器的HTTP端口默认为8080
port: 18010
servlet:
# 应用的访问路径
context-path: /
tomcat:
# tomcat的URI编码
uri-encoding: UTF-8
# 连接数满后的排队数默认为100
accept-count: 1000
threads:
# tomcat最大线程数默认为200
max: 800
# Tomcat启动初始化的线程数默认值10
min-spare: 100
spring:
datasource:
type: com.alibaba.druid.pool.DruidDataSource
driverClassName: com.mysql.cj.jdbc.Driver
druid:
# 主库数据源
master:
url: jdbc:mysql://64.201.30.46:3306/ibs?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&allowMultiQueries=true
username: db2icm
password: SZZHFZGLXT@jjj2024
# 从库数据源
slave:
# 从数据源开关/默认关闭
enabled: false
url:
username:
password:
# 初始连接数
initialSize: 5
# 最小连接池数量
minIdle: 10
# 最大连接池数量
maxActive: 20
# 配置获取连接等待超时的时间
maxWait: 60000
# 配置连接超时时间
connectTimeout: 30000
# 配置网络超时时间
socketTimeout: 60000
# 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒
timeBetweenEvictionRunsMillis: 60000
# 配置一个连接在池中最小生存的时间,单位是毫秒
minEvictableIdleTimeMillis: 300000
# 配置一个连接在池中最大生存的时间,单位是毫秒
maxEvictableIdleTimeMillis: 900000
# 配置检测连接是否有效
validationQuery: SELECT 1 FROM DUAL
testWhileIdle: true
testOnBorrow: false
testOnReturn: false
webStatFilter:
enabled: true
statViewServlet:
enabled: true
# 设置白名单,不填则允许所有访问
allow:
url-pattern: /druid/*
# 控制台管理用户名和密码
login-username: ruoyi
login-password: 123456
filter:
stat:
enabled: true
# 慢SQL记录
log-slow-sql: true
slow-sql-millis: 1000
merge-sql: true
wall:
config:
multi-statement-allow: true
redis:
# 地址
host: r-df5a65a2620cc3b4.redis.rds.ops.dc-pdt-zj96596.com
# 端口默认为6379
port: 6379
# 数据库索引
database: 0
# 密码
password: SZZHFZGLXT@zy2024
# 连接超时时间
timeout: 10s
lettuce:
pool:
# 连接池中的最小空闲连接
min-idle: 0
# 连接池中的最大空闲连接
max-idle: 8
# 连接池的最大数据库连接数
max-active: 8
# #连接池最大阻塞等待时间(使用负值表示没有限制)
max-wait: -1ms
# Swagger配置
swagger:
# 是否开启swagger
enabled: true
# 请求前缀
pathMapping: /
rate-pricing:
oa-url: http://64.202.32.20:18011
model-url: http://64.202.32.40:8083/api/service/interface/invokeService/ldfdbp
application-submit-url: /api/rate/applicationSubmit
pricing-result-url: /api/rate/pricingResult
pool-balance-url: /api/rate/poolBalance
get-application-url: /api/rate/getApplication

View File

@@ -0,0 +1,118 @@
# 开发环境配置
server:
# 服务器的HTTP端口默认为8080
port: 18010
servlet:
# 应用的访问路径
context-path: /
tomcat:
# tomcat的URI编码
uri-encoding: UTF-8
# 连接数满后的排队数默认为100
accept-count: 1000
threads:
# tomcat最大线程数默认为200
max: 800
# Tomcat启动初始化的线程数默认值10
min-spare: 100
spring:
datasource:
type: com.alibaba.druid.pool.DruidDataSource
driverClassName: com.mysql.cj.jdbc.Driver
druid:
# 主库数据源
master:
url: jdbc:mysql://158.234.96.113:3306/ibs?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&allowMultiQueries=true
username: db2icm
password: Kfcx@1234
driverClassName: com.mysql.cj.jdbc.Driver
# 从库数据源
slave:
# 从数据源开关/默认关闭
enabled: false
url: jdbc:postgresql://158.226.93.154:80/rt_flink?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&allowMultiQueries=true
username: GVUYmFEBI49wgPi8
password: PJNVm3RYHVjb5MLsoa1qZvUEvYmJn4
driverClassName: org.postgresql.Driver
# 初始连接数
initialSize: 5
# 最小连接池数量
minIdle: 10
# 最大连接池数量
maxActive: 20
# 配置获取连接等待超时的时间
maxWait: 60000
# 配置连接超时时间
connectTimeout: 30000
# 配置网络超时时间
socketTimeout: 60000
# 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒
timeBetweenEvictionRunsMillis: 60000
# 配置一个连接在池中最小生存的时间,单位是毫秒
minEvictableIdleTimeMillis: 300000
# 配置一个连接在池中最大生存的时间,单位是毫秒
maxEvictableIdleTimeMillis: 900000
# 配置检测连接是否有效
validationQuery: SELECT 1 FROM DUAL
testWhileIdle: true
testOnBorrow: false
testOnReturn: false
webStatFilter:
enabled: true
statViewServlet:
enabled: true
# 设置白名单,不填则允许所有访问
allow:
url-pattern: /druid/*
# 控制台管理用户名和密码
login-username: ruoyi
login-password: 123456
filter:
stat:
enabled: true
# 慢SQL记录
log-slow-sql: true
slow-sql-millis: 1000
merge-sql: true
wall:
config:
multi-statement-allow: true
redis:
# 地址
host: r-kz6b0ffa25687624.redis.rds.ops.dc-tst-zj96596.com
# 端口默认为6379
port: 6379
# 数据库索引
database: 0
# 密码
password: ibs_uat:Kfcx@1234
# 连接超时时间
timeout: 10s
lettuce:
pool:
# 连接池中的最小空闲连接
min-idle: 0
# 连接池中的最大空闲连接
max-idle: 8
# 连接池的最大数据库连接数
max-active: 8
# #连接池最大阻塞等待时间(使用负值表示没有限制)
max-wait: -1ms
# Swagger配置
swagger:
# 是否开启swagger
enabled: true
# 请求前缀
pathMapping: /
rate-pricing:
oa-url: http://localhost:18010
model-url: http://localhost:18010/rate/pricing/mock/invokeModel
application-submit-url: /rate/pricing/mock/submit/application
pricing-result-url: /rate/pricing/mock/submit/result
pool-balance-url: /rate/pricing/mock/pool/balance
get-application-url: /rate/pricing/mock/application

View File

@@ -0,0 +1,93 @@
# 项目相关配置
ruoyi:
# 名称
name: RuoYi
# 版本
version: 3.8.8
# 版权年份
copyrightYear: 2024
# 文件路径 示例( Windows配置D:/ruoyi/uploadPathLinux配置 /home/ruoyi/uploadPath
profile: D:/ruoyi/uploadPath
linuxProfile: /home/webapp/ruoyi/files/
windowsProfile: D:/ruoyi/files/
# 获取ip地址开关
addressEnabled: false
# 验证码类型 math 数字计算 char 字符验证
captchaType: math
downloadProductManualPath: /home/webapp/ruoyi/shouce/
productManualfileName: szzhcaozuoshouce.docx
# 日志配置
logging:
level:
com.ruoyi: debug
org.springframework: warn
# 用户配置
user:
password:
# 密码最大错误次数
maxRetryCount: 5
# 密码锁定时间默认10分钟
lockTime: 10
# Spring配置
spring:
# 资源信息
messages:
# 国际化资源文件路径
basename: i18n/messages
profiles:
active: uat
# 文件上传
servlet:
multipart:
# 单个文件大小
max-file-size: 10MB
# 设置总上传的文件大小
max-request-size: 20MB
# 服务模块
devtools:
restart:
# 热部署开关
enabled: false
# token配置
token:
# 令牌自定义标识
header: Authorization
# 令牌密钥
secret: abcdefghijklmnopqrstuvwxyz
# 令牌有效期默认30分钟
expireTime: 3000
# MyBatis Plus配置
mybatis-plus:
# 搜索指定包别名
typeAliasesPackage: com.ruoyi.**.domain
# 配置mapper的扫描找到所有的mapper.xml映射文件
mapperLocations: classpath*:mapper/**/*Mapper.xml
# 加载全局的配置文件
configLocation: classpath:mybatis/mybatis-config.xml
type-handlers-package: com.ruoyi.ibs.handler
# PageHelper分页插件
pagehelper:
helperDialect: mysql
supportMethodsArguments: true
params: count=countSql
# 防止XSS攻击
xss:
# 过滤开关
enabled: true
# 排除链接(多个用逗号分隔)
excludes: /system/notice
# 匹配链接
urlPatterns: /system/*,/monitor/*,/tool/*

View File

@@ -0,0 +1,24 @@
Application Version: ${ruoyi.version}
Spring Boot Version: ${spring-boot.version}
////////////////////////////////////////////////////////////////////
// _ooOoo_ //
// o8888888o //
// 88" . "88 //
// (| ^_^ |) //
// O\ = /O //
// ____/`---'\____ //
// .' \\| |// `. //
// / \\||| : |||// \ //
// / _||||| -:- |||||- \ //
// | | \\\ - /// | | //
// | \_| ''\---/'' | | //
// \ .-\__ `-` ___/-. / //
// ___`. .' /--.--\ `. . ___ //
// ."" '< `.___\_<|>_/___.' >'"". //
// | | : `- \`.;`\ _ /`;.`/ - ` : | | //
// \ \ `-. \_ __\ /__ _/ .-` / / //
// ========`-.____`-.___\_____/___.-`____.-'======== //
// `=---=' //
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ //
// 佛祖保佑 永不宕机 永无BUG //
////////////////////////////////////////////////////////////////////

View File

@@ -0,0 +1,38 @@
#错误消息
not.null=* 必须填写
user.jcaptcha.error=验证码错误
user.jcaptcha.expire=验证码已失效
user.not.exists=用户不存在/密码错误
user.password.not.match=用户不存在/密码错误
user.password.retry.limit.count=密码输入错误{0}次
user.password.retry.limit.exceed=密码输入错误{0}次,帐户锁定{1}分钟
user.password.delete=对不起,您的账号已被删除
user.blocked=用户已封禁,请联系管理员
role.blocked=角色已封禁,请联系管理员
login.blocked=很遗憾访问IP已被列入系统黑名单
user.logout.success=退出成功
length.not.valid=长度必须在{min}到{max}个字符之间
user.username.not.valid=* 2到20个汉字、字母、数字或下划线组成且必须以非数字开头
user.password.not.valid=* 5-50个字符
user.email.not.valid=邮箱格式错误
user.mobile.phone.number.not.valid=手机号格式错误
user.login.success=登录成功
user.register.success=注册成功
user.notfound=请重新登录
user.forcelogout=管理员强制退出,请重新登录
user.unknown.error=未知错误,请重新登录
##文件上传消息
upload.exceed.maxSize=上传的文件大小超出限制的文件大小!<br/>允许的文件最大大小是:{0}MB
upload.filename.exceed.length=上传的文件名最长{0}个字符
##权限
no.permission=您没有数据的权限,请联系管理员添加权限 [{0}]
no.create.permission=您没有创建数据的权限,请联系管理员添加权限 [{0}]
no.update.permission=您没有修改数据的权限,请联系管理员添加权限 [{0}]
no.delete.permission=您没有删除数据的权限,请联系管理员添加权限 [{0}]
no.export.permission=您没有导出数据的权限,请联系管理员添加权限 [{0}]
no.view.permission=您没有查看数据的权限,请联系管理员添加权限 [{0}]

View File

@@ -0,0 +1,93 @@
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<!-- 日志存放路径 -->
<property name="log.path" value="/home/webapp/backend/ruoyi/logs" />
<!-- 日志输出格式 -->
<property name="log.pattern" value="%d{HH:mm:ss.SSS} [%thread] %-5level %logger{20} - [%method,%line] - %msg%n" />
<!-- 控制台输出 -->
<appender name="console" class="ch.qos.logback.core.ConsoleAppender">
<encoder>
<pattern>${log.pattern}</pattern>
</encoder>
</appender>
<!-- 系统日志输出 -->
<appender name="file_info" class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${log.path}/sys-info.log</file>
<!-- 循环政策:基于时间创建日志文件 -->
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<!-- 日志文件名格式 -->
<fileNamePattern>${log.path}/sys-info.%d{yyyy-MM-dd}.log</fileNamePattern>
<!-- 日志最大的历史 60天 -->
<maxHistory>60</maxHistory>
</rollingPolicy>
<encoder>
<pattern>${log.pattern}</pattern>
</encoder>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<!-- 过滤的级别 -->
<level>INFO</level>
<!-- 匹配时的操作:接收(记录) -->
<onMatch>ACCEPT</onMatch>
<!-- 不匹配时的操作:拒绝(不记录) -->
<onMismatch>DENY</onMismatch>
</filter>
</appender>
<appender name="file_error" class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${log.path}/sys-error.log</file>
<!-- 循环政策:基于时间创建日志文件 -->
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<!-- 日志文件名格式 -->
<fileNamePattern>${log.path}/sys-error.%d{yyyy-MM-dd}.log</fileNamePattern>
<!-- 日志最大的历史 60天 -->
<maxHistory>60</maxHistory>
</rollingPolicy>
<encoder>
<pattern>${log.pattern}</pattern>
</encoder>
<filter class="ch.qos.logback.classic.filter.LevelFilter">
<!-- 过滤的级别 -->
<level>ERROR</level>
<!-- 匹配时的操作:接收(记录) -->
<onMatch>ACCEPT</onMatch>
<!-- 不匹配时的操作:拒绝(不记录) -->
<onMismatch>DENY</onMismatch>
</filter>
</appender>
<!-- 用户访问日志输出 -->
<appender name="sys-user" class="ch.qos.logback.core.rolling.RollingFileAppender">
<file>${log.path}/sys-user.log</file>
<rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
<!-- 按天回滚 daily -->
<fileNamePattern>${log.path}/sys-user.%d{yyyy-MM-dd}.log</fileNamePattern>
<!-- 日志最大的历史 60天 -->
<maxHistory>60</maxHistory>
</rollingPolicy>
<encoder>
<pattern>${log.pattern}</pattern>
</encoder>
</appender>
<!-- 系统模块日志级别控制 -->
<logger name="com.ruoyi" level="info" />
<!-- Spring日志级别控制 -->
<logger name="org.springframework" level="warn" />
<root level="info">
<appender-ref ref="console" />
</root>
<!--系统操作日志-->
<root level="info">
<appender-ref ref="file_info" />
<appender-ref ref="file_error" />
</root>
<!--系统用户操作日志-->
<logger name="sys-user" level="info">
<appender-ref ref="sys-user"/>
</logger>
</configuration>

View File

@@ -0,0 +1,22 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE configuration
PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-config.dtd">
<configuration>
<!-- 全局参数 -->
<settings>
<!-- 使全局的映射器启用或禁用缓存 -->
<setting name="cacheEnabled" value="true" />
<!-- 允许JDBC 支持自动生成主键 -->
<setting name="useGeneratedKeys" value="true" />
<!-- 配置默认的执行器.SIMPLE就是普通执行器;REUSE执行器会重用预处理语句(prepared statements);BATCH执行器将重用语句并执行批量更新 -->
<setting name="defaultExecutorType" value="SIMPLE" />
<!-- 指定 MyBatis 所用日志的具体实现 -->
<setting name="logImpl" value="SLF4J" />
<!-- 使用驼峰命名法转换字段 -->
<setting name="mapUnderscoreToCamelCase" value="true"/>
<!-- 开启二级缓存 -->
<!-- <setting name="cacheEnabled" value="true"/>-->
</settings>
</configuration>

169
ruoyi-common/pom.xml Normal file
View File

@@ -0,0 +1,169 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<parent>
<artifactId>ruoyi</artifactId>
<groupId>com.ruoyi</groupId>
<version>3.8.8</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<artifactId>ruoyi-common</artifactId>
<description>
common通用工具
</description>
<dependencies>
<dependency>
<groupId>net.coobird</groupId>
<artifactId>thumbnailator</artifactId>
<version>0.4.13</version>
</dependency>
<!-- Spring框架基本的核心工具 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
</dependency>
<!-- SpringWeb模块 -->
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
</dependency>
<!-- spring security 安全认证 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<!-- pagehelper 分页插件 -->
<dependency>
<groupId>com.github.pagehelper</groupId>
<artifactId>pagehelper-spring-boot-starter</artifactId>
</dependency>
<!-- 自定义验证注解 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
</dependency>
<dependency>
<groupId>com.aliyun.oss</groupId>
<artifactId>aliyun-sdk-oss</artifactId>
<version>3.13.2</version>
</dependency>
<!--常用工具类 -->
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-lang3</artifactId>
</dependency>
<!-- JSON工具类 -->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
</dependency>
<!-- 阿里JSON解析器 -->
<dependency>
<groupId>com.alibaba.fastjson2</groupId>
<artifactId>fastjson2</artifactId>
</dependency>
<!-- io常用工具类 -->
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
</dependency>
<!-- excel工具 -->
<dependency>
<groupId>org.apache.poi</groupId>
<artifactId>poi-ooxml</artifactId>
</dependency>
<!-- easyexcel -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>easyexcel</artifactId>
</dependency>
<!-- websocket -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-websocket</artifactId>
</dependency>
<!-- yml解析器 -->
<dependency>
<groupId>org.yaml</groupId>
<artifactId>snakeyaml</artifactId>
</dependency>
<!-- Token生成与解析-->
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
</dependency>
<!-- Jaxb -->
<dependency>
<groupId>javax.xml.bind</groupId>
<artifactId>jaxb-api</artifactId>
</dependency>
<!-- redis 缓存操作 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<!-- pool 对象池 -->
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-pool2</artifactId>
</dependency>
<!-- 解析客户端操作系统、浏览器等 -->
<dependency>
<groupId>eu.bitwalker</groupId>
<artifactId>UserAgentUtils</artifactId>
</dependency>
<!-- servlet包 -->
<dependency>
<groupId>javax.servlet</groupId>
<artifactId>javax.servlet-api</artifactId>
</dependency>
<!-- mybatis-plus 增强CRUD -->
<dependency>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-boot-starter</artifactId>
<version>3.5.1</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
<dependency>
<groupId>io.swagger</groupId>
<artifactId>swagger-annotations</artifactId>
<version>1.6.2</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>5.3.28</version>
</dependency>
</dependencies>
</project>

View File

@@ -0,0 +1,19 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 匿名访问不鉴权注解
*
* @author ruoyi
*/
@Target({ ElementType.METHOD, ElementType.TYPE })
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Anonymous
{
}

View File

@@ -0,0 +1,43 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 数据权限过滤注解
*
* @author ruoyi
*/
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface DataScope
{
/**
* 部门表的别名
*/
public String deptAlias() default "";
/**
* 部门表dept_id的别名
*/
public String deptIdAlias() default "dept_id";
/**
* 用户表的别名
*/
public String userAlias() default "";
/**
* 用户表user_id的别名
*/
public String userIdAlias() default "user_id";
/**
* 权限字符(用于多个角色匹配符合要求的权限)默认根据权限注解@ss获取多个权限用逗号分隔开来
*/
public String permission() default "";
}

View File

@@ -0,0 +1,28 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import com.ruoyi.common.enums.DataSourceType;
/**
* 自定义多数据源切换注解
*
* 优先级:先方法,后类,如果方法覆盖了类上的数据源类型,以方法的为准,否则以类上的为准
*
* @author ruoyi
*/
@Target({ ElementType.METHOD, ElementType.TYPE })
@Retention(RetentionPolicy.RUNTIME)
@Documented
@Inherited
public @interface DataSource
{
/**
* 切换数据源名称
*/
public DataSourceType value() default DataSourceType.MASTER;
}

View File

@@ -0,0 +1,192 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import java.math.BigDecimal;
import org.apache.poi.ss.usermodel.HorizontalAlignment;
import org.apache.poi.ss.usermodel.IndexedColors;
import com.ruoyi.common.utils.poi.ExcelHandlerAdapter;
/**
* 自定义导出Excel数据注解
*
* @author ruoyi
*/
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.FIELD)
public @interface Excel
{
/**
* 导出时在excel中排序
*/
public int sort() default Integer.MAX_VALUE;
/**
* 导出到Excel中的名字.
*/
public String name() default "";
/**
* 日期格式, 如: yyyy-MM-dd
*/
public String dateFormat() default "";
/**
* 如果是字典类型请设置字典的type值 (如: sys_user_sex)
*/
public String dictType() default "";
/**
* 读取内容转表达式 (如: 0=男,1=女,2=未知)
*/
public String readConverterExp() default "";
/**
* 分隔符,读取字符串组内容
*/
public String separator() default ",";
/**
* BigDecimal 精度 默认:-1(默认不开启BigDecimal格式化)
*/
public int scale() default -1;
/**
* BigDecimal 舍入规则 默认:BigDecimal.ROUND_HALF_EVEN
*/
public int roundingMode() default BigDecimal.ROUND_HALF_EVEN;
/**
* 导出时在excel中每个列的高度
*/
public double height() default 14;
/**
* 导出时在excel中每个列的宽度
*/
public double width() default 16;
/**
* 文字后缀,如% 90 变成90%
*/
public String suffix() default "";
/**
* 当值为空时,字段的默认值
*/
public String defaultValue() default "";
/**
* 提示信息
*/
public String prompt() default "";
/**
* 设置只能选择不能输入的列内容.
*/
public String[] combo() default {};
/**
* 是否从字典读数据到combo,默认不读取,如读取需要设置dictType注解.
*/
public boolean comboReadDict() default false;
/**
* 是否需要纵向合并单元格,应对需求:含有list集合单元格)
*/
public boolean needMerge() default false;
/**
* 是否导出数据,应对需求:有时我们需要导出一份模板,这是标题需要但内容需要用户手工填写.
*/
public boolean isExport() default true;
/**
* 另一个类中的属性名称,支持多级获取,以小数点隔开
*/
public String targetAttr() default "";
/**
* 是否自动统计数据,在最后追加一行统计数据总和
*/
public boolean isStatistics() default false;
/**
* 导出类型0数字 1字符串 2图片
*/
public ColumnType cellType() default ColumnType.STRING;
/**
* 导出列头背景颜色
*/
public IndexedColors headerBackgroundColor() default IndexedColors.GREY_50_PERCENT;
/**
* 导出列头字体颜色
*/
public IndexedColors headerColor() default IndexedColors.WHITE;
/**
* 导出单元格背景颜色
*/
public IndexedColors backgroundColor() default IndexedColors.WHITE;
/**
* 导出单元格字体颜色
*/
public IndexedColors color() default IndexedColors.BLACK;
/**
* 导出字段对齐方式
*/
public HorizontalAlignment align() default HorizontalAlignment.CENTER;
/**
* 自定义数据处理器
*/
public Class<?> handler() default ExcelHandlerAdapter.class;
/**
* 自定义数据处理器参数
*/
public String[] args() default {};
/**
* 字段类型0导出导入1仅导出2仅导入
*/
Type type() default Type.ALL;
public enum Type
{
ALL(0), EXPORT(1), IMPORT(2);
private final int value;
Type(int value)
{
this.value = value;
}
public int value()
{
return this.value;
}
}
public enum ColumnType
{
NUMERIC(0), STRING(1), IMAGE(2), TEXT(3);
private final int value;
ColumnType(int value)
{
this.value = value;
}
public int value()
{
return this.value;
}
}
}

View File

@@ -0,0 +1,18 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* Excel注解集
*
* @author ruoyi
*/
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Excels
{
public Excel[] value();
}

View File

@@ -0,0 +1,51 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import com.ruoyi.common.enums.BusinessType;
import com.ruoyi.common.enums.OperatorType;
/**
* 自定义操作日志记录注解
*
* @author ruoyi
*
*/
@Target({ ElementType.PARAMETER, ElementType.METHOD })
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface Log
{
/**
* 模块
*/
public String title() default "";
/**
* 功能
*/
public BusinessType businessType() default BusinessType.OTHER;
/**
* 操作人类别
*/
public OperatorType operatorType() default OperatorType.MANAGE;
/**
* 是否保存请求的参数
*/
public boolean isSaveRequestData() default true;
/**
* 是否保存响应的参数
*/
public boolean isSaveResponseData() default true;
/**
* 排除指定的请求参数
*/
public String[] excludeParamNames() default {};
}

View File

@@ -0,0 +1,40 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.enums.LimitType;
/**
* 限流注解
*
* @author ruoyi
*/
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface RateLimiter
{
/**
* 限流key
*/
public String key() default CacheConstants.RATE_LIMIT_KEY;
/**
* 限流时间,单位秒
*/
public int time() default 60;
/**
* 限流次数
*/
public int count() default 100;
/**
* 限流类型
*/
public LimitType limitType() default LimitType.DEFAULT;
}

View File

@@ -0,0 +1,31 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Inherited;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
/**
* 自定义注解防止表单重复提交
*
* @author ruoyi
*
*/
@Inherited
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface RepeatSubmit
{
/**
* 间隔时间(ms),小于此时间视为重复提交
*/
public int interval() default 5000;
/**
* 提示消息
*/
public String message() default "不允许重复提交,请稍候再试";
}

View File

@@ -0,0 +1,24 @@
package com.ruoyi.common.annotation;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
import com.fasterxml.jackson.annotation.JacksonAnnotationsInside;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import com.ruoyi.common.config.serializer.SensitiveJsonSerializer;
import com.ruoyi.common.enums.DesensitizedType;
/**
* 数据脱敏注解
*
* @author ruoyi
*/
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.FIELD)
@JacksonAnnotationsInside
@JsonSerialize(using = SensitiveJsonSerializer.class)
public @interface Sensitive
{
DesensitizedType desensitizedType();
}

View File

@@ -0,0 +1,35 @@
package com.ruoyi.common.config;
import org.apache.commons.lang3.concurrent.BasicThreadFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
import java.util.concurrent.*;
@Configuration
public class AsyncThreadPoolConfig {
@Bean("excelImportExecutor")
public ExecutorService excelImportExecutor() {
return new ThreadPoolExecutor(
4, 8,
60, TimeUnit.SECONDS,
new LinkedBlockingQueue<>(100),
new BasicThreadFactory.Builder().namingPattern("excel-import-%d").daemon(true).build(),
new ThreadPoolExecutor.AbortPolicy()
);
}
@Bean("excelExportExecutor")
public ExecutorService excelExportExecutor() {
return new ThreadPoolExecutor(
4, 8,
60, TimeUnit.SECONDS,
new LinkedBlockingQueue<>(100),
new BasicThreadFactory.Builder().namingPattern("excel-export-%d").daemon(true).build(),
new ThreadPoolExecutor.AbortPolicy()
);
}
}

View File

@@ -0,0 +1,28 @@
package com.ruoyi.common.config;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Configuration;
/**
* @Author 吴凯程
* @Date 2025/6/16
**/
@Data
@Configuration
@ConfigurationProperties(prefix = "oss")
public class OssFileProperties {
private String endpoint;
private String accessKeyId;
private String accessKeySecret;
private String bucketName;
}

View File

@@ -0,0 +1,153 @@
package com.ruoyi.common.config;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
/**
* 读取项目相关配置
*
* @author ruoyi
*/
@Data
@Component
@ConfigurationProperties(prefix = "ruoyi")
public class RuoYiConfig
{
/** 项目名称 */
private String name;
/** 版本 */
private String version;
/** 版权年份 */
private String copyrightYear;
/** 上传路径 */
private static String profile;
private static String linuxProfile;
private static String windowsProfile;
public static String getLinuxProfile() {
return linuxProfile;
}
public void setLinuxProfile(String linuxProfile) {
this.linuxProfile = linuxProfile;
}
public static String getWindowsProfile() {
return windowsProfile;
}
public void setWindowsProfile(String windowsProfile) {
this.windowsProfile = windowsProfile;
}
/** 获取地址开关 */
private static boolean addressEnabled;
/** 验证码类型 */
private static String captchaType;
public String getName()
{
return name;
}
public void setName(String name)
{
this.name = name;
}
public String getVersion()
{
return version;
}
public void setVersion(String version)
{
this.version = version;
}
public String getCopyrightYear()
{
return copyrightYear;
}
public void setCopyrightYear(String copyrightYear)
{
this.copyrightYear = copyrightYear;
}
public static String getProfile()
{
return profile;
}
public void setProfile(String profile)
{
RuoYiConfig.profile = profile;
}
public static boolean isAddressEnabled()
{
return addressEnabled;
}
public void setAddressEnabled(boolean addressEnabled)
{
RuoYiConfig.addressEnabled = addressEnabled;
}
public static String getCaptchaType() {
return captchaType;
}
public void setCaptchaType(String captchaType) {
RuoYiConfig.captchaType = captchaType;
}
/**
* 获取导入上传路径
*/
public static String getImportPath()
{
return getProfile() + "/import";
}
/**
* 获取头像上传路径
*/
public static String getAvatarPath()
{
return getProfile() + "/avatar";
}
/**
* 获取下载路径
*/
public static String getDownloadPath()
{
return getProfile() + "/download/";
}
/**
* 获取上传路径
*/
public static String getUploadPath()
{
return getProfile() + "/upload";
}
public static String getFileRootPath()
{
String os = System.getProperty("os.name").toLowerCase();
if (os.contains("win")) {
return getWindowsProfile();
} else {
return getLinuxProfile();
}
}
}

View File

@@ -0,0 +1,67 @@
package com.ruoyi.common.config.serializer;
import java.io.IOException;
import java.util.Objects;
import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.BeanProperty;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;
import com.fasterxml.jackson.databind.ser.ContextualSerializer;
import com.ruoyi.common.annotation.Sensitive;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.enums.DesensitizedType;
import com.ruoyi.common.utils.SecurityUtils;
/**
* 数据脱敏序列化过滤
*
* @author ruoyi
*/
public class SensitiveJsonSerializer extends JsonSerializer<String> implements ContextualSerializer
{
private DesensitizedType desensitizedType;
@Override
public void serialize(String value, JsonGenerator gen, SerializerProvider serializers) throws IOException
{
if (desensitization())
{
gen.writeString(desensitizedType.desensitizer().apply(value));
}
else
{
gen.writeString(value);
}
}
@Override
public JsonSerializer<?> createContextual(SerializerProvider prov, BeanProperty property)
throws JsonMappingException
{
Sensitive annotation = property.getAnnotation(Sensitive.class);
if (Objects.nonNull(annotation) && Objects.equals(String.class, property.getType().getRawClass()))
{
this.desensitizedType = annotation.desensitizedType();
return this;
}
return prov.findValueSerializer(property.getType(), property);
}
/**
* 是否需要脱敏处理
*/
private boolean desensitization()
{
try
{
LoginUser securityUser = SecurityUtils.getLoginUser();
// 管理员不脱敏
return !securityUser.getUser().isAdmin();
}
catch (Exception e)
{
return true;
}
}
}

View File

@@ -0,0 +1,44 @@
package com.ruoyi.common.constant;
/**
* 缓存的key 常量
*
* @author ruoyi
*/
public class CacheConstants
{
/**
* 登录用户 redis key
*/
public static final String LOGIN_TOKEN_KEY = "login_tokens:";
/**
* 验证码 redis key
*/
public static final String CAPTCHA_CODE_KEY = "captcha_codes:";
/**
* 参数管理 cache key
*/
public static final String SYS_CONFIG_KEY = "sys_config:";
/**
* 字典管理 cache key
*/
public static final String SYS_DICT_KEY = "sys_dict:";
/**
* 防重提交 redis key
*/
public static final String REPEAT_SUBMIT_KEY = "repeat_submit:";
/**
* 限流 redis key
*/
public static final String RATE_LIMIT_KEY = "rate_limit:";
/**
* 登录账户密码错误次数 redis key
*/
public static final String PWD_ERR_CNT_KEY = "pwd_err_cnt:";
}

View File

@@ -0,0 +1,180 @@
package com.ruoyi.common.constant;
import java.util.Locale;
import io.jsonwebtoken.Claims;
/**
* 通用常量信息
*
* @author ruoyi
*/
public class Constants
{
/**
* UTF-8 字符集
*/
public static final String UTF8 = "UTF-8";
/**
* GBK 字符集
*/
public static final String GBK = "GBK";
/**
* 系统语言
*/
public static final Locale DEFAULT_LOCALE = Locale.SIMPLIFIED_CHINESE;
/**
* www主域
*/
public static final String WWW = "www.";
/**
* http请求
*/
public static final String HTTP = "http://";
/**
* https请求
*/
public static final String HTTPS = "https://";
/**
* 通用成功标识
*/
public static final String SUCCESS = "0";
/**
* 通用失败标识
*/
public static final String FAIL = "1";
/**
* 登录成功
*/
public static final String LOGIN_SUCCESS = "Success";
/**
* 注销
*/
public static final String LOGOUT = "Logout";
/**
* 注册
*/
public static final String REGISTER = "Register";
/**
* 登录失败
*/
public static final String LOGIN_FAIL = "Error";
/** 状态标示 */
public static final String RESULT = "result";
/**
* 所有权限标识
*/
public static final String ALL_PERMISSION = "*:*:*";
/**
* 管理员角色权限标识
*/
public static final String SUPER_ADMIN = "admin";
public static final String HEAD_ADMIN = "head";
/**
* 角色权限分隔符
*/
public static final String ROLE_DELIMETER = ",";
/**
* 权限标识分隔符
*/
public static final String PERMISSION_DELIMETER = ",";
/**
* 验证码有效期(分钟)
*/
public static final Integer CAPTCHA_EXPIRATION = 2;
/**
* 令牌
*/
public static final String TOKEN = "token";
/**
* 令牌前缀
*/
public static final String TOKEN_PREFIX = "Bearer ";
/**
* 令牌前缀
*/
public static final String LOGIN_USER_KEY = "login_user_key";
/**
* 用户ID
*/
public static final String JWT_USERID = "userid";
public static final String JWT_USERID2 = "userId";
/**
* 用户名称
*/
public static final String JWT_USERNAME = Claims.SUBJECT;
/**
* 用户头像
*/
public static final String JWT_AVATAR = "avatar";
/**
* 创建时间
*/
public static final String JWT_CREATED = "created";
/**
* 用户权限
*/
public static final String JWT_AUTHORITIES = "authorities";
/**
* 资源映射路径 前缀
*/
public static final String RESOURCE_PREFIX = "/profile";
/**
* RMI 远程方法调用
*/
public static final String LOOKUP_RMI = "rmi:";
/**
* LDAP 远程方法调用
*/
public static final String LOOKUP_LDAP = "ldap:";
/**
* LDAPS 远程方法调用
*/
public static final String LOOKUP_LDAPS = "ldaps:";
/**
* 自动识别json对象白名单配置仅允许解析的包名范围越小越安全
*/
public static final String[] JSON_WHITELIST_STR = { "org.springframework", "com.ruoyi" };
/**
* 定时任务白名单配置(仅允许访问的包名,如其他需要可以自行添加)
*/
public static final String[] JOB_WHITELIST_STR = { "com.ruoyi.quartz.task" };
/**
* 定时任务违规的字符
*/
public static final String[] JOB_ERROR_STR = { "java.net.URL", "javax.naming.InitialContext", "org.yaml.snakeyaml",
"org.springframework", "org.apache", "com.ruoyi.common.utils.file", "com.ruoyi.common.config", "com.ruoyi.generator" };
}

View File

@@ -0,0 +1,117 @@
package com.ruoyi.common.constant;
/**
* 代码生成通用常量
*
* @author ruoyi
*/
public class GenConstants
{
/** 单表(增删改查) */
public static final String TPL_CRUD = "crud";
/** 树表(增删改查) */
public static final String TPL_TREE = "tree";
/** 主子表(增删改查) */
public static final String TPL_SUB = "sub";
/** 树编码字段 */
public static final String TREE_CODE = "treeCode";
/** 树父编码字段 */
public static final String TREE_PARENT_CODE = "treeParentCode";
/** 树名称字段 */
public static final String TREE_NAME = "treeName";
/** 上级菜单ID字段 */
public static final String PARENT_MENU_ID = "parentMenuId";
/** 上级菜单名称字段 */
public static final String PARENT_MENU_NAME = "parentMenuName";
/** 数据库字符串类型 */
public static final String[] COLUMNTYPE_STR = { "char", "varchar", "nvarchar", "varchar2" };
/** 数据库文本类型 */
public static final String[] COLUMNTYPE_TEXT = { "tinytext", "text", "mediumtext", "longtext" };
/** 数据库时间类型 */
public static final String[] COLUMNTYPE_TIME = { "datetime", "time", "date", "timestamp" };
/** 数据库数字类型 */
public static final String[] COLUMNTYPE_NUMBER = { "tinyint", "smallint", "mediumint", "int", "number", "integer",
"bit", "bigint", "float", "double", "decimal" };
/** 页面不需要编辑字段 */
public static final String[] COLUMNNAME_NOT_EDIT = { "id", "create_by", "create_time", "del_flag" };
/** 页面不需要显示的列表字段 */
public static final String[] COLUMNNAME_NOT_LIST = { "id", "create_by", "create_time", "del_flag", "update_by",
"update_time" };
/** 页面不需要查询字段 */
public static final String[] COLUMNNAME_NOT_QUERY = { "id", "create_by", "create_time", "del_flag", "update_by",
"update_time", "remark" };
/** Entity基类字段 */
public static final String[] BASE_ENTITY = { "createBy", "createTime", "updateBy", "updateTime", "remark" };
/** Tree基类字段 */
public static final String[] TREE_ENTITY = { "parentName", "parentId", "orderNum", "ancestors", "children" };
/** 文本框 */
public static final String HTML_INPUT = "input";
/** 文本域 */
public static final String HTML_TEXTAREA = "textarea";
/** 下拉框 */
public static final String HTML_SELECT = "select";
/** 单选框 */
public static final String HTML_RADIO = "radio";
/** 复选框 */
public static final String HTML_CHECKBOX = "checkbox";
/** 日期控件 */
public static final String HTML_DATETIME = "datetime";
/** 图片上传控件 */
public static final String HTML_IMAGE_UPLOAD = "imageUpload";
/** 文件上传控件 */
public static final String HTML_FILE_UPLOAD = "fileUpload";
/** 富文本控件 */
public static final String HTML_EDITOR = "editor";
/** 字符串类型 */
public static final String TYPE_STRING = "String";
/** 整型 */
public static final String TYPE_INTEGER = "Integer";
/** 长整型 */
public static final String TYPE_LONG = "Long";
/** 浮点型 */
public static final String TYPE_DOUBLE = "Double";
/** 高精度计算类型 */
public static final String TYPE_BIGDECIMAL = "BigDecimal";
/** 时间类型 */
public static final String TYPE_DATE = "Date";
/** 模糊查询 */
public static final String QUERY_LIKE = "LIKE";
/** 相等查询 */
public static final String QUERY_EQ = "EQ";
/** 需要 */
public static final String REQUIRE = "1";
}

View File

@@ -0,0 +1,94 @@
package com.ruoyi.common.constant;
/**
* 返回状态码
*
* @author ruoyi
*/
public class HttpStatus
{
/**
* 操作成功
*/
public static final int SUCCESS = 200;
/**
* 对象创建成功
*/
public static final int CREATED = 201;
/**
* 请求已经被接受
*/
public static final int ACCEPTED = 202;
/**
* 操作已经执行成功,但是没有返回数据
*/
public static final int NO_CONTENT = 204;
/**
* 资源已被移除
*/
public static final int MOVED_PERM = 301;
/**
* 重定向
*/
public static final int SEE_OTHER = 303;
/**
* 资源没有被修改
*/
public static final int NOT_MODIFIED = 304;
/**
* 参数列表错误(缺少,格式不匹配)
*/
public static final int BAD_REQUEST = 400;
/**
* 未授权
*/
public static final int UNAUTHORIZED = 401;
/**
* 访问受限,授权过期
*/
public static final int FORBIDDEN = 403;
/**
* 资源,服务未找到
*/
public static final int NOT_FOUND = 404;
/**
* 不允许的http方法
*/
public static final int BAD_METHOD = 405;
/**
* 资源冲突,或者资源被锁
*/
public static final int CONFLICT = 409;
/**
* 不支持的数据,媒体类型
*/
public static final int UNSUPPORTED_TYPE = 415;
/**
* 系统内部错误
*/
public static final int ERROR = 500;
/**
* 接口未实现
*/
public static final int NOT_IMPLEMENTED = 501;
/**
* 系统警告消息
*/
public static final int WARN = 601;
}

View File

@@ -0,0 +1,50 @@
package com.ruoyi.common.constant;
/**
* 任务调度通用常量
*
* @author ruoyi
*/
public class ScheduleConstants
{
public static final String TASK_CLASS_NAME = "TASK_CLASS_NAME";
/** 执行目标key */
public static final String TASK_PROPERTIES = "TASK_PROPERTIES";
/** 默认 */
public static final String MISFIRE_DEFAULT = "0";
/** 立即触发执行 */
public static final String MISFIRE_IGNORE_MISFIRES = "1";
/** 触发一次执行 */
public static final String MISFIRE_FIRE_AND_PROCEED = "2";
/** 不触发立即执行 */
public static final String MISFIRE_DO_NOTHING = "3";
public enum Status
{
/**
* 正常
*/
NORMAL("0"),
/**
* 暂停
*/
PAUSE("1");
private String value;
private Status(String value)
{
this.value = value;
}
public String getValue()
{
return value;
}
}
}

View File

@@ -0,0 +1,78 @@
package com.ruoyi.common.constant;
/**
* 用户常量信息
*
* @author ruoyi
*/
public class UserConstants
{
/**
* 平台内系统用户的唯一标志
*/
public static final String SYS_USER = "SYS_USER";
/** 正常状态 */
public static final String NORMAL = "0";
/** 异常状态 */
public static final String EXCEPTION = "1";
/** 用户封禁状态 */
public static final String USER_DISABLE = "1";
/** 角色封禁状态 */
public static final String ROLE_DISABLE = "1";
/** 部门正常状态 */
public static final String DEPT_NORMAL = "0";
/** 部门停用状态 */
public static final String DEPT_DISABLE = "1";
/** 字典正常状态 */
public static final String DICT_NORMAL = "0";
/** 是否为系统默认(是) */
public static final String YES = "Y";
/** 是否菜单外链(是) */
public static final String YES_FRAME = "0";
/** 是否菜单外链(否) */
public static final String NO_FRAME = "1";
/** 菜单类型(目录) */
public static final String TYPE_DIR = "M";
/** 菜单类型(菜单) */
public static final String TYPE_MENU = "C";
/** 菜单类型(按钮) */
public static final String TYPE_BUTTON = "F";
/** Layout组件标识 */
public final static String LAYOUT = "Layout";
/** ParentView组件标识 */
public final static String PARENT_VIEW = "ParentView";
/** InnerLink组件标识 */
public final static String INNER_LINK = "InnerLink";
/** 校验是否唯一的返回标识 */
public final static boolean UNIQUE = true;
public final static boolean NOT_UNIQUE = false;
/**
* 用户名长度限制
*/
public static final int USERNAME_MIN_LENGTH = 2;
public static final int USERNAME_MAX_LENGTH = 20;
/**
* 密码长度限制
*/
public static final int PASSWORD_MIN_LENGTH = 5;
public static final int PASSWORD_MAX_LENGTH = 20;
}

View File

@@ -0,0 +1,230 @@
package com.ruoyi.common.core.controller;
import java.beans.PropertyEditorSupport;
import java.util.Date;
import java.util.List;
import com.github.pagehelper.Page;
import com.ruoyi.common.core.page.TableDataPageInfo;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.bind.WebDataBinder;
import org.springframework.web.bind.annotation.InitBinder;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.ruoyi.common.constant.HttpStatus;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.model.LoginUser;
import com.ruoyi.common.core.page.PageDomain;
import com.ruoyi.common.core.page.TableDataInfo;
import com.ruoyi.common.core.page.TableSupport;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.PageUtils;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.common.utils.sql.SqlUtil;
/**
* web层通用数据处理
*
* @author ruoyi
*/
public class BaseController
{
protected final Logger logger = LoggerFactory.getLogger(this.getClass());
/**
* 将前台传递过来的日期格式的字符串自动转化为Date类型
*/
@InitBinder
public void initBinder(WebDataBinder binder)
{
// Date 类型转换
binder.registerCustomEditor(Date.class, new PropertyEditorSupport()
{
@Override
public void setAsText(String text)
{
setValue(DateUtils.parseDate(text));
}
});
}
/**
* 设置请求分页数据
*/
protected Page<Object> startPage()
{
return PageUtils.startPage();
}
/**
* 设置请求排序数据
*/
protected void startOrderBy()
{
PageDomain pageDomain = TableSupport.buildPageRequest();
if (StringUtils.isNotEmpty(pageDomain.getOrderBy()))
{
String orderBy = SqlUtil.escapeOrderBySql(pageDomain.getOrderBy());
PageHelper.orderBy(orderBy);
}
}
/**
* 清理分页的线程变量
*/
protected void clearPage()
{
PageUtils.clearPage();
}
/**
* 响应请求分页数据
*/
@SuppressWarnings({ "rawtypes", "unchecked" })
protected TableDataInfo getDataTable(List<?> list)
{
TableDataInfo rspData = new TableDataInfo();
rspData.setCode(HttpStatus.SUCCESS);
rspData.setMsg("查询成功");
rspData.setRows(list);
rspData.setTotal(new PageInfo(list).getTotal());
return rspData;
}
protected <T> TableDataPageInfo<T> getDataTable(List<T> list, Page page)
{
TableDataPageInfo<T> rspData = new TableDataPageInfo<>();
rspData.setCode(HttpStatus.SUCCESS);
rspData.setMsg("查询成功");
rspData.setRows(list);
rspData.setTotal(new PageInfo(page).getTotal());
return rspData;
}
/**
* 青田--返回分页数据
*/
protected <T> TableDataPageInfo<T> getDataTableByQt(List<T> list, long total)
{
TableDataPageInfo<T> rspData = new TableDataPageInfo<>();
rspData.setCode(HttpStatus.SUCCESS);
rspData.setMsg("查询成功");
rspData.setRows(list);
rspData.setTotal(total);
return rspData;
}
/**
* 返回成功
*/
public AjaxResult success()
{
return AjaxResult.success();
}
/**
* 返回失败消息
*/
public AjaxResult error()
{
return AjaxResult.error();
}
/**
* 返回成功消息
*/
public AjaxResult success(String message)
{
return AjaxResult.success(message);
}
/**
* 返回成功消息
*/
public AjaxResult success(Object data)
{
return AjaxResult.success(data);
}
/**
* 返回失败消息
*/
public AjaxResult error(String message)
{
return AjaxResult.error(message);
}
/**
* 返回警告消息
*/
public AjaxResult warn(String message)
{
return AjaxResult.warn(message);
}
/**
* 响应返回结果
*
* @param rows 影响行数
* @return 操作结果
*/
protected AjaxResult toAjax(int rows)
{
return rows > 0 ? AjaxResult.success() : AjaxResult.error();
}
/**
* 响应返回结果
*
* @param result 结果
* @return 操作结果
*/
protected AjaxResult toAjax(boolean result)
{
return result ? success() : error();
}
/**
* 页面跳转
*/
public String redirect(String url)
{
return StringUtils.format("redirect:{}", url);
}
/**
* 获取用户缓存信息
*/
public LoginUser getLoginUser()
{
return SecurityUtils.getLoginUser();
}
/**
* 获取登录用户id
*/
public Long getUserId()
{
return getLoginUser().getUserId();
}
/**
* 获取登录部门id
*/
public Long getDeptId()
{
return getLoginUser().getDeptId();
}
/**
* 获取登录用户名
*/
public String getUsername()
{
return getLoginUser().getUsername();
}
}

View File

@@ -0,0 +1,216 @@
package com.ruoyi.common.core.domain;
import java.util.HashMap;
import java.util.Objects;
import com.ruoyi.common.constant.HttpStatus;
import com.ruoyi.common.utils.StringUtils;
/**
* 操作消息提醒
*
* @author ruoyi
*/
public class AjaxResult extends HashMap<String, Object>
{
private static final long serialVersionUID = 1L;
/** 状态码 */
public static final String CODE_TAG = "code";
/** 返回内容 */
public static final String MSG_TAG = "msg";
/** 数据对象 */
public static final String DATA_TAG = "data";
/**
* 初始化一个新创建的 AjaxResult 对象,使其表示一个空消息。
*/
public AjaxResult()
{
}
/**
* 初始化一个新创建的 AjaxResult 对象
*
* @param code 状态码
* @param msg 返回内容
*/
public AjaxResult(int code, String msg)
{
super.put(CODE_TAG, code);
super.put(MSG_TAG, msg);
}
/**
* 初始化一个新创建的 AjaxResult 对象
*
* @param code 状态码
* @param msg 返回内容
* @param data 数据对象
*/
public AjaxResult(int code, String msg, Object data)
{
super.put(CODE_TAG, code);
super.put(MSG_TAG, msg);
if (StringUtils.isNotNull(data))
{
super.put(DATA_TAG, data);
}
}
/**
* 返回成功消息
*
* @return 成功消息
*/
public static AjaxResult success()
{
return AjaxResult.success("操作成功");
}
/**
* 返回成功数据
*
* @return 成功消息
*/
public static AjaxResult success(Object data)
{
return AjaxResult.success("操作成功", data);
}
/**
* 返回成功消息
*
* @param msg 返回内容
* @return 成功消息
*/
public static AjaxResult success(String msg)
{
return AjaxResult.success(msg, null);
}
/**
* 返回成功消息
*
* @param msg 返回内容
* @param data 数据对象
* @return 成功消息
*/
public static AjaxResult success(String msg, Object data)
{
return new AjaxResult(HttpStatus.SUCCESS, msg, data);
}
/**
* 返回警告消息
*
* @param msg 返回内容
* @return 警告消息
*/
public static AjaxResult warn(String msg)
{
return AjaxResult.warn(msg, null);
}
/**
* 返回警告消息
*
* @param msg 返回内容
* @param data 数据对象
* @return 警告消息
*/
public static AjaxResult warn(String msg, Object data)
{
return new AjaxResult(HttpStatus.WARN, msg, data);
}
/**
* 返回错误消息
*
* @return 错误消息
*/
public static AjaxResult error()
{
return AjaxResult.error("操作失败");
}
/**
* 返回错误消息
*
* @param msg 返回内容
* @return 错误消息
*/
public static AjaxResult error(String msg)
{
return AjaxResult.error(msg, null);
}
/**
* 返回错误消息
*
* @param msg 返回内容
* @param data 数据对象
* @return 错误消息
*/
public static AjaxResult error(String msg, Object data)
{
return new AjaxResult(HttpStatus.ERROR, msg, data);
}
/**
* 返回错误消息
*
* @param code 状态码
* @param msg 返回内容
* @return 错误消息
*/
public static AjaxResult error(int code, String msg)
{
return new AjaxResult(code, msg, null);
}
/**
* 是否为成功消息
*
* @return 结果
*/
public boolean isSuccess()
{
return Objects.equals(HttpStatus.SUCCESS, this.get(CODE_TAG));
}
/**
* 是否为警告消息
*
* @return 结果
*/
public boolean isWarn()
{
return Objects.equals(HttpStatus.WARN, this.get(CODE_TAG));
}
/**
* 是否为错误消息
*
* @return 结果
*/
public boolean isError()
{
return Objects.equals(HttpStatus.ERROR, this.get(CODE_TAG));
}
/**
* 方便链式调用
*
* @param key 键
* @param value 值
* @return 数据对象
*/
@Override
public AjaxResult put(String key, Object value)
{
super.put(key, value);
return this;
}
}

View File

@@ -0,0 +1,118 @@
package com.ruoyi.common.core.domain;
import java.io.Serializable;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.fasterxml.jackson.annotation.JsonIgnore;
import com.fasterxml.jackson.annotation.JsonInclude;
/**
* Entity基类
*
* @author ruoyi
*/
public class BaseEntity implements Serializable
{
private static final long serialVersionUID = 1L;
/** 搜索值 */
@JsonIgnore
private String searchValue;
/** 创建者 */
private String createBy;
/** 创建时间 */
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
private Date createTime;
/** 更新者 */
private String updateBy;
/** 更新时间 */
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
private Date updateTime;
/** 备注 */
private String remark;
/** 请求参数 */
@JsonInclude(JsonInclude.Include.NON_EMPTY)
private Map<String, Object> params;
public String getSearchValue()
{
return searchValue;
}
public void setSearchValue(String searchValue)
{
this.searchValue = searchValue;
}
public String getCreateBy()
{
return createBy;
}
public void setCreateBy(String createBy)
{
this.createBy = createBy;
}
public Date getCreateTime()
{
return createTime;
}
public void setCreateTime(Date createTime)
{
this.createTime = createTime;
}
public String getUpdateBy()
{
return updateBy;
}
public void setUpdateBy(String updateBy)
{
this.updateBy = updateBy;
}
public Date getUpdateTime()
{
return updateTime;
}
public void setUpdateTime(Date updateTime)
{
this.updateTime = updateTime;
}
public String getRemark()
{
return remark;
}
public void setRemark(String remark)
{
this.remark = remark;
}
public Map<String, Object> getParams()
{
if (params == null)
{
params = new HashMap<>();
}
return params;
}
public void setParams(Map<String, Object> params)
{
this.params = params;
}
}

View File

@@ -0,0 +1,115 @@
package com.ruoyi.common.core.domain;
import java.io.Serializable;
import com.ruoyi.common.constant.HttpStatus;
/**
* 响应信息主体
*
* @author ruoyi
*/
public class R<T> implements Serializable
{
private static final long serialVersionUID = 1L;
/** 成功 */
public static final int SUCCESS = HttpStatus.SUCCESS;
/** 失败 */
public static final int FAIL = HttpStatus.ERROR;
private int code;
private String msg;
private T data;
public static <T> R<T> ok()
{
return restResult(null, SUCCESS, "操作成功");
}
public static <T> R<T> ok(T data)
{
return restResult(data, SUCCESS, "操作成功");
}
public static <T> R<T> ok(T data, String msg)
{
return restResult(data, SUCCESS, msg);
}
public static <T> R<T> fail()
{
return restResult(null, FAIL, "操作失败");
}
public static <T> R<T> fail(String msg)
{
return restResult(null, FAIL, msg);
}
public static <T> R<T> fail(T data)
{
return restResult(data, FAIL, "操作失败");
}
public static <T> R<T> fail(T data, String msg)
{
return restResult(data, FAIL, msg);
}
public static <T> R<T> fail(int code, String msg)
{
return restResult(null, code, msg);
}
private static <T> R<T> restResult(T data, int code, String msg)
{
R<T> apiResult = new R<>();
apiResult.setCode(code);
apiResult.setData(data);
apiResult.setMsg(msg);
return apiResult;
}
public int getCode()
{
return code;
}
public void setCode(int code)
{
this.code = code;
}
public String getMsg()
{
return msg;
}
public void setMsg(String msg)
{
this.msg = msg;
}
public T getData()
{
return data;
}
public void setData(T data)
{
this.data = data;
}
public static <T> Boolean isError(R<T> ret)
{
return !isSuccess(ret);
}
public static <T> Boolean isSuccess(R<T> ret)
{
return R.SUCCESS == ret.getCode();
}
}

View File

@@ -0,0 +1,79 @@
package com.ruoyi.common.core.domain;
import java.util.ArrayList;
import java.util.List;
/**
* Tree基类
*
* @author ruoyi
*/
public class TreeEntity extends BaseEntity
{
private static final long serialVersionUID = 1L;
/** 父菜单名称 */
private String parentName;
/** 父菜单ID */
private Long parentId;
/** 显示顺序 */
private Integer orderNum;
/** 祖级列表 */
private String ancestors;
/** 子部门 */
private List<?> children = new ArrayList<>();
public String getParentName()
{
return parentName;
}
public void setParentName(String parentName)
{
this.parentName = parentName;
}
public Long getParentId()
{
return parentId;
}
public void setParentId(Long parentId)
{
this.parentId = parentId;
}
public Integer getOrderNum()
{
return orderNum;
}
public void setOrderNum(Integer orderNum)
{
this.orderNum = orderNum;
}
public String getAncestors()
{
return ancestors;
}
public void setAncestors(String ancestors)
{
this.ancestors = ancestors;
}
public List<?> getChildren()
{
return children;
}
public void setChildren(List<?> children)
{
this.children = children;
}
}

View File

@@ -0,0 +1,92 @@
package com.ruoyi.common.core.domain;
import java.io.Serializable;
import java.util.List;
import java.util.stream.Collectors;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.ruoyi.common.core.domain.entity.SysDept;
import com.ruoyi.common.core.domain.entity.SysMenu;
/**
* Treeselect树结构实体类
*
* @author ruoyi
*/
public class TreeSelect implements Serializable
{
private static final long serialVersionUID = 1L;
/** 节点ID */
private Long id;
/** 节点名称 */
private String label;
/** 节点层级 */
private String level;
/** 子节点 */
@JsonInclude(JsonInclude.Include.NON_EMPTY)
private List<TreeSelect> children;
public TreeSelect()
{
}
public TreeSelect(SysDept dept)
{
this.id = dept.getDeptId();
this.label = dept.getDeptName();
this.level = dept.getDeptType();
this.children = dept.getChildren().stream().map(TreeSelect::new).collect(Collectors.toList());
}
public TreeSelect(SysMenu menu)
{
this.id = menu.getMenuId();
this.label = menu.getMenuName();
this.children = menu.getChildren().stream().map(TreeSelect::new).collect(Collectors.toList());
}
public Long getId()
{
return id;
}
public void setId(Long id)
{
this.id = id;
}
public String getLabel()
{
return label;
}
public void setLabel(String label)
{
this.label = label;
}
public List<TreeSelect> getChildren()
{
return children;
}
public void setChildren(List<TreeSelect> children)
{
this.children = children;
}
public String getLevel()
{
return level;
}
public void setLevel(String level)
{
this.level = level;
}
}

View File

@@ -0,0 +1,217 @@
package com.ruoyi.common.core.domain.entity;
import java.util.ArrayList;
import java.util.List;
import javax.validation.constraints.Email;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
import com.ruoyi.common.core.domain.BaseEntity;
/**
* 部门表 sys_dept
*
* @author ruoyi
*/
public class SysDept extends BaseEntity
{
private static final long serialVersionUID = 1L;
/** 部门ID */
private Long deptId;
/** 父部门ID */
private Long parentId;
/** 祖级列表 */
private String ancestors;
/** 部门名称 */
private String deptName;
/** 显示顺序 */
private Integer orderNum;
/** 负责人 */
private String leader;
/** 联系电话 */
private String phone;
/** 邮箱 */
private String email;
/** 部门状态:0正常,1停用 */
private String status;
/** 删除标志0代表存在 2代表删除 */
private String delFlag;
/** 父部门名称 */
private String parentName;
private String deptType;
/** 子部门 */
private List<SysDept> children = new ArrayList<SysDept>();
public Long getDeptId()
{
return deptId;
}
public void setDeptId(Long deptId)
{
this.deptId = deptId;
}
public Long getParentId()
{
return parentId;
}
public void setParentId(Long parentId)
{
this.parentId = parentId;
}
public String getAncestors()
{
return ancestors;
}
public void setAncestors(String ancestors)
{
this.ancestors = ancestors;
}
@NotBlank(message = "部门名称不能为空")
@Size(min = 0, max = 30, message = "部门名称长度不能超过30个字符")
public String getDeptName()
{
return deptName;
}
public void setDeptName(String deptName)
{
this.deptName = deptName;
}
@NotNull(message = "显示顺序不能为空")
public Integer getOrderNum()
{
return orderNum;
}
public void setOrderNum(Integer orderNum)
{
this.orderNum = orderNum;
}
public String getLeader()
{
return leader;
}
public void setLeader(String leader)
{
this.leader = leader;
}
@Size(min = 0, max = 11, message = "联系电话长度不能超过11个字符")
public String getPhone()
{
return phone;
}
public void setPhone(String phone)
{
this.phone = phone;
}
@Email(message = "邮箱格式不正确")
@Size(min = 0, max = 50, message = "邮箱长度不能超过50个字符")
public String getEmail()
{
return email;
}
public void setEmail(String email)
{
this.email = email;
}
public String getStatus()
{
return status;
}
public void setStatus(String status)
{
this.status = status;
}
public String getDelFlag()
{
return delFlag;
}
public void setDelFlag(String delFlag)
{
this.delFlag = delFlag;
}
public String getParentName()
{
return parentName;
}
public void setParentName(String parentName)
{
this.parentName = parentName;
}
public List<SysDept> getChildren()
{
return children;
}
public void setChildren(List<SysDept> children)
{
this.children = children;
}
public String getDeptType()
{
return deptType;
}
public void setDeptType(String depteType)
{
this.deptType = depteType;
}
@Override
public String toString() {
return new ToStringBuilder(this,ToStringStyle.MULTI_LINE_STYLE)
.append("deptId", getDeptId())
.append("parentId", getParentId())
.append("ancestors", getAncestors())
.append("deptName", getDeptName())
.append("orderNum", getOrderNum())
.append("leader", getLeader())
.append("phone", getPhone())
.append("email", getEmail())
.append("status", getStatus())
.append("delFlag", getDelFlag())
.append("createBy", getCreateBy())
.append("createTime", getCreateTime())
.append("updateBy", getUpdateBy())
.append("updateTime", getUpdateTime())
.append("deptType",getDeptType())
.toString();
}
}

View File

@@ -0,0 +1,176 @@
package com.ruoyi.common.core.domain.entity;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.Size;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
import com.ruoyi.common.annotation.Excel;
import com.ruoyi.common.annotation.Excel.ColumnType;
import com.ruoyi.common.constant.UserConstants;
import com.ruoyi.common.core.domain.BaseEntity;
/**
* 字典数据表 sys_dict_data
*
* @author ruoyi
*/
public class SysDictData extends BaseEntity
{
private static final long serialVersionUID = 1L;
/** 字典编码 */
@Excel(name = "字典编码", cellType = ColumnType.NUMERIC)
private Long dictCode;
/** 字典排序 */
@Excel(name = "字典排序", cellType = ColumnType.NUMERIC)
private Long dictSort;
/** 字典标签 */
@Excel(name = "字典标签")
private String dictLabel;
/** 字典键值 */
@Excel(name = "字典键值")
private String dictValue;
/** 字典类型 */
@Excel(name = "字典类型")
private String dictType;
/** 样式属性(其他样式扩展) */
private String cssClass;
/** 表格字典样式 */
private String listClass;
/** 是否默认Y是 N否 */
@Excel(name = "是否默认", readConverterExp = "Y=是,N=否")
private String isDefault;
/** 状态0正常 1停用 */
@Excel(name = "状态", readConverterExp = "0=正常,1=停用")
private String status;
public Long getDictCode()
{
return dictCode;
}
public void setDictCode(Long dictCode)
{
this.dictCode = dictCode;
}
public Long getDictSort()
{
return dictSort;
}
public void setDictSort(Long dictSort)
{
this.dictSort = dictSort;
}
@NotBlank(message = "字典标签不能为空")
@Size(min = 0, max = 100, message = "字典标签长度不能超过100个字符")
public String getDictLabel()
{
return dictLabel;
}
public void setDictLabel(String dictLabel)
{
this.dictLabel = dictLabel;
}
@NotBlank(message = "字典键值不能为空")
@Size(min = 0, max = 100, message = "字典键值长度不能超过100个字符")
public String getDictValue()
{
return dictValue;
}
public void setDictValue(String dictValue)
{
this.dictValue = dictValue;
}
@NotBlank(message = "字典类型不能为空")
@Size(min = 0, max = 100, message = "字典类型长度不能超过100个字符")
public String getDictType()
{
return dictType;
}
public void setDictType(String dictType)
{
this.dictType = dictType;
}
@Size(min = 0, max = 100, message = "样式属性长度不能超过100个字符")
public String getCssClass()
{
return cssClass;
}
public void setCssClass(String cssClass)
{
this.cssClass = cssClass;
}
public String getListClass()
{
return listClass;
}
public void setListClass(String listClass)
{
this.listClass = listClass;
}
public boolean getDefault()
{
return UserConstants.YES.equals(this.isDefault);
}
public String getIsDefault()
{
return isDefault;
}
public void setIsDefault(String isDefault)
{
this.isDefault = isDefault;
}
public String getStatus()
{
return status;
}
public void setStatus(String status)
{
this.status = status;
}
@Override
public String toString() {
return new ToStringBuilder(this,ToStringStyle.MULTI_LINE_STYLE)
.append("dictCode", getDictCode())
.append("dictSort", getDictSort())
.append("dictLabel", getDictLabel())
.append("dictValue", getDictValue())
.append("dictType", getDictType())
.append("cssClass", getCssClass())
.append("listClass", getListClass())
.append("isDefault", getIsDefault())
.append("status", getStatus())
.append("createBy", getCreateBy())
.append("createTime", getCreateTime())
.append("updateBy", getUpdateBy())
.append("updateTime", getUpdateTime())
.append("remark", getRemark())
.toString();
}
}

View File

@@ -0,0 +1,96 @@
package com.ruoyi.common.core.domain.entity;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.Pattern;
import javax.validation.constraints.Size;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
import com.ruoyi.common.annotation.Excel;
import com.ruoyi.common.annotation.Excel.ColumnType;
import com.ruoyi.common.core.domain.BaseEntity;
/**
* 字典类型表 sys_dict_type
*
* @author ruoyi
*/
public class SysDictType extends BaseEntity
{
private static final long serialVersionUID = 1L;
/** 字典主键 */
@Excel(name = "字典主键", cellType = ColumnType.NUMERIC)
private Long dictId;
/** 字典名称 */
@Excel(name = "字典名称")
private String dictName;
/** 字典类型 */
@Excel(name = "字典类型")
private String dictType;
/** 状态0正常 1停用 */
@Excel(name = "状态", readConverterExp = "0=正常,1=停用")
private String status;
public Long getDictId()
{
return dictId;
}
public void setDictId(Long dictId)
{
this.dictId = dictId;
}
@NotBlank(message = "字典名称不能为空")
@Size(min = 0, max = 100, message = "字典类型名称长度不能超过100个字符")
public String getDictName()
{
return dictName;
}
public void setDictName(String dictName)
{
this.dictName = dictName;
}
@NotBlank(message = "字典类型不能为空")
@Size(min = 0, max = 100, message = "字典类型类型长度不能超过100个字符")
@Pattern(regexp = "^[a-z][a-z0-9_]*$", message = "字典类型必须以字母开头,且只能为(小写字母,数字,下滑线)")
public String getDictType()
{
return dictType;
}
public void setDictType(String dictType)
{
this.dictType = dictType;
}
public String getStatus()
{
return status;
}
public void setStatus(String status)
{
this.status = status;
}
@Override
public String toString() {
return new ToStringBuilder(this,ToStringStyle.MULTI_LINE_STYLE)
.append("dictId", getDictId())
.append("dictName", getDictName())
.append("dictType", getDictType())
.append("status", getStatus())
.append("createBy", getCreateBy())
.append("createTime", getCreateTime())
.append("updateBy", getUpdateBy())
.append("updateTime", getUpdateTime())
.append("remark", getRemark())
.toString();
}
}

View File

@@ -0,0 +1,298 @@
package com.ruoyi.common.core.domain.entity;
import com.ruoyi.common.core.domain.BaseEntity;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
import java.util.ArrayList;
import java.util.List;
/**
* 菜单权限表 sys_menu
*
* @author ruoyi
*/
public class SysMenu extends BaseEntity {
private static final long serialVersionUID = 1L;
/**
* 菜单ID
*/
private Long menuId;
/**
* 菜单名称
*/
private String menuName;
/**
* 父菜单名称
*/
private String parentName;
/**
* 父菜单ID
*/
private Long parentId;
/**
* 显示顺序
*/
private Integer orderNum;
/**
* 路由地址
*/
private String path;
/**
* 组件路径
*/
private String component;
/**
* 路由参数
*/
private String query;
/**
* 路由名称默认和路由地址相同的驼峰格式注意因为vue3版本的router会删除名称相同路由为避免名字的冲突特殊情况可以自定义
*/
private String routeName;
/**
* 是否为外链0是 1否
*/
private String isFrame;
/**
* 是否缓存0缓存 1不缓存
*/
private String isCache;
/**
* 类型M目录 C菜单 F按钮
*/
private String menuType;
/**
* 显示状态0显示 1隐藏
*/
private String visible;
/**
* 菜单状态0正常 1停用
*/
private String status;
/**
* 权限字符串
*/
private String perms;
/**
* 菜单图标
*/
private String icon;
private Boolean isLink;
/**
* 子菜单
*/
private List<SysMenu> children = new ArrayList<SysMenu>();
/**
* 可见部门
*/
private String deptIds;
public String getDeptIds() {
return deptIds;
}
public void setDeptIds(String deptIds) {
this.deptIds = deptIds;
}
public Long getMenuId() {
return menuId;
}
public void setMenuId(Long menuId) {
this.menuId = menuId;
}
@NotBlank(message = "菜单名称不能为空")
@Size(min = 0, max = 50, message = "菜单名称长度不能超过50个字符")
public String getMenuName() {
return menuName;
}
public void setMenuName(String menuName) {
this.menuName = menuName;
}
public String getParentName() {
return parentName;
}
public void setParentName(String parentName) {
this.parentName = parentName;
}
public Long getParentId() {
return parentId;
}
public void setParentId(Long parentId) {
this.parentId = parentId;
}
@NotNull(message = "显示顺序不能为空")
public Integer getOrderNum() {
return orderNum;
}
public void setOrderNum(Integer orderNum) {
this.orderNum = orderNum;
}
@Size(min = 0, max = 200, message = "路由地址不能超过200个字符")
public String getPath() {
return path;
}
public void setPath(String path) {
this.path = path;
}
@Size(min = 0, max = 200, message = "组件路径不能超过255个字符")
public String getComponent() {
return component;
}
public void setComponent(String component) {
this.component = component;
}
public String getQuery() {
return query;
}
public void setQuery(String query) {
this.query = query;
}
public String getRouteName() {
return routeName;
}
public void setRouteName(String routeName) {
this.routeName = routeName;
}
public String getIsFrame() {
return isFrame;
}
public void setIsFrame(String isFrame) {
this.isFrame = isFrame;
}
public String getIsCache() {
return isCache;
}
public void setIsCache(String isCache) {
this.isCache = isCache;
}
@NotBlank(message = "菜单类型不能为空")
public String getMenuType() {
return menuType;
}
public void setMenuType(String menuType) {
this.menuType = menuType;
}
public String getVisible() {
return visible;
}
public void setVisible(String visible) {
this.visible = visible;
}
public String getStatus() {
return status;
}
public void setStatus(String status) {
this.status = status;
}
@Size(min = 0, max = 100, message = "权限标识长度不能超过100个字符")
public String getPerms() {
return perms;
}
public void setPerms(String perms) {
this.perms = perms;
}
public String getIcon() {
return icon;
}
public void setIcon(String icon) {
this.icon = icon;
}
public List<SysMenu> getChildren() {
return children;
}
public void setChildren(List<SysMenu> children) {
this.children = children;
}
public Boolean getIsLink() {
return isLink;
}
public void setIsLink(Boolean isLink) {
this.isLink = isLink;
}
@Override
public String toString() {
return new ToStringBuilder(this, ToStringStyle.MULTI_LINE_STYLE)
.append("menuId", getMenuId())
.append("menuName", getMenuName())
.append("parentId", getParentId())
.append("orderNum", getOrderNum())
.append("path", getPath())
.append("component", getComponent())
.append("query", getQuery())
.append("routeName", getRouteName())
.append("isFrame", getIsFrame())
.append("IsCache", getIsCache())
.append("menuType", getMenuType())
.append("visible", getVisible())
.append("status ", getStatus())
.append("perms", getPerms())
.append("icon", getIcon())
.append("createBy", getCreateBy())
.append("createTime", getCreateTime())
.append("updateBy", getUpdateBy())
.append("updateTime", getUpdateTime())
.append("remark", getRemark())
.append("deptIds",getDeptIds())
.toString();
}
}

View File

@@ -0,0 +1,267 @@
package com.ruoyi.common.core.domain.entity;
import java.util.Set;
import javax.validation.constraints.NotBlank;
import javax.validation.constraints.NotNull;
import javax.validation.constraints.Size;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
import com.ruoyi.common.annotation.Excel;
import com.ruoyi.common.annotation.Excel.ColumnType;
import com.ruoyi.common.core.domain.BaseEntity;
/**
* 角色表 sys_role
*
* @author ruoyi
*/
public class SysRole extends BaseEntity
{
private static final long serialVersionUID = 1L;
/** 角色ID */
@Excel(name = "角色序号", cellType = ColumnType.NUMERIC)
private Long roleId;
/** 角色名称 */
@Excel(name = "角色名称")
private String roleName;
/** 角色权限 */
@Excel(name = "角色权限")
private String roleKey;
/** 角色排序 */
@Excel(name = "角色排序")
private Integer roleSort;
/** 数据范围1所有数据权限2自定义数据权限3本部门数据权限4本部门及以下数据权限5仅本人数据权限 */
@Excel(name = "数据范围", readConverterExp = "1=所有数据权限,2=自定义数据权限,3=本部门数据权限,4=本部门及以下数据权限,5=仅本人数据权限")
private String dataScope;
/** 菜单树选择项是否关联显示( 0父子不互相关联显示 1父子互相关联显示 */
private boolean menuCheckStrictly;
/** 部门树选择项是否关联显示0父子不互相关联显示 1父子互相关联显示 */
private boolean deptCheckStrictly;
/** 角色状态0正常 1停用 */
@Excel(name = "角色状态", readConverterExp = "0=正常,1=停用")
private String status;
/** 删除标志0代表存在 2代表删除 */
private String delFlag;
/** 用户是否存在此角色标识 默认不存在 */
private boolean flag = false;
/** 菜单组 */
private Long[] menuIds;
/** 部门组(数据权限) */
private Long[] deptIds;
/** 角色菜单权限 */
private Set<String> permissions;
/** 角色描述 */
@Excel(name = "角色描述")
private String description;
/** 类型 */
@Excel(name = "角色类型")
private String type;
public SysRole()
{
}
public SysRole(Long roleId)
{
this.roleId = roleId;
}
public Long getRoleId()
{
return roleId;
}
public void setRoleId(Long roleId)
{
this.roleId = roleId;
}
public boolean isAdmin()
{
return isAdmin(this.roleId);
}
public static boolean isAdmin(Long roleId)
{
return roleId != null && 1L == roleId;
}
@NotBlank(message = "角色名称不能为空")
@Size(min = 0, max = 30, message = "角色名称长度不能超过30个字符")
public String getRoleName()
{
return roleName;
}
public void setRoleName(String roleName)
{
this.roleName = roleName;
}
@NotBlank(message = "权限字符不能为空")
@Size(min = 0, max = 100, message = "权限字符长度不能超过100个字符")
public String getRoleKey()
{
return roleKey;
}
public void setRoleKey(String roleKey)
{
this.roleKey = roleKey;
}
@NotNull(message = "显示顺序不能为空")
public Integer getRoleSort()
{
return roleSort;
}
public void setRoleSort(Integer roleSort)
{
this.roleSort = roleSort;
}
public String getDataScope()
{
return dataScope;
}
public void setDataScope(String dataScope)
{
this.dataScope = dataScope;
}
public boolean isMenuCheckStrictly()
{
return menuCheckStrictly;
}
public void setMenuCheckStrictly(boolean menuCheckStrictly)
{
this.menuCheckStrictly = menuCheckStrictly;
}
public boolean isDeptCheckStrictly()
{
return deptCheckStrictly;
}
public void setDeptCheckStrictly(boolean deptCheckStrictly)
{
this.deptCheckStrictly = deptCheckStrictly;
}
public String getStatus()
{
return status;
}
public void setStatus(String status)
{
this.status = status;
}
public String getDelFlag()
{
return delFlag;
}
public void setDelFlag(String delFlag)
{
this.delFlag = delFlag;
}
public boolean isFlag()
{
return flag;
}
public void setFlag(boolean flag)
{
this.flag = flag;
}
public Long[] getMenuIds()
{
return menuIds;
}
public void setMenuIds(Long[] menuIds)
{
this.menuIds = menuIds;
}
public Long[] getDeptIds()
{
return deptIds;
}
public void setDeptIds(Long[] deptIds)
{
this.deptIds = deptIds;
}
public Set<String> getPermissions()
{
return permissions;
}
public void setPermissions(Set<String> permissions)
{
this.permissions = permissions;
}
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public String getType() {
return type;
}
public void setType(String type) {
this.type = type;
}
@Override
public String toString() {
return new ToStringBuilder(this,ToStringStyle.MULTI_LINE_STYLE)
.append("roleId", getRoleId())
.append("roleName", getRoleName())
.append("roleKey", getRoleKey())
.append("roleSort", getRoleSort())
.append("dataScope", getDataScope())
.append("menuCheckStrictly", isMenuCheckStrictly())
.append("deptCheckStrictly", isDeptCheckStrictly())
.append("status", getStatus())
.append("delFlag", getDelFlag())
.append("createBy", getCreateBy())
.append("createTime", getCreateTime())
.append("updateBy", getUpdateBy())
.append("updateTime", getUpdateTime())
.append("remark", getRemark())
.append("description", getDescription())
.append("type", getType())
.toString();
}
}

View File

@@ -0,0 +1,336 @@
package com.ruoyi.common.core.domain.entity;
import java.util.Date;
import java.util.List;
import javax.validation.constraints.*;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
import com.ruoyi.common.annotation.Excel;
import com.ruoyi.common.annotation.Excel.ColumnType;
import com.ruoyi.common.annotation.Excel.Type;
import com.ruoyi.common.annotation.Excels;
import com.ruoyi.common.core.domain.BaseEntity;
import com.ruoyi.common.xss.Xss;
/**
* 用户对象 sys_user
*
* @author ruoyi
*/
public class SysUser extends BaseEntity
{
private static final long serialVersionUID = 1L;
/** 用户ID */
@Excel(name = "用户序号", type = Type.EXPORT, cellType = ColumnType.NUMERIC, prompt = "用户编号")
private Long userId;
/** 部门ID */
@Excel(name = "部门编号", type = Type.IMPORT)
private Long deptId;
/** 用户账号 */
@Excel(name = "登录名称")
private String userName;
/** 用户账号 */
@Excel(name = "角色名")
private String roleName;
/** 用户昵称 */
@Excel(name = "用户名称")
private String nickName;
/** 用户邮箱 */
@Excel(name = "用户邮箱")
private String email;
/** 手机号码 */
@Excel(name = "手机号码", cellType = ColumnType.TEXT)
private String phonenumber;
/** 用户性别 */
@Excel(name = "用户性别", readConverterExp = "0=男,1=女,2=未知")
private String sex;
/** 用户头像 */
private String avatar;
/** 密码 */
private String password;
/** 帐号状态0正常 1停用 */
@Excel(name = "帐号状态", readConverterExp = "0=正常,1=停用")
private String status;
/** 删除标志0代表存在 2代表删除 */
private String delFlag;
/** 最后登录IP */
@Excel(name = "最后登录IP", type = Type.EXPORT)
private String loginIp;
/** 最后登录时间 */
@Excel(name = "最后登录时间", width = 30, dateFormat = "yyyy-MM-dd HH:mm:ss", type = Type.EXPORT)
private Date loginDate;
/** 部门对象 */
@Excels({
@Excel(name = "部门名称", targetAttr = "deptName", type = Type.EXPORT),
@Excel(name = "部门负责人", targetAttr = "leader", type = Type.EXPORT)
})
private SysDept dept;
/** 角色对象 */
private List<SysRole> roles;
/** 角色组 */
private Long[] roleIds;
/** 岗位组 */
private Long[] postIds;
/** 角色ID */
private Long roleId;
public SysUser()
{
}
public String getRoleName() {
return roleName;
}
public void setRoleName(String roleName) {
this.roleName = roleName;
}
public SysUser(Long userId)
{
this.userId = userId;
}
public Long getUserId()
{
return userId;
}
public void setUserId(Long userId)
{
this.userId = userId;
}
public boolean isAdmin()
{
return isAdmin(this.userId);
}
public static boolean isAdmin(Long userId)
{
return userId != null && 1L == userId;
}
public Long getDeptId()
{
return deptId;
}
public void setDeptId(Long deptId)
{
this.deptId = deptId;
}
@Xss(message = "用户昵称不能包含脚本字符")
@Size(min = 0, max = 30, message = "用户昵称长度不能超过30个字符")
public String getNickName()
{
return nickName;
}
public void setNickName(String nickName)
{
this.nickName = nickName;
}
@Xss(message = "用户账号不能包含脚本字符")
@NotBlank(message = "用户账号不能为空")
@Size(min = 0, max = 30, message = "用户账号长度不能超过30个字符")
public String getUserName()
{
return userName;
}
public void setUserName(String userName)
{
this.userName = userName;
}
@Email(message = "邮箱格式不正确")
@Size(min = 0, max = 50, message = "邮箱长度不能超过50个字符")
public String getEmail()
{
return email;
}
public void setEmail(String email)
{
this.email = email;
}
@Size(min = 0, max = 11, message = "手机号码长度不能超过11个字符")
public String getPhonenumber()
{
return phonenumber;
}
public void setPhonenumber(String phonenumber)
{
this.phonenumber = phonenumber;
}
public String getSex()
{
return sex;
}
public void setSex(String sex)
{
this.sex = sex;
}
public String getAvatar()
{
return avatar;
}
public void setAvatar(String avatar)
{
this.avatar = avatar;
}
public String getPassword()
{
return password;
}
public void setPassword(String password)
{
this.password = password;
}
public String getStatus()
{
return status;
}
public void setStatus(String status)
{
this.status = status;
}
public String getDelFlag()
{
return delFlag;
}
public void setDelFlag(String delFlag)
{
this.delFlag = delFlag;
}
public String getLoginIp()
{
return loginIp;
}
public void setLoginIp(String loginIp)
{
this.loginIp = loginIp;
}
public Date getLoginDate()
{
return loginDate;
}
public void setLoginDate(Date loginDate)
{
this.loginDate = loginDate;
}
public SysDept getDept()
{
return dept;
}
public void setDept(SysDept dept)
{
this.dept = dept;
}
public List<SysRole> getRoles()
{
return roles;
}
public void setRoles(List<SysRole> roles)
{
this.roles = roles;
}
public Long[] getRoleIds()
{
return roleIds;
}
public void setRoleIds(Long[] roleIds)
{
this.roleIds = roleIds;
}
public Long[] getPostIds()
{
return postIds;
}
public void setPostIds(Long[] postIds)
{
this.postIds = postIds;
}
public Long getRoleId()
{
return roleId;
}
public void setRoleId(Long roleId)
{
this.roleId = roleId;
}
@Override
public String toString() {
return new ToStringBuilder(this,ToStringStyle.MULTI_LINE_STYLE)
.append("userId", getUserId())
.append("deptId", getDeptId())
.append("userName", getUserName())
.append("nickName", getNickName())
.append("email", getEmail())
.append("phonenumber", getPhonenumber())
.append("sex", getSex())
.append("avatar", getAvatar())
.append("password", getPassword())
.append("status", getStatus())
.append("delFlag", getDelFlag())
.append("loginIp", getLoginIp())
.append("loginDate", getLoginDate())
.append("createBy", getCreateBy())
.append("createTime", getCreateTime())
.append("updateBy", getUpdateBy())
.append("updateTime", getUpdateTime())
.append("remark", getRemark())
.append("dept", getDept())
.toString();
}
}

View File

@@ -0,0 +1,69 @@
package com.ruoyi.common.core.domain.model;
/**
* 用户登录对象
*
* @author ruoyi
*/
public class LoginBody
{
/**
* 用户名
*/
private String username;
/**
* 用户密码
*/
private String password;
/**
* 验证码
*/
private String code;
/**
* 唯一标识
*/
private String uuid;
public String getUsername()
{
return username;
}
public void setUsername(String username)
{
this.username = username;
}
public String getPassword()
{
return password;
}
public void setPassword(String password)
{
this.password = password;
}
public String getCode()
{
return code;
}
public void setCode(String code)
{
this.code = code;
}
public String getUuid()
{
return uuid;
}
public void setUuid(String uuid)
{
this.uuid = uuid;
}
}

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