open-embodied hai 6 meses
pai
achega
fa48161c03
Modificáronse 100 ficheiros con 7486 adicións e 66 borrados
  1. 194 0
      LICENSE
  2. 149 66
      README.md
  3. 8 0
      admin/.gitignore
  4. 0 0
      admin/.keep
  5. 43 0
      admin/Jenkinsfile
  6. 39 0
      admin/Readme.txt
  7. 144 0
      admin/admin/pom.xml
  8. 30 0
      admin/admin/src/main/java/com/kakarote/admin/AdminApplication.java
  9. 52 0
      admin/admin/src/main/java/com/kakarote/admin/common/AdminCodeEnum.java
  10. 28 0
      admin/admin/src/main/java/com/kakarote/admin/common/AdminConst.java
  11. 174 0
      admin/admin/src/main/java/com/kakarote/admin/common/AdminDictUtils.java
  12. 81 0
      admin/admin/src/main/java/com/kakarote/admin/common/AdminModuleEnum.java
  13. 47 0
      admin/admin/src/main/java/com/kakarote/admin/common/AdminRoleTypeEnum.java
  14. 42 0
      admin/admin/src/main/java/com/kakarote/admin/common/EncryptableResolver.java
  15. 74 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminCommonController.java
  16. 373 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminConfigController.java
  17. 96 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminDeptConfigController.java
  18. 136 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminDeptController.java
  19. 114 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminDictDataController.java
  20. 100 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminDictMatchController.java
  21. 149 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminDictTypeController.java
  22. 221 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminFileController.java
  23. 45 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminInstrumentInfoController.java
  24. 59 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminInstrumentRoleController.java
  25. 151 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminMenuController.java
  26. 208 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminMessageController.java
  27. 606 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminRoleController.java
  28. 50 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminRoleMenuDpController.java
  29. 91 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminTenantController.java
  30. 502 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminUserController.java
  31. 38 0
      admin/admin/src/main/java/com/kakarote/admin/controller/AdminUserHisTableController.java
  32. 44 0
      admin/admin/src/main/java/com/kakarote/admin/controller/SysAreaController.java
  33. 87 0
      admin/admin/src/main/java/com/kakarote/admin/demo/controller/WfDemoController.java
  34. 70 0
      admin/admin/src/main/java/com/kakarote/admin/demo/entity/BO/WfDemoBO.java
  35. 76 0
      admin/admin/src/main/java/com/kakarote/admin/demo/entity/PO/WfDemo.java
  36. 19 0
      admin/admin/src/main/java/com/kakarote/admin/demo/mapper/WfDemoMapper.java
  37. 21 0
      admin/admin/src/main/java/com/kakarote/admin/demo/mapper/xml/WfDemoMapper.xml
  38. 18 0
      admin/admin/src/main/java/com/kakarote/admin/demo/service/IWfDemoService.java
  39. 27 0
      admin/admin/src/main/java/com/kakarote/admin/demo/service/impl/WfDemoServiceImpl.java
  40. 24 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminCompanyBO.java
  41. 15 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDeleteByBatchIdBO.java
  42. 43 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDeptBO.java
  43. 44 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDeptConfigBO.java
  44. 22 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDeptQueryBO.java
  45. 27 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDictMathBO.java
  46. 47 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDictTypeBO.java
  47. 23 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminMessageQueryBO.java
  48. 44 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminUserBO.java
  49. 28 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminUserStatusBO.java
  50. 15 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/DeptUserListByHrmBO.java
  51. 17 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/DeptUserListVO.java
  52. 26 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/DeptVO.java
  53. 29 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/HrmAddUserBO.java
  54. 29 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/LogWelcomeSpeechBO.java
  55. 34 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/ModuleSettingBO.java
  56. 16 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/RenameFileBO.java
  57. 22 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/SysAreaBO.java
  58. 26 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/SystemUserBO.java
  59. 33 0
      admin/admin/src/main/java/com/kakarote/admin/entity/BO/UserBookBO.java
  60. 39 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminAttention.java
  61. 51 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminConfig.java
  62. 74 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDept.java
  63. 51 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDeptConfig.java
  64. 46 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDeptMenu.java
  65. 270 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDictData.java
  66. 66 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDictMatch.java
  67. 194 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDictType.java
  68. 70 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminFile.java
  69. 61 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminInstrumentInfo.java
  70. 52 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminInstrumentRole.java
  71. 109 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminMenu.java
  72. 72 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminMessage.java
  73. 51 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminModelSort.java
  74. 59 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminOfficialImg.java
  75. 71 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminRole.java
  76. 42 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminRoleMenu.java
  77. 45 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminRoleMenuDp.java
  78. 95 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminUser.java
  79. 54 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminUserConfig.java
  80. 44 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminUserHisTable.java
  81. 44 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminUserRole.java
  82. 72 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminVisitingCard.java
  83. 51 0
      admin/admin/src/main/java/com/kakarote/admin/entity/PO/SysArea.java
  84. 82 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminDeptVO.java
  85. 54 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminInstrumentRoleVO.java
  86. 39 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminMenuVO.java
  87. 38 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminMessageVO.java
  88. 28 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminRoleVO.java
  89. 107 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminUserVO.java
  90. 31 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/CloudConfigVO.java
  91. 36 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/HrmSimpleUserVO.java
  92. 31 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/ModuleSettingVO.java
  93. 67 0
      admin/admin/src/main/java/com/kakarote/admin/entity/VO/UserBookVO.java
  94. 16 0
      admin/admin/src/main/java/com/kakarote/admin/mapper/AdminAttentionMapper.java
  95. 21 0
      admin/admin/src/main/java/com/kakarote/admin/mapper/AdminConfigMapper.java
  96. 24 0
      admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDeptConfigMapper.java
  97. 20 0
      admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDeptMapper.java
  98. 13 0
      admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDeptMenuMapper.java
  99. 97 0
      admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDictDataMapper.java
  100. 29 0
      admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDictMatchMapper.java

+ 194 - 0
LICENSE

@@ -0,0 +1,194 @@
+木兰宽松许可证,第2版
+
+木兰宽松许可证,第2版
+
+2020年1月 http://license.coscl.org.cn/MulanPSL2
+
+您对“软件”的复制、使用、修改及分发受木兰宽松许可证,第2版(“本许可证”)的如下条款的约束:
+
+0.   定义
+
+“软件” 是指由“贡献”构成的许可在“本许可证”下的程序和相关文档的集合。
+
+“贡献” 是指由任一“贡献者”许可在“本许可证”下的受版权法保护的作品。
+
+“贡献者” 是指将受版权法保护的作品许可在“本许可证”下的自然人或“法人实体”。
+
+“法人实体” 是指提交贡献的机构及其“关联实体”。
+
+“关联实体” 是指,对“本许可证”下的行为方而言,控制、受控制或与其共同受控制的机构,此处的控制是
+指有受控方或共同受控方至少50%直接或间接的投票权、资金或其他有价证券。
+
+1.   授予版权许可
+
+每个“贡献者”根据“本许可证”授予您永久性的、全球性的、免费的、非独占的、不可撤销的版权许可,您可
+以复制、使用、修改、分发其“贡献”,不论修改与否。
+
+2.   授予专利许可
+
+每个“贡献者”根据“本许可证”授予您永久性的、全球性的、免费的、非独占的、不可撤销的(根据本条规定
+撤销除外)专利许可,供您制造、委托制造、使用、许诺销售、销售、进口其“贡献”或以其他方式转移其“贡
+献”。前述专利许可仅限于“贡献者”现在或将来拥有或控制的其“贡献”本身或其“贡献”与许可“贡献”时的“软
+件”结合而将必然会侵犯的专利权利要求,不包括对“贡献”的修改或包含“贡献”的其他结合。如果您或您的“
+关联实体”直接或间接地,就“软件”或其中的“贡献”对任何人发起专利侵权诉讼(包括反诉或交叉诉讼)或
+其他专利维权行动,指控其侵犯专利权,则“本许可证”授予您对“软件”的专利许可自您提起诉讼或发起维权
+行动之日终止。
+
+3.   无商标许可
+
+“本许可证”不提供对“贡献者”的商品名称、商标、服务标志或产品名称的商标许可,但您为满足第4条规定
+的声明义务而必须使用除外。
+
+4.   分发限制
+
+您可以在任何媒介中将“软件”以源程序形式或可执行形式重新分发,不论修改与否,但您必须向接收者提供“
+本许可证”的副本,并保留“软件”中的版权、商标、专利及免责声明。
+
+5.   免责声明与责任限制
+
+“软件”及其中的“贡献”在提供时不带任何明示或默示的担保。在任何情况下,“贡献者”或版权所有者不对
+任何人因使用“软件”或其中的“贡献”而引发的任何直接或间接损失承担责任,不论因何种原因导致或者基于
+何种法律理论,即使其曾被建议有此种损失的可能性。
+
+6.   语言
+
+“本许可证”以中英文双语表述,中英文版本具有同等法律效力。如果中英文版本存在任何冲突不一致,以中文
+版为准。
+
+条款结束
+
+如何将木兰宽松许可证,第2版,应用到您的软件
+
+如果您希望将木兰宽松许可证,第2版,应用到您的新软件,为了方便接收者查阅,建议您完成如下三步:
+
+1, 请您补充如下声明中的空白,包括软件名、软件的首次发表年份以及您作为版权人的名字;
+
+2, 请您在软件包的一级目录下创建以“LICENSE”为名的文件,将整个许可证文本放入该文件中;
+
+3, 请将如下声明文本放入每个源文件的头部注释中。
+
+Copyright (c) [Year] [name of copyright holder]
+[Software Name] is licensed under Mulan PSL v2.
+You can use this software according to the terms and conditions of the Mulan
+PSL v2.
+You may obtain a copy of Mulan PSL v2 at:
+         http://license.coscl.org.cn/MulanPSL2
+THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY
+KIND, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO
+NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
+See the Mulan PSL v2 for more details.
+
+Mulan Permissive Software License,Version 2
+
+Mulan Permissive Software License,Version 2 (Mulan PSL v2)
+
+January 2020 http://license.coscl.org.cn/MulanPSL2
+
+Your reproduction, use, modification and distribution of the Software shall
+be subject to Mulan PSL v2 (this License) with the following terms and
+conditions:
+
+0. Definition
+
+Software means the program and related documents which are licensed under
+this License and comprise all Contribution(s).
+
+Contribution means the copyrightable work licensed by a particular
+Contributor under this License.
+
+Contributor means the Individual or Legal Entity who licenses its
+copyrightable work under this License.
+
+Legal Entity means the entity making a Contribution and all its
+Affiliates.
+
+Affiliates means entities that control, are controlled by, or are under
+common control with the acting entity under this License, ‘control’ means
+direct or indirect ownership of at least fifty percent (50%) of the voting
+power, capital or other securities of controlled or commonly controlled
+entity.
+
+1. Grant of Copyright License
+
+Subject to the terms and conditions of this License, each Contributor hereby
+grants to you a perpetual, worldwide, royalty-free, non-exclusive,
+irrevocable copyright license to reproduce, use, modify, or distribute its
+Contribution, with modification or not.
+
+2. Grant of Patent License
+
+Subject to the terms and conditions of this License, each Contributor hereby
+grants to you a perpetual, worldwide, royalty-free, non-exclusive,
+irrevocable (except for revocation under this Section) patent license to
+make, have made, use, offer for sale, sell, import or otherwise transfer its
+Contribution, where such patent license is only limited to the patent claims
+owned or controlled by such Contributor now or in future which will be
+necessarily infringed by its Contribution alone, or by combination of the
+Contribution with the Software to which the Contribution was contributed.
+The patent license shall not apply to any modification of the Contribution,
+and any other combination which includes the Contribution. If you or your
+Affiliates directly or indirectly institute patent litigation (including a
+cross claim or counterclaim in a litigation) or other patent enforcement
+activities against any individual or entity by alleging that the Software or
+any Contribution in it infringes patents, then any patent license granted to
+you under this License for the Software shall terminate as of the date such
+litigation or activity is filed or taken.
+
+3. No Trademark License
+
+No trademark license is granted to use the trade names, trademarks, service
+marks, or product names of Contributor, except as required to fulfill notice
+requirements in section 4.
+
+4. Distribution Restriction
+
+You may distribute the Software in any medium with or without modification,
+whether in source or executable forms, provided that you provide recipients
+with a copy of this License and retain copyright, patent, trademark and
+disclaimer statements in the Software.
+
+5. Disclaimer of Warranty and Limitation of Liability
+
+THE SOFTWARE AND CONTRIBUTION IN IT ARE PROVIDED WITHOUT WARRANTIES OF ANY
+KIND, EITHER EXPRESS OR IMPLIED. IN NO EVENT SHALL ANY CONTRIBUTOR OR
+COPYRIGHT HOLDER BE LIABLE TO YOU FOR ANY DAMAGES, INCLUDING, BUT NOT
+LIMITED TO ANY DIRECT, OR INDIRECT, SPECIAL OR CONSEQUENTIAL DAMAGES ARISING
+FROM YOUR USE OR INABILITY TO USE THE SOFTWARE OR THE CONTRIBUTION IN IT, NO
+MATTER HOW IT’S CAUSED OR BASED ON WHICH LEGAL THEORY, EVEN IF ADVISED OF
+THE POSSIBILITY OF SUCH DAMAGES.
+
+6. Language
+
+THIS LICENSE IS WRITTEN IN BOTH CHINESE AND ENGLISH, AND THE CHINESE VERSION
+AND ENGLISH VERSION SHALL HAVE THE SAME LEGAL EFFECT. IN THE CASE OF
+DIVERGENCE BETWEEN THE CHINESE AND ENGLISH VERSIONS, THE CHINESE VERSION
+SHALL PREVAIL.
+
+END OF THE TERMS AND CONDITIONS
+
+How to Apply the Mulan Permissive Software License,Version 2
+(Mulan PSL v2) to Your Software
+
+To apply the Mulan PSL v2 to your work, for easy identification by
+recipients, you are suggested to complete following three steps:
+
+i. Fill in the blanks in following statement, including insert your software
+name, the year of the first publication of your software, and your name
+identified as the copyright owner;
+
+ii. Create a file named "LICENSE" which contains the whole context of this
+License in the first directory of your software package;
+
+iii. Attach the statement to the appropriate annotated syntax at the
+beginning of each source file.
+
+Copyright (c) [Year] [name of copyright holder]
+[Software Name] is licensed under Mulan PSL v2.
+You can use this software according to the terms and conditions of the Mulan
+PSL v2.
+You may obtain a copy of Mulan PSL v2 at:
+         http://license.coscl.org.cn/MulanPSL2
+THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY
+KIND, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO
+NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
+See the Mulan PSL v2 for more details.

+ 149 - 66
README.md

@@ -1,92 +1,175 @@
-# projectcc-smart-Construction
 
+<div align="center" >
+    <img src="https://foruda.gitee.com/avatar/1728719990621654075/13695585_qingyun-software_1728719990.png!avatar100" />
+</div>
+
+<div align="center">
+
+智慧工地管理系统Java版本
+
+</div>
+
+<div align="center" >
+    <a href="https://www.sdyingfeng.cn">
+        <img src="https://img.shields.io/badge/Licence-apache2.0-green.svg?style=flat" />
+    </a>
+    <a href="https://www.sdyingfeng.cn">
+        <img src="https://img.shields.io/badge/Edition-5.4-blue.svg" />
+    </a>
+     <a href="https://gitee.com/ZhongBangKeJi/CRMEB/repository/archive/master.zip">
+        <img src="https://img.shields.io/badge/Download-240m-red.svg" />
+    </a>
+</div>
+
+#### 
+
+<div align="center">
+
+[官网](https://sdyingfeng.cn/?gongdi) |
+[在线体验](http://zhgd.sdyingfeng.cn) |
+[宽屏预览](https://gitee.com/qingyun-software/YFConstruction/blob/master/README.md) 
+
+</div>
+
+<div align="center">
+    如果对您有帮助,您可以点右上角 "Star" ❤️ 支持一下 谢谢!
+</div>
+
+---
+
+### 📖 简介:
+
+萤丰 开源智慧工地系统Java版,基于微服务架构+Java+Spring Cloud +Uni-App +MySql开发,在微信公众号、小程序、H5、移动端都能使用,代码全开源无加密,独立部署,二开很方便,还支持免费商用,自用、做二开项目都很合适。
 
+萤丰开源智慧工地Java版本:https://gitee.com/qingyun-software/YFConstruction
+
+
+系统代码全开源无加密,独立部署、二开方便,适用于建筑公司、建筑集团、房地产公司等各种业务需求。利用互联网与AI技术,以建筑工地为核心,支持视频监控、工地实名制、安全帽识别、反光背心、抽烟等多模型同步对接。
+
+---
+
+### 💡 系统亮点:
+>1.SpringBoot 框架开发业界主流。  </br>
+>2.【前端】Web PC 管理端 Vue + Element UI。<br>
+>3.【前端】移动端使用 Uni-app 框架,前后端分离开发。<br>
+>4.标准RESTful 接口、标准数据传输,逻辑层次更明确,更多的提高api复用。<br>
+>5.支持Redis队列,降低流量高峰,解除耦合,高可用。<br>
+>6.数据导出,方便个性化分析。<br>
+>7.数据统计分析,使用ECharts图表统计,实现多种统计分析。<br>
+>8.Spring Security 权限管理,后台多种角色,多重身份权限管理,权限可以控制到按钮级别的操作。<br>
+>9.Vue表单生成控件,拖拽配置表单,减少前端重复表单工作量,提高前端开发效率。<br>
+>9.Uniapp生成小程序、H5、移动端都能使用<br>
+---
 
-## Getting started
+### 💻 运行环境及框架:
+~~~
+1.	WEB Pc 管理后台使用Vue + Element UI 开发 兼容主流浏览器 ie11+
+2.	后台服务 Java SpringBoot + Mybatis + Mysql + redis
+3.	运行环境 linux和windows等都支持,只要有Java环境和对应的数据库 redis
+4.	运行条件 Java 1.8 Mysql5.7
+~~~
+---
 
-To make it easy for you to get started with GitLab, here's a list of recommended next steps.
+### 🔧 Java项目框架 和 WEB PC 项目运行环境
+~~~
+1. SpringBoot 2.2.5.RELEASE
+2. Jdk 1.8
+3. Maven 3.5.0+   
+4. Mysql 5.7.20 
+5. Redis (版本不限)
+6. Nacos(1.2.1)
+5. npm 8.19.1
+6. node v14.18.0
+7. vue 2.x
+8. element ui 2.13
+~~~
 
-Already a pro? Just edit this README.md and make it your own. Want to make it easy? [Use the template at the bottom](#editing-this-readme)!
+---
 
-## Add your files
+### 🧭 项目代码包介绍
+~~~
+1. admin     WEB程序         Java SpringBoot + mybatis
+   ├── admin         -- 系统管理模块和用户管理模块
+   ├── authorization -- 登录鉴权模块
+   ├── core          -- 通用的代码和工具类
+   ├── crm           -- 客户管理模块(租户相关)
+   ├── gateway       -- 网关模块
+   ├── oa            -- OA模块(审批相关)
+   ├── work          -- 项目管理模块(任务分配相关)
+   ├── build         -- 智慧工地功能模块(核心业务)
+   ├── dataagg       -- 数据聚合模块
+   ├── datarecept    -- 数据接收模块
+   ├── message       -- 消息发送模块
+   ├── xxl-job-admin -- 定时任务模块
+   └── workflow      -- 工作流模块
+2. front     PC端管理端       VUE + ElementUi
+3. 接口文档   Api对应的接口文档也可以部署项目后查看
+~~~
 
-- [ ] [Create](https://docs.gitlab.com/ee/user/project/repository/web_editor.html#create-a-file) or [upload](https://docs.gitlab.com/ee/user/project/repository/web_editor.html#upload-a-file) files
-- [ ] [Add files using the command line](https://docs.gitlab.com/ee/gitlab-basics/add-file.html#add-a-file-using-the-command-line) or push an existing Git repository with the following command:
+---
 
-```
-cd existing_repo
-git remote add origin http://47.103.205.229:8099/qiyego/projectcc-smart-construction.git
-git branch -M main
-git push -uf origin main
-```
+### 🎬 系统演示:
 
-## Integrate with your tools
 
-- [ ] [Set up project integrations](http://47.103.205.229:8099/qiyego/projectcc-smart-construction/-/settings/integrations)
+1、PC端演示: http://zhgd.sdyingfeng.cn <br>
 
-## Collaborate with your team
+请联系客服获取,客服微信:lhl-bmy-bhw
 
-- [ ] [Invite team members and collaborators](https://docs.gitlab.com/ee/user/project/members/)
-- [ ] [Create a new merge request](https://docs.gitlab.com/ee/user/project/merge_requests/creating_merge_requests.html)
-- [ ] [Automatically close issues from merge requests](https://docs.gitlab.com/ee/user/project/issues/managing_issues.html#closing-issues-automatically)
-- [ ] [Enable merge request approvals](https://docs.gitlab.com/ee/user/project/merge_requests/approvals/)
-- [ ] [Set auto-merge](https://docs.gitlab.com/ee/user/project/merge_requests/merge_when_pipeline_succeeds.html)
+~~~
+项目端账号:15854827610 密码:联系客服
 
-## Test and Deploy
+监管端账号:13241588504  密码:联系客服
+~~~
+ 
 
-Use the built-in continuous integration in GitLab.
+2、大屏端演示:http://zhgd.sdyingfeng.cn/njv<br>
+~~~
+项目端账号:15854827610 密码:联系客服
+监管端账号:13241588504 密码:联系客服
+~~~
 
-- [ ] [Get started with GitLab CI/CD](https://docs.gitlab.com/ee/ci/quick_start/index.html)
-- [ ] [Analyze your code for known vulnerabilities with Static Application Security Testing(SAST)](https://docs.gitlab.com/ee/user/application_security/sast/)
-- [ ] [Deploy to Kubernetes, Amazon EC2, or Amazon ECS using Auto Deploy](https://docs.gitlab.com/ee/topics/autodevops/requirements.html)
-- [ ] [Use pull-based deployments for improved Kubernetes management](https://docs.gitlab.com/ee/user/clusters/agent/)
-- [ ] [Set up protected environments](https://docs.gitlab.com/ee/ci/environments/protected_environments.html)
+3、移动端APP演示:
+~~~
+ 项目端APP下载地址:http://zhgd.sdyingfeng.cn/apk/xmapk/gd.apk
+ 项目端账号:15854827610  密码:联系客服
 
-***
+ 移动端监管端APP下载地址:http://zhgd.sdyingfeng.cn/apk/jgapk/gd.apk
+ 监管端账号:13241588504 密码:联系客服
+~~~
 
-# Editing this README
+---
 
-When you're ready to make this README your own, just edit this file and use the handy template below (or feel free to structure it however you want - this is just a starting point!). Thank you to [makeareadme.com](https://www.makeareadme.com/) for this template.
+###  📞 联系我们
 
-## Suggestions for a good README
-Every project is different, so consider which of these sections apply to yours. The sections used in the template are suggestions for most open source projects. Also keep in mind that while a README can be too long and detailed, too long is better than too short. If you think your README is too long, consider utilizing another form of documentation rather than cutting out information.
+如果您有任何疑问或需要咨询,欢迎与我们联系:
+~~~
+客服微信:lhl-bmy-bhw
+吕经理: 13241588504(微信同号)
+~~~
+
+---
+
+###  📺 架构图
+
+![输入图片说明](readme/jiagoutu.jpg)
+![输入图片说明](readme/gailan.png)
+---
+
+### 🔔 使用须知
+1.允许用于个人学习、毕业设计、教学案例、公益事业、商业使用;<br>
+2.如果商用必须保留版权信息,请自觉遵守;<br>
+3.禁止将本项目的代码和资源进行任何形式的出售,产生的一切任何后果责任由侵权者自负。<br>
 
-## Name
-Choose a self-explaining name for your project.
+---
+### 🪪 版权信息
+本项目包含的第三方源码和二进制文件之版权信息另行标注。<br>
+版权所有Copyright © 2017-2024 by 萤丰信息 (https://www.sdyingfeng.cn)<br>
+All rights reserved。<br>
+著作权所有者为山东萤丰信息技术有限公司。<br>
 
-## Description
-Let people know what your project can do specifically. Provide context and add a link to any reference visitors might be unfamiliar with. A list of Features or a Background subsection can also be added here. If there are alternatives to your project, this is a good place to list differentiating factors.
+---
 
-## Badges
-On some READMEs, you may see small images that convey metadata, such as whether or not all the tests are passing for the project. You can use Shields to add some to your README. Many services also have instructions for adding a badge.
 
-## Visuals
-Depending on what you are making, it can be a good idea to include screenshots or even a video (you'll frequently see GIFs rather than actual videos). Tools like ttygif can help, but check out Asciinema for a more sophisticated method.
 
-## Installation
-Within a particular ecosystem, there may be a common way of installing things, such as using Yarn, NuGet, or Homebrew. However, consider the possibility that whoever is reading your README is a novice and would like more guidance. Listing specific steps helps remove ambiguity and gets people to using your project as quickly as possible. If it only runs in a specific context like a particular programming language version or operating system or has dependencies that have to be installed manually, also add a Requirements subsection.
 
-## Usage
-Use examples liberally, and show the expected output if you can. It's helpful to have inline the smallest example of usage that you can demonstrate, while providing links to more sophisticated examples if they are too long to reasonably include in the README.
 
-## Support
-Tell people where they can go to for help. It can be any combination of an issue tracker, a chat room, an email address, etc.
-
-## Roadmap
-If you have ideas for releases in the future, it is a good idea to list them in the README.
-
-## Contributing
-State if you are open to contributions and what your requirements are for accepting them.
-
-For people who want to make changes to your project, it's helpful to have some documentation on how to get started. Perhaps there is a script that they should run or some environment variables that they need to set. Make these steps explicit. These instructions could also be useful to your future self.
-
-You can also document commands to lint the code or run tests. These steps help to ensure high code quality and reduce the likelihood that the changes inadvertently break something. Having instructions for running tests is especially helpful if it requires external setup, such as starting a Selenium server for testing in a browser.
-
-## Authors and acknowledgment
-Show your appreciation to those who have contributed to the project.
-
-## License
-For open source projects, say how it is licensed.
-
-## Project status
-If you have run out of energy or time for your project, put a note at the top of the README saying that development has slowed down or stopped completely. Someone may choose to fork your project or volunteer to step in as a maintainer or owner, allowing your project to keep going. You can also make an explicit request for maintainers.

+ 8 - 0
admin/.gitignore

@@ -0,0 +1,8 @@
+.DS_Store
+.idea/
+*.iml
+logs
+target
+*/target/**
+rebel.xml
+rebel-remote.xml

+ 0 - 0
admin/.keep


+ 43 - 0
admin/Jenkinsfile

@@ -0,0 +1,43 @@
+pipeline {
+    agent any
+
+    stages {
+        stage('pull') {
+            steps {
+                checkout([$class: 'GitSCM', branches: [[name: "*/${branch}"]],
+                doGenerateSubmoduleConfigurations: false, extensions: [], submoduleCfg: [],
+                userRemoteConfigs: [[credentialsId: '9bc5f661-86ed-446c-b0b3-e41b364a39a2',
+                url: 'http://git.5kcrm.com/zhangzhiwei/wk_crm_single.git']]])
+                echo '拉取代码成功'
+            }
+        }
+        stage('build') {
+            steps {
+                script {
+                         def apps = "${project_name}".split(",")
+                         for (int i = 0; i < apps.size(); ++i) {
+                             sh label: '', script: "sh package.sh ${apps[i]}"
+                             echo " ${apps[i]} 打包成功"
+                         }
+                    }
+            }
+        }
+        stage('deploy') {
+            steps {
+                echo 'deploy'
+                withEnv(['JENKINS_NODE_COOKIE=dontkillme']) {
+                    script {
+                            def apps = "${project_name}".split(",")
+                            for (int i = 0; i < apps.size(); ++i) {
+                                sh label: '', script: "sh deploy.sh stop ${apps[i]}"
+                                sh label: '', script: "sh deploy.sh copy ${apps[i]}"
+                                sh label: '', script: "sh deploy.sh start ${apps[i]}"
+                                echo " ${apps[i]} 部署成功"
+                            }
+                        }
+                   }
+            }
+        }
+
+    }
+}

+ 39 - 0
admin/Readme.txt

@@ -0,0 +1,39 @@
+
+crm_pro
+├── admin         -- 系统管理模块和用户管理模块
+├── authorization -- 登录鉴权模块
+├── core          -- 通用的代码和工具类
+├── crm           -- 客户管理模块(租户相关)
+├── gateway       -- 网关模块
+├── oa            -- OA模块(审批相关)
+└── work          -- 项目管理模块(任务分配相关)
+└── workflow          -- 工作流模块
+-----------------------以上原框架自带---------------------------
+├── build           -- 智慧工地功能模块(核心业务)
+├── dataagg     -- 数据聚合模块
+├── datarecept   -- 数据接收模块
+├── message   -- 消息发送模块
+├── xxl-job-admin   -- 定时任务模块
+
+
+### 前置环境
+- Jdk1.8
+- Maven3.5.0+   
+- Mysql5.7.20 
+- Redis(版本不限)
+- Nacos(1.2.1)
+
+### 安装说明
+#### 1. 导入初始化sql,目前项目下gateway模块使用的独立数据库,其他模块使用同一数据库
+- 初始化gateway模块数据库:新建数据库 wk_nacos,参见脚本:DBsql/wk_nacos.sql
+- 初始化其余模块数据库:新建数据库 wk_build_demo,参见脚本:DBsql/wk_build_demo.sql
+- 初始化定时任务模块数据库:新建数据库 xxl_job ,参见脚本:DBsql/xxl_job.sql
+#### 2.在各个模块下resource目录配置数据库以及redis帐号信息(默认使用的是application-dev.yml配置文件)
+#### 3.项目需在项目根目录执行mvn install
+#### 4.项目启动 
+先启动nacos、redis等基础服务
+其中项目基础模块:gateway,authorization,admin必须启动,其他模块可按需启动。
+启动完成后,在浏览器中访问:http://localhost:8443/即可登录系统
+
+### 其他说明
+新增服务时需在wk_nacos.config_info_route表中新增相应网关路由

+ 144 - 0
admin/admin/pom.xml

@@ -0,0 +1,144 @@
+<?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>
+	<packaging>jar</packaging>
+	<parent>
+		<groupId>com.kakarote</groupId>
+		<artifactId>wkcrm</artifactId>
+		<version>0.0.1-SNAPSHOT</version>
+	</parent>
+
+	<artifactId>wk_admin</artifactId>
+	<version>0.0.1-SNAPSHOT</version>
+	<name>wk_admin</name>
+	<description>系统管理</description>
+
+
+	<dependencies>
+		<dependency>
+			<groupId>com.kakarote</groupId>
+			<artifactId>core</artifactId>
+			<version>${core.version}</version>
+		</dependency>
+		<dependency>
+			<groupId>io.seata</groupId>
+			<artifactId>seata-spring-boot-starter</artifactId>
+			<version>1.2.0</version>
+		</dependency>
+        <dependency>
+            <groupId>com.alibaba.cloud</groupId>
+            <artifactId>spring-cloud-starter-alibaba-seata</artifactId>
+        </dependency>
+		<dependency>
+			<groupId>com.alibaba.nacos</groupId>
+			<artifactId>nacos-client</artifactId>
+			<version>1.2.0</version>
+		</dependency>
+	</dependencies>
+
+	<build>
+		<resources>
+			<resource>
+				<!-- xml放在java目录下-->
+				<directory>src/main/java/com/kakarote/admin/</directory>
+				<includes>
+					<!-- 代表编译此目录下的所有下的所有xml文件 -->
+					<include>**/*.xml</include>
+				</includes>
+			</resource>
+			<!--解决idea不识别resources的问题-->
+			<resource>
+				<directory>src/main/resources</directory>
+				<filtering>true</filtering>
+			</resource>
+		</resources>
+		<plugins>
+
+			<!--打包jar-->
+			<plugin>
+				<groupId>org.apache.maven.plugins</groupId>
+				<artifactId>maven-jar-plugin</artifactId>
+				<configuration>
+					<archive>
+						<manifest>
+							<addClasspath>true</addClasspath>
+							<!--MANIFEST.MF 中 Class-Path 加入前缀-->
+							<classpathPrefix>lib/</classpathPrefix>
+							<!--jar包不包含唯一版本标识-->
+							<useUniqueVersions>false</useUniqueVersions>
+							<!--指定入口类-->
+							<mainClass>com.kakarote.admin.AdminApplication</mainClass>
+						</manifest>
+						<manifestEntries>
+							<!--MANIFEST.MF 中 Class-Path 加入资源文件目录-->
+							<Class-Path>./config/</Class-Path>
+						</manifestEntries>
+					</archive>
+					<outputDirectory>${project.build.directory}</outputDirectory>
+				</configuration>
+			</plugin>
+
+			<!--拷贝依赖 copy-dependencies-->
+			<plugin>
+				<groupId>org.apache.maven.plugins</groupId>
+				<artifactId>maven-dependency-plugin</artifactId>
+				<executions>
+					<execution>
+						<id>copy-dependencies</id>
+						<phase>package</phase>
+						<goals>
+							<goal>copy-dependencies</goal>
+						</goals>
+						<configuration>
+							<outputDirectory>
+								${project.build.directory}/lib/
+							</outputDirectory>
+						</configuration>
+					</execution>
+				</executions>
+			</plugin>
+
+			<!--拷贝资源文件 copy-resources-->
+			<plugin>
+				<artifactId>maven-resources-plugin</artifactId>
+				<executions>
+					<execution>
+						<id>copy-resources</id>
+						<phase>package</phase>
+						<goals>
+							<goal>copy-resources</goal>
+						</goals>
+						<configuration>
+							<resources>
+								<resource>
+									<directory>src/main/resources/</directory>
+								</resource>
+							</resources>
+							<outputDirectory>${project.build.directory}/config</outputDirectory>
+						</configuration>
+					</execution>
+				</executions>
+			</plugin>
+			<plugin>
+				<artifactId>maven-assembly-plugin</artifactId>
+				<configuration>
+					<appendAssemblyId>false</appendAssemblyId>
+					<descriptors>
+						<descriptor>../assembly.xml</descriptor>
+					</descriptors>
+				</configuration>
+				<executions>
+					<execution>
+						<id>make-assembly</id>
+						<phase>package</phase>
+						<goals>
+							<goal>single</goal>
+						</goals>
+					</execution>
+				</executions>
+			</plugin>
+		</plugins>
+	</build>
+
+</project>

+ 30 - 0
admin/admin/src/main/java/com/kakarote/admin/AdminApplication.java

@@ -0,0 +1,30 @@
+package com.kakarote.admin;
+
+import com.alicp.jetcache.anno.config.EnableCreateCacheAnnotation;
+import com.alicp.jetcache.anno.config.EnableMethodCache;
+import com.kakarote.core.CoreApplication;
+import io.seata.spring.annotation.datasource.EnableAutoDataSourceProxy;
+import org.mybatis.spring.annotation.MapperScan;
+import org.springframework.boot.SpringApplication;
+import org.springframework.boot.autoconfigure.SpringBootApplication;
+import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
+import org.springframework.cloud.openfeign.EnableFeignClients;
+import org.springframework.context.annotation.ComponentScan;
+
+/**
+ * @author zhangzhiwei
+ */
+@SpringBootApplication
+@EnableAutoDataSourceProxy
+@EnableDiscoveryClient
+@EnableFeignClients(basePackageClasses = {CoreApplication.class, AdminApplication.class})
+@ComponentScan(basePackageClasses = {CoreApplication.class, AdminApplication.class})
+@MapperScan(basePackages = {"com.kakarote.*.mapper","com.kakarote.*.*.mapper"})
+@EnableMethodCache(basePackages = "com.kakarote.admin",order = -9999)
+@EnableCreateCacheAnnotation
+public class AdminApplication {
+    public static void main(String[] args) {
+        SpringApplication.run(AdminApplication.class, args);
+
+    }
+}

+ 52 - 0
admin/admin/src/main/java/com/kakarote/admin/common/AdminCodeEnum.java

@@ -0,0 +1,52 @@
+package com.kakarote.admin.common;
+
+import com.kakarote.core.common.ResultCode;
+
+/**
+ * @author zhangzhiwei
+ * 管理后台响应错误代码枚举类
+ */
+
+public enum AdminCodeEnum implements ResultCode {
+    //客户模块管理
+    ADMIN_MODULE_CLOSE_ERROR(1101, "客户管理模块不能关闭"),
+    ADMIN_DATA_EXIST_ERROR(1102, "数据不存在"),
+    ADMIN_PARENT_USER_NOTNULL_ERROR(1105, "启用重新开始编号需要有日期编号规则"),
+    ADMIN_PASSWORD_INTENSITY_ERROR(1106, "密码必须由 6-20位字母、数字组成"),
+    ADMIN_USER_EXIST_ERROR(1107, "用户已存在!"),
+    ADMIN_PARENT_USER_ERROR(1109, "这个用户的下属不能设置为直属上级!"),
+    ADMIN_PARENT_DEPT_ERROR(1110, "这个部门的下属不能设置为直属部门!"),
+    ADMIN_DEPT_REMOVE_EXIST_USER_ERROR(1111, "这个部门下有员工,不能删除!"),
+    ADMIN_DEPT_REMOVE_EXIST_DEPT_ERROR(1112, "这个部门下有下级部门,不能删除!"),
+    ADMIN_USER_NOT_ROLE_ERROR(1113, "请先给用户设置角色"),
+    ADMIN_USER_NOT_DEPT_ERROR(1114, "请先给用户设置部门"),
+    ADMIN_USER_NOT_PARENT_ERROR(1115, "请先给用户设置直属上级"),
+    ADMIN_SUPER_USER_DISABLED_ERROR(1116, "超级管理员用户不可禁用"),
+    ADMIN_ROLE_NAME_EXIST_ERROR(1117, "角色名称已存在"),
+    ADMIN_PHONE_CODE_ERROR(1118, "手机验证码出错!"),
+    ADMIN_PHONE_REGISTER_ERROR(1119, "手机号已被注册!"),
+    ADMIN_USER_NOT_EXIST_ERROR(1125, "用户不存在!"),
+    ADMIN_ACCOUNT_ERROR(1126, "账号不能和原账号相同!"),
+    ADMIN_PASSWORD_ERROR(1127, "密码输入错误!"),
+    ADMIN_USERNAME_EDIT_ERROR(1128, "用户名不可修改!"),
+    ADMIN_PARENT_USER_ERROR1(1130, "直属上级不能为自己!"),
+    ;
+
+    AdminCodeEnum(int code, String msg) {
+        this.code = code;
+        this.msg = msg;
+    }
+
+    private int code;
+    private String msg;
+
+    @Override
+    public int getCode() {
+        return code;
+    }
+
+    @Override
+    public String getMsg() {
+        return msg;
+    }
+}

+ 28 - 0
admin/admin/src/main/java/com/kakarote/admin/common/AdminConst.java

@@ -0,0 +1,28 @@
+package com.kakarote.admin.common;
+
+import com.kakarote.core.common.Const;
+
+/**
+ * @author zhangzhiwei
+ * 系统管理模块的常量
+ */
+public class AdminConst extends Const {
+    /**
+     * 默认的权限缓存KEY
+     */
+    public static final String DEFAULT_AUTH_CACHE_NAME = "CRM:AUTH";
+
+    /**
+     * 默认的密码强度正则
+     */
+    public static final String DEFAULT_PASSWORD_INTENSITY = "^(?=.*[a-zA-Z])(?=.*\\d).{6,20}$";
+
+    /** 校验返回结果码 */
+    public final static String UNIQUE = "0";
+
+    public final static String NOT_UNIQUE = "1";
+
+    public static final String SYS_DICT_KEY = "sd-";
+
+    public static final String RELATION_DICT_KEY="rd-";
+}

+ 174 - 0
admin/admin/src/main/java/com/kakarote/admin/common/AdminDictUtils.java

@@ -0,0 +1,174 @@
+package com.kakarote.admin.common;
+
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.entity.PO.AdminDictMatch;
+import com.kakarote.admin.mapper.AdminDictDataMapper;
+import com.kakarote.admin.mapper.AdminDictMatchMapper;
+import com.kakarote.core.common.Const;
+import com.kakarote.core.redis.Redis;
+import com.kakarote.admin.entity.PO.AdminDictData;
+
+import java.util.*;
+
+import com.kakarote.core.servlet.ApplicationContextHolder;
+import com.kakarote.core.utils.BaseUtil;
+import com.kakarote.core.utils.SpringUtils;
+import com.kakarote.core.utils.UserUtil;
+import org.apache.ibatis.javassist.expr.NewArray;
+
+import java.util.List;
+
+/**
+ * @Description 字典项工具类
+ * @Author PangZhen
+ * @Date 2020-11-16 16:48
+ */
+public class AdminDictUtils {
+
+    public static final String SYS_DICT_CHAR = "-";
+
+    /**
+     * 设置字典缓存
+     *
+     * @param key 参数键
+     * @param dictDatas 字典数据列表
+     */
+    public static void setDictCache(Long tenantId, String key, List<AdminDictData> dictDatas)
+    {
+        Redis redis = BaseUtil.getRedis();
+
+//        System.out.println("setDictCache"+ getCacheKey(tenantId, key));
+        redis.set(getCacheKey(tenantId, key), dictDatas);
+//        System.out.println("setDictCacheOK");
+    }
+
+    /**
+     * 获取字典缓存
+     *
+     * @param key 参数键
+     * @return dictDatas 字典数据列表
+     */
+    public static List<AdminDictData> getDictCache(String key)
+    {
+        Redis redis = BaseUtil.getRedis();
+//        System.out.println("getDictCache"+ getCacheKey(UserUtil.getUser().getTenantId(), key));
+        Object cacheObj = redis.get(getCacheKey(UserUtil.getUser().getTenantId(), key));
+        if (cacheObj != null)
+        {
+//            System.out.println("cacheObj != null:=="+key);
+            List<AdminDictData> dictDatas = (List<AdminDictData>)cacheObj;
+            return dictDatas;
+        }else{
+            List<AdminDictData> dictDatas = ApplicationContextHolder.getBean(AdminDictDataMapper.class)
+                    .selectDictDataByType(key, UserUtil.getUser().getTenantId());
+            setDictCache(UserUtil.getUser().getTenantId(), key, dictDatas);
+//            System.out.println("dictDatas=="+dictDatas.size());
+        }
+        return null;
+    }
+
+
+    /**
+     * 获取字典缓存
+     *
+     * @param key 参数键
+     * @return dictDatas 字典数据列表
+     */
+    public static String getDictLabel(String key,String value)
+    {
+        List<AdminDictData> dictDatas = getDictCache(key);
+        for(AdminDictData data : dictDatas){
+            if(data.getDictValue().equals(value)){
+                return data.getDictLabel();
+            }
+        }
+        return null;
+    }
+
+    /**
+     * 清空字典缓存
+     */
+    public static void clearDictCache()
+    {
+        Redis redis = BaseUtil.getRedis();
+        //此处使用*无法匹配相应key,未能实际清除缓存-->改为获取所有后遍历重组
+        Set<String> keys = redis.keys(AdminConst.SYS_DICT_KEY + UserUtil.getUser().getTenantId() + SYS_DICT_CHAR + "*");
+
+//        Set<String> keys2 = redis.keys("*");
+//        Set<String> keyDel = new HashSet<>();
+//        System.out.println("key-size=="+keys2.size());
+//        for(String key : keys2){
+//            System.out.println("key=="+key);
+//            if(key.contains(AdminConst.SYS_DICT_KEY + UserUtil.getUser().getTenantId())){
+//                keyDel.add(key);
+//            }
+//        }
+        redis.delKeys(keys);
+
+    }
+
+    /**
+     * 设置cache key
+     *
+     * @param configKey 参数键
+     * @return 缓存键key
+     */
+    public static String getCacheKey(Long tenantId, String configKey)
+    {
+//        System.out.println("getCacheKey"+ (AdminConst.SYS_DICT_KEY + tenantId + SYS_DICT_CHAR + configKey));
+        return AdminConst.SYS_DICT_KEY + tenantId + SYS_DICT_CHAR + configKey;
+    }
+
+    /**
+    * @Description:清除关联字典缓存
+    * @author shz
+    * @date 2022-4-22 11:40
+    * @param 
+    * @return 
+    */
+    public static void clearRelationDictCache(Long tenantId,String matchDict,String value) {
+        Redis redis = BaseUtil.getRedis();
+        //此处使用*无法匹配相应key,未能实际清除缓存-->改为获取所有后遍历重组
+        Set<String> keys = redis.keys(Const.RELATION_DICT_KEY + tenantId + SYS_DICT_CHAR +matchDict+SYS_DICT_CHAR+value);
+        redis.delKeys(keys);
+
+    }
+    /**
+    * @Description:关联字典缓存
+    * @author shz
+    * @date 2022-4-22 14:39
+    * @param 
+    * @return 
+    */
+    public static void setDictMatchCache(Integer tenantId,String matchDict,String value ,String dictDatas) {
+        Redis redis = BaseUtil.getRedis();;
+        redis.set(Const.RELATION_DICT_KEY + tenantId + SYS_DICT_CHAR +matchDict+SYS_DICT_CHAR+value, dictDatas);
+    }
+    /**
+    * @Description:根据对应系统字典类型获取关联字典表
+    * @author shz
+    * @date 2022-4-22 14:40
+    * @param tenantId 租户id
+     * @param matchDict 对应系统代码
+     * @param value 本系统相关字典JSON数据
+    * @return 对应系统值
+    */
+    public static String getDictMatcValue (Integer tenantId,String matchDict,String value){
+        Redis redis = BaseUtil.getRedis();
+        Object cacheObj = redis.get(Const.RELATION_DICT_KEY + tenantId + SYS_DICT_CHAR +matchDict+ SYS_DICT_CHAR +value);
+        if (cacheObj != null)
+        {
+            String dictDatas = (String)cacheObj;
+            return dictDatas;
+        }else{
+            Map dictDatas = ApplicationContextHolder.getBean(AdminDictMatchMapper.class)
+                    .selectDictMatchByType(matchDict,value,tenantId);
+            String str = "";
+            if(dictDatas != null ){
+                str = new JSONObject(dictDatas).toJSONString();
+                setDictMatchCache(tenantId,matchDict,value,str);
+            }
+            return str;
+        }
+    }
+}

+ 81 - 0
admin/admin/src/main/java/com/kakarote/admin/common/AdminModuleEnum.java

@@ -0,0 +1,81 @@
+package com.kakarote.admin.common;
+
+/**
+ * @author zhangzhiwei
+ * 模块的枚举
+ */
+
+public enum AdminModuleEnum {
+
+    /**
+     * 任务审批
+     */
+    TASK_EXAMINE("taskExamine"),
+    /**
+     * crm模块
+     */
+    CRM("crm"),
+    /**
+     * 项目管理
+     */
+    PROJECT("project"),
+    /**
+     * 日志模块
+     */
+    LOG("log"),
+    /**
+     * 通讯录模块
+     */
+    BOOK("book"),
+    /**
+     * 办公模块
+     */
+    OA("oa"),
+    /**
+     * 商业智能模块
+     */
+    BI("bi"),
+    /**
+     * 邮箱模块
+     */
+    EMAIL("email"),
+    /**
+     * 日历模块
+     */
+    CALENDAR("calendar"),
+    /**
+     * 知识库
+     */
+    KNOWLEDGE("knowledge"),
+    /**
+     * 呼叫中心
+     */
+    CALL("call"),
+    /**
+     * 名片小程序
+     */
+    CARD("applet"),
+
+    HRM("hrm"),
+
+    JXC("jxc");
+
+    private AdminModuleEnum(String value) {
+        this.value = value;
+    }
+
+    private String value;
+
+    public String getValue() {
+        return this.value;
+    }
+
+    public static String[] getValues() {
+        String[] values = new String[values().length];
+        for (int i = 0; i < values().length; i++) {
+            values[i] = values()[i].getValue();
+        }
+        return values;
+    }
+
+}

+ 47 - 0
admin/admin/src/main/java/com/kakarote/admin/common/AdminRoleTypeEnum.java

@@ -0,0 +1,47 @@
+package com.kakarote.admin.common;
+
+/**
+ * 角色类型枚举
+ *
+ * @author zhangzhiwei
+ */
+public enum AdminRoleTypeEnum {
+    /**
+     * 自定义
+     */
+    CUSTOM(0),
+    MANAGER(1),
+    CUSTOMER_MANAGER(2),
+    PERSONNEL(3),
+    FINANCE(4),
+    WORK(5),
+    OA(7),
+    PROJECT(8),
+    HRM(9),
+    JXC(10)
+    ;
+
+    AdminRoleTypeEnum(Integer type) {
+        this.type = type;
+    }
+
+    private Integer type;
+
+    public Integer getType() {
+        return type;
+    }
+
+    public void setType(Integer type) {
+        this.type = type;
+    }
+
+    public static AdminRoleTypeEnum parse(Integer type) {
+        for (AdminRoleTypeEnum typeEnum : values()) {
+            if (typeEnum.getType().equals(type)) {
+                return typeEnum;
+            }
+        }
+        return null;
+    }
+
+}

+ 42 - 0
admin/admin/src/main/java/com/kakarote/admin/common/EncryptableResolver.java

@@ -0,0 +1,42 @@
+package com.kakarote.admin.common;
+
+import com.kakarote.core.utils.EncryptorUtil;
+import com.ulisesbocchio.jasyptspringboot.EncryptablePropertyResolver;
+import org.jasypt.encryption.pbe.StandardPBEStringEncryptor;
+import org.jasypt.encryption.pbe.config.EnvironmentStringPBEConfig;
+import org.springframework.stereotype.Component;
+
+/**
+ * 配置项解密
+ */
+@Component(value = "encryptablePropertyResolver")
+public class EncryptableResolver implements EncryptablePropertyResolver {
+    //加密工具
+    private static StandardPBEStringEncryptor ENCRYPTOR = new StandardPBEStringEncryptor();
+
+    static {
+        EnvironmentStringPBEConfig config = new EnvironmentStringPBEConfig();
+        config.setPassword(getPassword());//加密所需的salt(盐)
+        ENCRYPTOR.setConfig(config);
+    }
+
+    @Override
+    public String resolvePropertyValue(String value) {
+        if (null != value && value.contains("ENC(")) {
+            return EncryptorUtil.decrypt(ENCRYPTOR, value);
+        }
+        return value;
+    }
+    //独有的加密盐 这里建议修改
+    private static String getPassword(){
+        return "ADMIN_WUDAOWEN";
+    }
+    /**
+     * 密码生成
+     * @param args
+     */
+    public static void main(String[] args){
+        EncryptorUtil.encryption("root",getPassword());
+    }
+
+}

+ 74 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminCommonController.java

@@ -0,0 +1,74 @@
+package com.kakarote.admin.controller;
+
+import com.kakarote.admin.entity.PO.AdminUser;
+import com.kakarote.admin.service.IAdminCommonService;
+import com.kakarote.admin.service.IAdminUserService;
+import com.kakarote.core.common.BusinessTypeEntity;
+import com.kakarote.core.common.R;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.entity.UserInfo;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ * 通用 前端控制器
+ * </p>
+ *
+ * @author wudw
+ * @since 2021-03-12
+ */
+@RestController
+@RequestMapping("/adminCommon")
+@Api(tags = "系统配置接口")
+@Slf4j
+public class AdminCommonController {
+
+    @Autowired
+    private IAdminCommonService commonService;
+
+    @Autowired
+    private IAdminUserService adminUserService;
+
+    /**
+     * 业务类型
+     */
+    @ApiOperation(value = "获取业务类型")
+    @PostMapping("/getBType")
+    public Result<List<BusinessTypeEntity>> setAdminConfig() {
+        List<BusinessTypeEntity> list = commonService.getAllBusinessType();
+        return R.ok(list);
+    }
+
+    /**
+     * 自定义字典查询
+     */
+    @ApiOperation(value = "获取自定义字典")
+    @PostMapping("/getDict")
+    public Result<List<Map<String,Object>>> setAdminConfig(@RequestBody Map<String,String> params) {
+        List<Map<String,Object>> list = commonService.selectCustomList(params);
+        return R.ok(list);
+    }
+
+
+    /**
+     * 切换项目
+     */
+    @ApiOperation(value = "切换项目")
+    @PostMapping("/changeProject/{projectId}")
+    public Result changeProjectr(@PathVariable Integer projectId) {
+        UserInfo userInfo = UserUtil.getUser();
+        AdminUser adminUser = adminUserService.getById(userInfo.getUserId());
+        adminUser.setProjectId(projectId);
+        adminUserService.updateById(adminUser);
+        return Result.ok();
+    }
+
+}

+ 373 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminConfigController.java

@@ -0,0 +1,373 @@
+package com.kakarote.admin.controller;
+
+import cn.hutool.core.bean.BeanUtil;
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.kakarote.admin.common.AdminCodeEnum;
+import com.kakarote.admin.common.AdminConst;
+import com.kakarote.admin.common.AdminModuleEnum;
+import com.kakarote.admin.entity.BO.AdminCompanyBO;
+import com.kakarote.admin.entity.BO.LogWelcomeSpeechBO;
+import com.kakarote.admin.entity.BO.ModuleSettingBO;
+import com.kakarote.admin.entity.PO.AdminConfig;
+import com.kakarote.admin.entity.PO.AdminModelSort;
+import com.kakarote.admin.entity.PO.AdminUserConfig;
+import com.kakarote.admin.entity.VO.ModuleSettingVO;
+import com.kakarote.admin.service.IAdminConfigService;
+import com.kakarote.admin.service.IAdminFileService;
+import com.kakarote.admin.service.IAdminModelSortService;
+import com.kakarote.admin.service.IAdminUserConfigService;
+import com.kakarote.core.common.ApiExplain;
+import com.kakarote.core.common.Const;
+import com.kakarote.core.common.R;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.redis.Redis;
+import com.kakarote.core.servlet.upload.UploadEntity;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import io.swagger.annotations.ApiParam;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.web.multipart.MultipartFile;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.validation.Valid;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.stream.Collectors;
+
+
+/**
+ * <p>
+ * 客户规则 前端控制器
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+@RestController
+@RequestMapping("/adminConfig")
+@Api(tags = "系统配置接口")
+@Slf4j
+public class AdminConfigController {
+
+    @Autowired
+    private IAdminConfigService adminConfigService;
+
+    @Autowired
+    private IAdminFileService adminFileService;
+
+    @Autowired
+    private IAdminUserConfigService adminUserConfigService;
+
+    @Autowired
+    private IAdminModelSortService adminModelSortService;
+
+
+    /**
+     * 设置系统配置
+     */
+    @ApiOperation(value = "设置企业配置")
+    @PostMapping("/setAdminConfig")
+    public Result setAdminConfig(@RequestParam(value = "file",required = false)
+                                 @ApiParam("文件") MultipartFile file,
+                                 @ApiParam("name") String name) {
+        AdminCompanyBO adminCompanyBO = new AdminCompanyBO();
+        adminCompanyBO.setCompanyName(name);
+        try {
+            if (file != null && file.getSize() > 1) {
+                UploadEntity img = adminFileService.upload(file, null, "img","0");
+                adminCompanyBO.setCompanyLogo(img.getUrl());
+            }
+        } catch (IOException ignored) {
+        }
+        adminConfigService.setAdminConfig(adminCompanyBO);
+        return Result.ok();
+    }
+
+    /**
+     * 查询企业配置
+     *
+     * @return Result
+     * @author zhangzhiwei
+     */
+    @ApiOperation(value = "查询企业配置")
+    @PostMapping("/queryAdminConfig")
+    public Result<AdminCompanyBO> queryAdminConfig() {
+        return R.ok(adminConfigService.queryAdminConfig());
+    }
+
+    @ApiOperation(value = "头部设置")
+    @PostMapping("/queryHeaderModelSort")
+    public Result<List<String>> queryHeaderModelSort() {
+        List<AdminModelSort> list = adminModelSortService.lambdaQuery().select(AdminModelSort::getModel)
+                .eq(AdminModelSort::getType, 1)
+                .eq(AdminModelSort::getUserId, UserUtil.getUserId())
+                .list();
+        return Result.ok(list.stream().map(AdminModelSort::getModel).collect(Collectors.toList()));
+    }
+
+    @ApiOperation(value = "头部设置")
+    @PostMapping("/setHeaderModelSort")
+    public Result setHeaderModelSort(@RequestBody List<String> list) {
+        List<AdminModelSort> modelSortList = new ArrayList<>();
+        for (int i = 0; i < list.size(); i++) {
+            AdminModelSort adminModelSort = new AdminModelSort();
+            adminModelSort.setType(1).setModel(list.get(i)).setSort(i).setIsHidden(0).setUserId(UserUtil.getUserId());
+            modelSortList.add(adminModelSort);
+        }
+        LambdaQueryWrapper<AdminModelSort> wrapper = new LambdaQueryWrapper<>();
+        wrapper.eq(AdminModelSort::getType, 1).eq(AdminModelSort::getUserId, UserUtil.getUserId());
+        adminModelSortService.remove(wrapper);
+        adminModelSortService.saveBatch(modelSortList, Const.BATCH_SAVE_SIZE);
+        return R.ok();
+    }
+
+    @ApiOperation(value = "设置活动咨询状态")
+    @PostMapping("/setMarketing")
+    public Result setMarketing(@RequestParam("status") Integer status) {
+       adminConfigService.setMarketing(status);
+       return R.ok();
+    }
+
+
+    @ApiOperation(value = "查询活动咨询状态")
+    @PostMapping("/queryMarketing")
+    public Result queryMarketing() {
+        return R.ok(adminConfigService.queryMarketing());
+    }
+
+    /**
+     * 查询企业模块配置
+     *
+     * @author zhangzhiwei
+     */
+    @ApiOperation(value = "查询企业模块配置")
+    @PostMapping("/queryModuleSetting")
+    public Result<List<ModuleSettingVO>> queryModuleSetting() {
+        return R.ok(adminConfigService.queryModuleSetting());
+    }
+
+    /**
+     * 设置企业模块
+     *
+     * @param moduleSetting data
+     */
+    @ApiOperation(value = "设置企业模块")
+    @PostMapping("/setModuleSetting")
+    public Result setModuleSetting(@Valid @RequestBody ModuleSettingBO moduleSetting) {
+        AdminConfig adminConfig = adminConfigService.getById(moduleSetting.getSettingId());
+        if (AdminModuleEnum.CRM.getValue().equals(adminConfig.getName())) {
+            return R.error(AdminCodeEnum.ADMIN_MODULE_CLOSE_ERROR);
+        }
+        adminConfig.setStatus(moduleSetting.getStatus());
+        adminConfigService.setModuleSetting(adminConfig);
+        return Result.ok();
+    }
+
+    @ApiOperation(value = "设置日志欢迎语")
+    @PostMapping("/setLogWelcomeSpeech")
+    public Result setLogWelcomeSpeech(@Valid @RequestBody List<String> stringList) {
+        adminConfigService.setLogWelcomeSpeech(stringList);
+        return Result.ok();
+    }
+
+    /**
+     * 获取日志欢迎语列表
+     */
+    @ApiOperation(value = "获取日志欢迎语")
+    @PostMapping("/getLogWelcomeSpeechList")
+    public Result<List<LogWelcomeSpeechBO>> getLogWelcomeSpeechList() {
+        List<LogWelcomeSpeechBO> adminConfigs = adminConfigService.getLogWelcomeSpeechList();
+        return R.ok(adminConfigs);
+    }
+
+    /**
+     * 删除配置数据
+     */
+    @ApiOperation(value = "删除配置数据")
+    @PostMapping("/deleteConfigById")
+    public Result deleteConfigById(@RequestBody @ApiParam(name = "settingId", value = "主键ID", required = true) Integer settingId) {
+        if (settingId == null) {
+            return R.error(AdminCodeEnum.ADMIN_DATA_EXIST_ERROR);
+        }
+        adminConfigService.removeById(settingId);
+        return R.ok();
+    }
+
+    /**
+     * 查询呼叫中心设置
+     */
+    @ApiOperation(value = "查询手机端模块设置")
+    @PostMapping("/queryCallModuleSetting")
+    public Result<ModuleSettingVO> queryCallModuleSetting() {
+        ModuleSettingVO moduleSettingVO = adminConfigService.queryCallModuleSetting();
+        return R.ok(moduleSettingVO);
+    }
+
+    @ApiOperation(value = "查询手机端模块配置")
+    @PostMapping("/queryMobileModuleSetting")
+    public Result<JSONArray> queryMobileModuleSetting() {
+        String name = "MobileModuleSetting";
+        AdminUserConfig userConfig = adminUserConfigService.queryUserConfigByName(name);
+        if (userConfig == null) {
+            return Result.ok(new JSONArray());
+        }
+        return Result.ok(JSON.parseArray(userConfig.getValue()));
+    }
+
+    /**
+     * 修改手机端模块设置
+     */
+
+    @ApiOperation(value = "修改手机端模块配置")
+    @PostMapping("/setMobileModuleSetting")
+    public Result setMobileModuleSetting(@RequestBody JSONArray json) {
+        String name = "MobileModuleSetting";
+        AdminUserConfig userConfig = adminUserConfigService.queryUserConfigByName(name);
+        if (userConfig != null) {
+            userConfig.setValue(json.toJSONString());
+            adminUserConfigService.updateById(userConfig);
+        } else {
+            userConfig = new AdminUserConfig();
+            userConfig.setStatus(1);
+            userConfig.setName("MobileModuleSetting");
+            userConfig.setValue(json.toJSONString());
+            userConfig.setUserId(UserUtil.getUserId());
+            userConfig.setDescription("手机端模块设置");
+            adminUserConfigService.save(userConfig);
+        }
+        return R.ok();
+    }
+
+    @ApiOperation(value = "设置跟进记录常用语")
+    @PostMapping("/setActivityPhrase")
+    public Result setActivityPhrase(@RequestBody List<String> stringList) {
+        String name = "ActivityPhrase";
+        Long userId = UserUtil.getUserId();
+        String description = "跟进记录常用语";
+        adminUserConfigService.deleteUserConfigByName(name);
+        List<AdminUserConfig> adminUserConfigList = new ArrayList<>(stringList.size());
+        stringList.forEach(str -> {
+            AdminUserConfig userConfig = new AdminUserConfig();
+            userConfig.setStatus(1);
+            userConfig.setName(name);
+            userConfig.setValue(str);
+            userConfig.setUserId(userId);
+            userConfig.setDescription(description);
+            adminUserConfigList.add(userConfig);
+        });
+        adminUserConfigService.saveBatch(adminUserConfigList, AdminConst.BATCH_SAVE_SIZE);
+        return R.ok();
+    }
+
+    @ApiOperation(value = "设置跟进记录类型")
+    @PostMapping("/setRecordOptions")
+    public Result setRecordOptions(@RequestBody List<String> stringList) {
+        String name = "followRecordOption";
+        String description = "跟进记录选项";
+        adminConfigService.removeByMap(new JSONObject().fluentPut("name", name));
+        List<AdminConfig> adminUserConfigList = new ArrayList<>(stringList.size());
+        stringList.forEach(str -> {
+            AdminConfig userConfig = new AdminConfig();
+            userConfig.setStatus(1);
+            userConfig.setName(name);
+            userConfig.setValue(str);
+            userConfig.setDescription(description);
+            adminUserConfigList.add(userConfig);
+        });
+        adminConfigService.saveBatch(adminUserConfigList, AdminConst.BATCH_SAVE_SIZE);
+        return R.ok();
+    }
+
+    @ApiOperation(value = "设置报销费用类型")
+    @PostMapping("/setExamineExpenseType")
+    public Result setExamineExpenseType(@RequestBody List<String> stringList) {
+        String name = "examineExpenseType";
+        String description = "报销费用类型";
+        adminConfigService.removeByMap(new JSONObject().fluentPut("name", name));
+        List<AdminConfig> adminUserConfigList = new ArrayList<>(stringList.size());
+        stringList.forEach(str -> {
+            AdminConfig userConfig = new AdminConfig();
+            userConfig.setStatus(1);
+            userConfig.setName(name);
+            userConfig.setValue(str);
+            userConfig.setDescription(description);
+            adminUserConfigList.add(userConfig);
+        });
+        adminConfigService.saveBatch(adminUserConfigList, AdminConst.BATCH_SAVE_SIZE);
+        return R.ok();
+    }
+
+
+    @PostMapping("/queryExamineExpenseType")
+    @ApiOperation("查询报销费用列表")
+    public Result<List<String>> queryRecordOptions() {
+        List<String> strings = adminConfigService.queryRecordOptions();
+        return Result.ok(strings);
+    }
+
+
+    /**
+     * 查询跟进记录常用语
+     */
+    @ApiOperation(value = "查询跟进记录常用语")
+    @PostMapping("/queryActivityPhrase")
+    public Result<List<String>> queryActivityPhrase() {
+        String name = "ActivityPhrase";
+        List<AdminUserConfig> adminConfigList = adminUserConfigService.queryUserConfigListByName(name);
+        return Result.ok(adminConfigList.stream().map(AdminUserConfig::getValue).collect(Collectors.toList()));
+    }
+
+    @ApiExplain(value = "查询config配置")
+    @RequestMapping("/queryConfigByName")
+    public Result<List<com.kakarote.core.feign.admin.entity.AdminConfig>> queryConfigByName(@RequestParam("name") String name) {
+        List<AdminConfig> adminConfigs = adminConfigService.queryConfigListByName(name);
+        return Result.ok(adminConfigs.stream().map(config -> BeanUtil.copyProperties(config, com.kakarote.core.feign.admin.entity.AdminConfig.class)).collect(Collectors.toList()));
+    }
+    @Autowired
+    private Redis redis;
+    @ApiExplain(value = "查询config配置")
+    @RequestMapping("/queryFirstConfigByName")
+    public Result<com.kakarote.core.feign.admin.entity.AdminConfig> queryFirstConfigByName(@RequestParam("name") String name, HttpServletRequest request) {
+        String token = request.getHeader("ADMIN-TOKEN");
+        log.info("ADMIN-TOKEN:{}",token);
+        Object data = redis.get(token);
+        log.info("userInfo:{}",JSON.toJSONString(data));
+        AdminConfig config = adminConfigService.queryConfigByName(name);
+        return Result.ok(BeanUtil.copyProperties(config, com.kakarote.core.feign.admin.entity.AdminConfig.class));
+    }
+
+    @ApiExplain(value = "修改config配置")
+    @PostMapping("/updateAdminConfig")
+    public Result updateAdminConfig(@RequestBody AdminConfig adminConfig) {
+        adminConfigService.updateAdminConfig(adminConfig);
+        return R.ok();
+    }
+    @ApiExplain(value = "修改config配置")
+    @PostMapping("/updateAdminConfigNoTenantId")
+    public Result updateAdminConfigNoTenantId(@RequestBody AdminConfig adminConfig) {
+        adminConfigService.updateAdminConfigNoTenantId(adminConfig);
+        return R.ok();
+    }
+    @ApiExplain(value = "查询config配置")
+    @RequestMapping("/queryFirstConfigByNameAndValue")
+    public Result<com.kakarote.core.feign.admin.entity.AdminConfig> queryFirstConfigByNameAndValue(@RequestParam("name") String name,
+                                                                                                   @RequestParam("value") String value) {
+        AdminConfig config = adminConfigService.queryFirstConfigByNameAndValue(name, value);
+        return Result.ok(BeanUtil.copyProperties(config, com.kakarote.core.feign.admin.entity.AdminConfig.class));
+    }
+
+    @ApiExplain(value = "查询config配置")
+    @RequestMapping("/queryConfigByNameAndTenantId")
+    public Result<List<com.kakarote.core.feign.admin.entity.AdminConfig>> queryConfigByNameAndTenantId(@RequestParam("name") String name) {
+        List<AdminConfig> adminConfigs = adminConfigService.queryConfigByNameAndTenantId(name);
+        return Result.ok(adminConfigs.stream().map(config -> BeanUtil.copyProperties(config, com.kakarote.core.feign.admin.entity.AdminConfig.class)).collect(Collectors.toList()));
+    }
+}
+

+ 96 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminDeptConfigController.java

@@ -0,0 +1,96 @@
+package com.kakarote.admin.controller;
+
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.entity.BO.AdminDeptConfigBO;
+import com.kakarote.admin.entity.PO.AdminDeptConfig;
+import com.kakarote.admin.service.IAdminDeptConfigService;
+import com.kakarote.core.common.*;
+import com.kakarote.core.entity.BasePage;
+import io.seata.spring.annotation.GlobalTransactional;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+import java.util.Map;
+import java.util.stream.Collectors;
+
+/**
+ * <p>
+ * 前端控制器
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-16
+ */
+@RestController
+@RequestMapping("/adminDeptConfig")
+public class AdminDeptConfigController {
+    @Autowired
+    IAdminDeptConfigService adminDeptConfigService;
+
+    @PostMapping("/queryConfigList")
+    @ApiOperation("分页查询对接配置列表")
+    @OperateLog(detail = "新增部门(租户)--系统管理员用", types = LogTypes.SYS, behavior = LogBehavior.SELECT)
+    public Result<BasePage<AdminDeptConfig>> queryConfigList(@RequestBody AdminDeptConfigBO adminConfigBO) {
+        return R.ok(adminDeptConfigService.queryConfigList(adminConfigBO));
+    }
+
+    @GetMapping("/getInfo/{id}")
+    @ApiOperation("获取对接配置")
+    @OperateLog(detail = "获取对接配置--系统管理员用", types = LogTypes.SYS, behavior = LogBehavior.DELETE)
+    public Result<AdminDeptConfig> getInfo(@PathVariable("id") String id) {
+        return R.ok(adminDeptConfigService.getById(id));
+    }
+
+    @PostMapping("/addOrUpdateConfig")
+    @ApiOperation("新增/修改对接配置")
+    @OperateLog(detail = "新增/修改对接配置--系统管理员用", types = LogTypes.SYS, behavior = LogBehavior.INSERT)
+    public Result addOrUpdateConfig(@RequestBody AdminDeptConfig adminDeptConfig) {
+        return adminDeptConfigService.addOrUpdateConfig(adminDeptConfig);
+    }
+
+//    @PostMapping("/updateConfig")
+//    @ApiOperation("修改对接配置")
+//    @OperateLog(detail="修改对接配置--系统管理员用",types= LogTypes.SYS,behavior=LogBehavior.UPDATE)
+//    public Result updateConfig(@RequestBody AdminDeptConfig adminDeptConfig) {
+//        adminDeptConfigService.updateById(adminDeptConfig);
+//        return R.ok();
+//    }
+
+    @PostMapping("/delConfig")
+    @ApiOperation("删除对接配置")
+    @OperateLog(detail = "删除对接配置--系统管理员用", types = LogTypes.SYS, behavior = LogBehavior.DELETE)
+    public Result delConfig(@RequestBody Map<String, Object> param) {
+        adminDeptConfigService.removeByMap(param);
+        return R.ok();
+    }
+
+
+    @GetMapping("/getConfig/{configId}")
+    @ApiOperation("获取租户配置")
+    public Result<JSONObject> getConfig(@PathVariable String configId) {
+        AdminDeptConfig adminDeptConfig = adminDeptConfigService.getById(configId);
+        if (adminDeptConfig == null) {
+            return Result.error(-1, "参数出现异常");
+        }
+        String config = adminDeptConfig.getParams();
+        return Result.ok(JSONObject.parseObject(config));
+    }
+
+    @GetMapping("/queryDeptConfigForMessage/{type}/{messageType}/{tenantId}")
+    @ApiOperation("消息:获取配置")
+    public Result<JSONObject> queryDeptConfigForMessage(@PathVariable("type") String type, @PathVariable("messageType") String messageType,
+                                                        @PathVariable("tenantId") Long tenantId) {
+        AdminDeptConfig adminDeptConfig = adminDeptConfigService.lambdaQuery()
+                .eq(AdminDeptConfig::getType, type)
+                .like(AdminDeptConfig::getMessageType, "%" + messageType + "%")
+                .eq(AdminDeptConfig::getTenantId, tenantId).one();
+        if (adminDeptConfig == null) {
+            return Result.error(-1, "参数出现异常");
+        }
+        return Result.ok(JSONObject.parseObject(JSON.toJSONString(adminDeptConfig)));
+    }
+}
+

+ 136 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminDeptController.java

@@ -0,0 +1,136 @@
+package com.kakarote.admin.controller;
+
+
+import cn.hutool.core.bean.BeanUtil;
+import com.kakarote.admin.entity.BO.AdminDeptBO;
+import com.kakarote.admin.entity.BO.AdminDeptQueryBO;
+import com.kakarote.admin.entity.PO.AdminDept;
+import com.kakarote.admin.entity.VO.AdminDeptVO;
+import com.kakarote.admin.service.IAdminDeptService;
+import com.kakarote.admin.service.impl.AdminMenuServiceImpl;
+import com.kakarote.core.common.*;
+import com.kakarote.core.feign.admin.entity.SimpleDept;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import javax.validation.Valid;
+import javax.validation.constraints.NotNull;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ * 部门表 前端控制器
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+@RestController
+@RequestMapping("/adminDept")
+@Api(tags = "部门管理相关接口")
+public class AdminDeptController {
+
+    @Autowired
+    private IAdminDeptService adminDeptService;
+    @Autowired
+    private AdminMenuServiceImpl adminMenuService;
+
+    @PostMapping("/queryDeptTree")
+    @ApiOperation("查询部门列表树")
+    @OperateLog(detail = "查询部门列表树", types = LogTypes.SYS, behavior = LogBehavior.SELECT)
+    public Result<List<AdminDeptVO>> queryDeptTree(@RequestBody AdminDeptQueryBO queryBO) {
+        List<AdminDeptVO> deptList = adminDeptService.queryDeptTree(queryBO);
+        return Result.ok(deptList);
+    }
+
+    @PostMapping("/addDept")
+    @ApiOperation("新增部门")
+    @OperateLog(detail = "新增部门", types = LogTypes.SYS, behavior = LogBehavior.INSERT)
+    public Result addDept(@RequestBody @Valid AdminDeptBO adminDept) {
+        Integer deptId = adminDeptService.addDept(adminDept);
+        return Result.ok();
+    }
+
+    @PostMapping("/setDept")
+    @ApiOperation("修改部门")
+    @OperateLog(detail = "修改部门(租户)", types = LogTypes.SYS, behavior = LogBehavior.UPDATE)
+    public Result setDept(@RequestBody @Valid AdminDeptBO adminDept) {
+        adminDeptService.setDept(adminDept);
+        return Result.ok();
+    }
+
+    @PostMapping("/deleteDept/{deptId}")
+    @ApiOperation("删除部门")
+    @OperateLog(detail = "删除部门", types = LogTypes.SYS, behavior = LogBehavior.DELETE)
+    public Result deleteDept(@PathVariable("deptId") Integer deptId) {
+        adminDeptService.deleteDept(deptId);
+        return Result.ok();
+    }
+
+    @RequestMapping("/getNameByDeptId")
+    @ApiExplain("根据部门ID获取部门名称")
+    @OperateLog(detail = "根据部门ID获取部门名称", types = LogTypes.SYS, behavior = LogBehavior.SELECT)
+    public Result getNameByDeptId(Integer deptId) {
+        return R.ok(adminDeptService.getNameByDeptId(deptId));
+    }
+
+    @RequestMapping("/getPIdByUser")
+    @ApiExplain("根据登录用户获取部门父ID")
+    @OperateLog(detail = "根据登录用户获取部门父ID", types = LogTypes.SYS, behavior = LogBehavior.SELECT)
+    public Result getPIdByUser() {
+        return R.ok(adminDeptService.getPIdByUser());
+    }
+
+    @RequestMapping("/queryChildDeptId")
+    @ApiExplain("根据部门ID下的子部门")
+    @OperateLog(detail = "根据部门ID下的子部门", types = LogTypes.SYS, behavior = LogBehavior.SELECT)
+    public Result<List<Integer>> queryChildDeptId(@NotNull Integer deptId) {
+        return R.ok(adminDeptService.queryChildDept(deptId));
+    }
+
+    @PostMapping("/queryDeptByIds")
+    @ApiExplain("根据部门ID获取用户")
+    @OperateLog(detail = "根据部门ID获取用户", types = LogTypes.SYS, behavior = LogBehavior.SELECT)
+    public Result<List<SimpleDept>> queryDeptByIds(@RequestBody List<Integer> ids) {
+        List<SimpleDept> simpleDepts = adminDeptService.queryDeptByIds(ids);
+        return R.ok(simpleDepts);
+    }
+
+    @RequestMapping("/getNameByDeptIdForAPP/{deptId}")
+    @ApiExplain("根据部门ID获取部门名称-app端")
+    @OperateLog(detail = "根据部门ID获取部门名称-app端", types = LogTypes.SYS, behavior = LogBehavior.SELECT)
+    public Result getNameByDeptIdForAPP(@PathVariable("deptId") Integer deptId) {
+        return R.ok(adminDeptService.getNameByDeptId(deptId));
+    }
+
+    @RequestMapping("/getParentId/{deptId}")
+    @ApiExplain("根据部门ID获取上级部门ID")
+    //@OperateLog(detail = "根据部门ID获取上级部门ID", types = LogTypes.SYS, behavior = LogBehavior.SELECT)
+    public Result getParentId(@PathVariable("deptId") Integer deptId) {
+        AdminDept adminDept = adminDeptService.getById(deptId);
+        if (adminDept != null) {
+            return R.ok(adminDept.getPid());
+        }
+        return R.ok();
+    }
+
+    @PostMapping("/addDeptMap")
+    @ApiOperation("同步账号:新增部门")
+    @OperateLog(detail = "同步账号:新增部门", types = LogTypes.SYS, behavior = LogBehavior.INSERT)
+    public Integer addDept(@RequestBody Map map) {
+        String name = map.get("name").toString();
+        //是否已存在
+        List<AdminDept> list = adminDeptService.lambdaQuery().eq(AdminDept::getName,name).list();
+        if(list.size() > 0){
+            return -1;
+        }
+        AdminDeptBO adminDept = new AdminDeptBO();
+        BeanUtil.copyProperties(map, adminDept);
+        Integer deptId = adminDeptService.addDept(adminDept);
+        return deptId;
+    }
+}
+

+ 114 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminDictDataController.java

@@ -0,0 +1,114 @@
+package com.kakarote.admin.controller;
+
+import java.util.List;
+
+import com.kakarote.core.common.LogBehavior;
+import com.kakarote.core.common.LogTypes;
+import com.kakarote.core.common.OperateLog;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+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.kakarote.admin.entity.PO.AdminDictData;
+import com.kakarote.admin.service.IAdminDictDataService;
+import com.kakarote.admin.service.IAdminDictTypeService;
+
+/**
+ * 数据字典信息
+ * 
+ * @author ruoyi
+ */
+@RestController
+@RequestMapping("/adminDict/data")
+public class AdminDictDataController {
+    @Autowired
+    private IAdminDictDataService dictDataService;
+    
+    @Autowired
+    private IAdminDictTypeService dictTypeService;
+
+    @GetMapping("/list")
+    @ApiOperation("查询字典表明细列表")
+    @OperateLog(detail = "查询字典表明细列表--管理员用",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Result list(AdminDictData dictData)
+    {
+        List<AdminDictData> list = dictDataService.selectDictDataList(dictData);
+        return Result.ok(list);
+    }
+
+//    @Log(title = "字典数据", businessType = BusinessType.EXPORT)
+//    @PreAuthorize(hasPermi = "system:dict:export")
+//    @PostMapping("/export")
+//    public void export(HttpServletResponse response, SysDictData dictData) throws IOException
+//    {
+//        List<SysDictData> list = dictDataService.selectDictDataList(dictData);
+//        ExcelUtil<SysDictData> util = new ExcelUtil<SysDictData>(SysDictData.class);
+//        util.exportExcel(response, list, "字典数据");
+//    }
+
+    /**
+     * 查询字典数据详细
+     */
+    @GetMapping(value = "/{dictCode}")
+    @ApiOperation("查询字典数据详细")
+    @OperateLog(detail = "查询字典数据详细--管理员用",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Result getInfo(@PathVariable Long dictCode)
+    {
+        return Result.ok(dictDataService.selectDictDataById(dictCode));
+    }
+
+    /**
+     * 根据字典类型查询字典数据信息
+     */
+    @GetMapping(value = "/type/{dictType}")
+    @ApiOperation("根据字典类型查询字典数据信息")
+    @OperateLog(detail = "根据字典类型查询字典数据信息",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Result dictType(@PathVariable String dictType)
+    {
+        return Result.ok(dictTypeService.selectDictDataByType(dictType));
+    }
+
+    /**
+     * 新增字典类型
+     */
+    @PostMapping
+    @ApiOperation("新增字典类型")
+    @OperateLog(detail = "新增字典类型",types= LogTypes.SYS ,behavior = LogBehavior.INSERT)
+    public Result add(@Validated @RequestBody AdminDictData dict)
+    {
+        dict.setCreateBy(UserUtil.getUser().getRealname());
+        return Result.ok(dictDataService.insertDictData(dict));
+    }
+
+    /**
+     * 修改保存字典类型
+     */
+    @PutMapping
+    @ApiOperation("修改保存字典类型")
+    @OperateLog(detail = "修改保存字典类型",types= LogTypes.SYS ,behavior = LogBehavior.UPDATE)
+    public Result edit(@Validated @RequestBody AdminDictData dict)
+    {
+        dict.setUpdateBy(UserUtil.getUser().getRealname());
+        return Result.ok(dictDataService.updateDictData(dict));
+    }
+
+    /**
+     * 删除字典类型
+     */
+    @DeleteMapping("/{dictCodes}")
+    @ApiOperation("删除字典类型")
+    @OperateLog(detail = "删除字典类型",types= LogTypes.SYS ,behavior = LogBehavior.UPDATE)
+    public Result remove(@PathVariable Long[] dictCodes)
+    {
+        return Result.ok(dictDataService.deleteDictDataByIds(dictCodes));
+    }
+}

+ 100 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminDictMatchController.java

@@ -0,0 +1,100 @@
+package com.kakarote.admin.controller;
+
+
+import com.alibaba.fastjson.JSON;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.kakarote.admin.common.AdminDictUtils;
+import com.kakarote.admin.entity.BO.AdminDictMathBO;
+import com.kakarote.admin.entity.PO.AdminDictMatch;
+import com.kakarote.admin.service.IAdminDictMatchService;
+import com.kakarote.core.common.*;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.entity.UserInfo;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ *  前端控制器
+ * </p>
+ *
+ * @author lzy
+ * @since 2021-11-30
+ */
+@RestController
+@RequestMapping("/adminDictMatch")
+public class AdminDictMatchController {
+
+
+    @Autowired
+    private IAdminDictMatchService adminDictMatchService;
+
+    @PostMapping("/list")
+    @ApiOperation("查询列表")
+    @OperateLog(detail = "查询列表", types = LogTypes.BUILD, behavior = LogBehavior.SELECT)
+    public Result<BasePage<AdminDictMatch>> list(@RequestBody AdminDictMathBO adminDictMathBO) {
+        BasePage<AdminDictMatch> list = adminDictMatchService.selectByPage(adminDictMathBO);
+        return Result.ok(list);
+    }
+
+    @PostMapping("/get/{id}")
+    @ApiOperation("查询字典转换详情")
+    @OperateLog(detail = "查询字典转换详情", types = LogTypes.BUILD, behavior = LogBehavior.SELECT)
+    public Result<AdminDictMatch> get(@PathVariable Integer id) {
+        AdminDictMatch adminDictMatch = adminDictMatchService.getById(id);
+        return Result.ok(adminDictMatch);
+    }
+
+    @PostMapping("/saveOrUpdate")
+    @ApiOperation("字典转换数据保持或更新")
+    @OperateLog(detail = "字典转换数据保持或更新", types = LogTypes.BUILD, behavior = LogBehavior.INSERT)
+    public Result save(@RequestBody AdminDictMatch adminDictMatch) {
+        UserInfo userInfo = UserUtil.getUser();
+        if (adminDictMatch.getId() == null) {
+            if(adminDictMatchService.save(adminDictMatch)){
+                /*字典表关联对接数据 redis处理  邵化振*/
+                AdminDictUtils.setDictMatchCache(userInfo.getTenantId().intValue(),adminDictMatch.getMatchDict(),adminDictMatch.getSelfDictValue(), JSON.toJSONString(adminDictMatch));
+            }
+        } else {
+            if(adminDictMatchService.updateById(adminDictMatch)){
+                AdminDictUtils.clearRelationDictCache(userInfo.getTenantId(),adminDictMatch.getMatchDict(),adminDictMatch.getSelfDictValue());
+                AdminDictUtils.setDictMatchCache(userInfo.getTenantId().intValue(),adminDictMatch.getMatchDict(),adminDictMatch.getSelfDictValue(), JSON.toJSONString(adminDictMatch));
+            }
+        }
+        return Result.ok();
+    }
+
+    @PostMapping("/delete/{selfDict}/{selfDictValue}")
+    @ApiOperation("根据本系统类型和本系统值删除字典转数据")
+    @OperateLog(detail = "根据本系统类型和本系统值删除字典转数据", types = LogTypes.BUILD, behavior = LogBehavior.DELETE)
+    public Result delete(@PathVariable String selfDict, @PathVariable String selfDictValue) {
+        Map<String, Object> where = new HashMap<>();
+        where.put("self_dict",selfDict);
+        where.put("self_dict_value",selfDictValue);
+        adminDictMatchService.removeByMap(where);
+        return R.ok();
+    }
+
+    @PostMapping("/delete/{id}")
+    @ApiOperation("删除字典转数据")
+    @OperateLog(detail = "删除字典转数据", types = LogTypes.BUILD, behavior = LogBehavior.DELETE)
+    public Result delete(@PathVariable Integer id) {
+        adminDictMatchService.removeById(id);
+        return R.ok();
+    }
+
+    @PostMapping("/selectSuggestList")
+    @ApiOperation("查询建议列表")
+    @OperateLog(detail = "查询建议列表", types = LogTypes.BUILD, behavior = LogBehavior.SELECT)
+    public Result<List<Map<String, Object>>> selectSuggestList(@RequestBody Map<String, Object> params) {
+        List<Map<String, Object>> list = adminDictMatchService.selectSuggestList(params);
+        return Result.ok(list);
+    }
+}
+

+ 149 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminDictTypeController.java

@@ -0,0 +1,149 @@
+package com.kakarote.admin.controller;
+
+import java.io.IOException;
+import java.util.List;
+import java.util.Map;
+import javax.servlet.http.HttpServletResponse;
+
+import com.kakarote.admin.entity.BO.AdminDictTypeBO;
+import com.kakarote.admin.entity.VO.AdminDeptVO;
+import com.kakarote.core.common.LogBehavior;
+import com.kakarote.core.common.LogTypes;
+import com.kakarote.core.common.OperateLog;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+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.kakarote.admin.entity.PO.AdminDictType;
+import com.kakarote.admin.service.IAdminDictTypeService;
+
+/**
+ * 数据字典信息
+ * 
+ * @author ruoyi
+ */
+@RestController
+@RequestMapping("/adminDict/type")
+@Api(tags = "字典管理相关接口")
+@Slf4j
+public class AdminDictTypeController {
+    @Autowired
+    private IAdminDictTypeService dictTypeService;
+
+    @RequestMapping("/list")
+    @ApiOperation("查询字典表列表")
+    @OperateLog(detail = "查询字典表列表--管理员用",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Result<BasePage<AdminDictType>> list(@RequestBody AdminDictTypeBO dictTypeBO)
+    {
+        BasePage<AdminDictType> list = dictTypeService.selectDictTypeList(dictTypeBO);
+        return Result.ok(list);
+    }
+
+    @RequestMapping("/custom")
+    @ApiOperation("自定义下拉框查询数据")
+    @OperateLog(detail = "自定义下拉框查询数据--页面控件用",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Result<List<AdminDictType>> custome(@RequestBody Map<String,String> params)
+    {
+        List<AdminDictType> list = dictTypeService.selectCustomList(params);
+        return Result.ok(list);
+    }
+
+//    @Log(title = "字典类型", businessType = BusinessType.EXPORT)
+//    @PreAuthorize(hasPermi = "system:dict:export")
+//    @PostMapping("/export")
+//    public void export(HttpServletResponse response, AdminDictType dictType) throws IOException
+//    {
+//        List<AdminDictType> list = dictTypeService.selectDictTypeList(dictType);
+//        ExcelUtil<AdminDictType> util = new ExcelUtil<AdminDictType>(AdminDictType.class);
+//        util.exportExcel(response, list, "字典类型");
+//    }
+
+    /**
+     * 查询字典类型详细
+     */
+    @GetMapping(value = "/{dictId}")
+    @ApiOperation("查询字典类型详细")
+    @OperateLog(detail = "查询字典类型详细",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Result getInfo(@PathVariable Long dictId)
+    {
+        return Result.ok(dictTypeService.selectDictTypeById(dictId));
+    }
+
+    /**
+     * 新增字典类型
+     */
+    @PostMapping
+    @ApiOperation("新增字典类型")
+    @OperateLog(detail = "新增字典类型",types= LogTypes.SYS ,behavior = LogBehavior.INSERT)
+    public Result add(@Validated @RequestBody AdminDictType dict)
+    {
+        //TODO
+//        if (UserConstants.NOT_UNIQUE.equals(dictTypeService.checkDictTypeUnique(dict)))
+//        {
+//            return AjaxResult.error("新增字典'" + dict.getDictName() + "'失败,字典类型已存在");
+//        }
+        dict.setCreateBy(UserUtil.getUser().getRealname());
+        return Result.ok(dictTypeService.insertDictType(dict));
+    }
+
+    /**
+     * 修改字典类型
+     */
+    @PutMapping
+    @ApiOperation("修改字典类型")
+    @OperateLog(detail = "修改字典类型",types= LogTypes.SYS ,behavior = LogBehavior.UPDATE)
+    public Result edit(@Validated @RequestBody AdminDictType dict)
+    {
+//        if (UserConstants.NOT_UNIQUE.equals(dictTypeService.checkDictTypeUnique(dict)))
+//        {
+//            return AjaxResult.error("修改字典'" + dict.getDictName() + "'失败,字典类型已存在");
+//        }
+        dict.setUpdateBy(UserUtil.getUser().getRealname());
+        return Result.ok(dictTypeService.updateDictType(dict));
+    }
+
+    /**
+     * 删除字典类型
+     */
+    @DeleteMapping("/{dictIds}")
+    @ApiOperation("删除字典类型")
+    @OperateLog(detail = "删除字典类型",types= LogTypes.SYS ,behavior = LogBehavior.DELETE)
+    public Result remove(@PathVariable Long[] dictIds)
+    {
+        return Result.ok(dictTypeService.deleteDictTypeByIds(dictIds));
+    }
+
+    /**
+     * 清空字典缓存
+     */
+    @DeleteMapping("/clearCache")
+    @ApiOperation("清空字典缓存")
+    @OperateLog(detail = "清空字典缓存",types= LogTypes.SYS ,behavior = LogBehavior.DELETE)
+    public Result clearCache()
+    {
+        dictTypeService.clearCache();
+        return Result.ok();
+    }
+
+//    /**
+//     * 获取字典选择框列表
+//     */
+//    @GetMapping("/optionselect")
+//    public AjaxResult optionselect()
+//    {
+//        List<AdminDictType> dictTypes = dictTypeService.selectDictTypeAll();
+//        return AjaxResult.success(dictTypes);
+//    }
+}

+ 221 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminFileController.java

@@ -0,0 +1,221 @@
+package com.kakarote.admin.controller;
+
+
+import cn.hutool.core.util.StrUtil;
+import com.kakarote.admin.entity.BO.AdminDeleteByBatchIdBO;
+import com.kakarote.admin.entity.BO.RenameFileBO;
+import com.kakarote.admin.entity.PO.AdminFile;
+import com.kakarote.admin.service.IAdminFileService;
+import com.kakarote.core.common.ApiExplain;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.common.SystemCodeEnum;
+import com.kakarote.core.exception.CrmException;
+import com.kakarote.core.servlet.LoginFromCookie;
+import com.kakarote.core.servlet.upload.FileEntity;
+import com.kakarote.core.servlet.upload.UploadEntity;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import io.swagger.annotations.ApiParam;
+import org.mvel2.util.Make;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.web.multipart.MultipartFile;
+
+import javax.servlet.http.HttpServletResponse;
+import javax.validation.constraints.NotNull;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ * 附件表 前端控制器
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+@RestController
+@RequestMapping("/adminFile")
+@Api(tags = "文件操作相关接口")
+public class AdminFileController {
+
+    @Autowired
+    private IAdminFileService adminFileService;
+
+    @PostMapping("/upload")
+    @ApiOperation("上传文件")
+    public Result<UploadEntity> upload(@RequestParam("file")
+                                       @ApiParam("文件") MultipartFile file,
+                                       @ApiParam("batchId") String batchId,
+                                       @ApiParam("文件类型") String type,
+                                       @RequestParam(value = "isPublic",required = false)String isPublic) throws IOException {
+        if (StrUtil.isEmpty(isPublic)){
+            isPublic = "0";
+        }
+        UploadEntity entity = adminFileService.upload(file, batchId, type,isPublic);
+        return Result.ok(entity);
+    }
+
+    @RequestMapping(value = "/queryFileList/{batchId}", method = RequestMethod.POST)
+    @ApiOperation(value = "通过批次ID查询文件列表", httpMethod = "POST")
+    public Result<List<FileEntity>> queryFileList(@NotNull @PathVariable String batchId) {
+        List<FileEntity> entityList = adminFileService.queryFileList(batchId);
+        return Result.ok(entityList);
+    }
+
+    @RequestMapping(value = "/queryById/{fileId}", method = RequestMethod.POST)
+    @ApiOperation(value = "通过ID查询文件", httpMethod = "POST")
+    public Result<FileEntity> queryById(@NotNull @PathVariable @ApiParam("文件ID") Long fileId) {
+        FileEntity fileEntity = adminFileService.queryById(fileId);
+        return Result.ok(fileEntity);
+    }
+
+    @RequestMapping(value = "/queryByIds", method = RequestMethod.POST)
+    @ApiOperation(value = "通过ID查询文件", httpMethod = "POST")
+    public Result<List<FileEntity>> queryByIds(@RequestBody Collection<Long> fileIds) {
+        List<FileEntity> fileEntitys = adminFileService.queryByIds(fileIds);
+        return Result.ok(fileEntitys);
+    }
+
+    @RequestMapping(value = "/queryOneByBatchId/{batchId}", method = RequestMethod.POST)
+    @ApiOperation(value = "通过批次ID查询单个文件", httpMethod = "POST")
+    public Result<FileEntity> queryOneByBatchId(@NotNull @PathVariable @ApiParam("batchId") String batchId) {
+        FileEntity fileEntity = adminFileService.queryOneByBatchId(batchId);
+        return Result.ok(fileEntity);
+    }
+
+    @RequestMapping(value = "/deleteById/{fileId}", method = RequestMethod.POST)
+    @ApiOperation(value = "通过ID删除文件", httpMethod = "POST")
+    public Result deleteById(@NotNull @PathVariable @ApiParam("文件ID") Object fileId) {
+        if (fileId instanceof Number) {
+            adminFileService.deleteById(((Number) fileId).longValue());
+        } else if (fileId instanceof String) {
+            if(((String) fileId).length() == 19){
+                adminFileService.deleteById(Long.valueOf(fileId.toString()));
+            }else {
+                AdminDeleteByBatchIdBO bo = new AdminDeleteByBatchIdBO();
+                bo.setBatchId((String) fileId);
+                adminFileService.deleteByBatchId(bo);
+            }
+        }
+        return Result.ok();
+    }
+
+    @RequestMapping(value = "/deleteByBatchId", method = RequestMethod.POST)
+    @ApiOperation(value = "通过批次ID和文件类型删除文件", httpMethod = "POST")
+    public Result deleteByBatchId(@RequestBody AdminDeleteByBatchIdBO deleteByBatchIdBO) {
+        adminFileService.deleteByBatchId(deleteByBatchIdBO);
+        return Result.ok();
+    }
+
+    @RequestMapping(value = "/deleteByBatchIds", method = RequestMethod.POST)
+    @ApiOperation(value = "通过批次ID删除文件", httpMethod = "POST")
+    public Result deleteByBatchId(@RequestBody @ApiParam("batchId") List<String> batchId) {
+        adminFileService.deleteByBatchId(batchId);
+        return Result.ok();
+    }
+
+    @RequestMapping(value = "/down/{fileId}")
+    @ApiOperation(value = "下载文件接口", httpMethod = "POST")
+    @LoginFromCookie
+    public void down(@PathVariable("fileId") @ApiParam("文件ID") Long fileId, HttpServletResponse response) {
+//        if (UserUtil.getUser() == null) {
+//            throw new CrmException(SystemCodeEnum.SYSTEM_NO_AUTH);
+//        }
+        adminFileService.down(response, fileId);
+    }
+
+    @PostMapping(value = "/renameFileById")
+    @ApiOperation(value = "修改附件名称", httpMethod = "POST")
+    public Result renameFileById(@RequestBody RenameFileBO renameFileBO) {
+        adminFileService.renameFileById(renameFileBO);
+        return Result.ok();
+    }
+
+    @PostMapping(value = "/queryNum")
+    @ApiExplain("查询文件数量")
+    public Result<Integer> queryNum(@RequestBody List<String> batchId) {
+        Integer num = adminFileService.queryNum(batchId);
+        return Result.ok(num);
+    }
+
+    @PostMapping(value = "/queryFileList")
+    @ApiExplain("查询文件")
+    public Result<List<FileEntity>> queryFileList(@RequestBody List<String> batchIdList) {
+        List<FileEntity> fileEntities = adminFileService.queryFileList(batchIdList);
+        return Result.ok(fileEntities);
+    }
+
+
+    @PostMapping(value = "/copyJxcImg")
+    @ApiExplain("copy进销存产品详情图")
+    public Result<String> copyJxcImg(@RequestParam(value = "batchId") String batchId) {
+        String newBatchId = adminFileService.copyJxcImg(batchId);
+        return Result.ok(newBatchId);
+    }
+
+    @PostMapping(value = "/saveBatchFileEntity")
+    @ApiExplain("批量保存附件(查询附件id,修改batchId)")
+    public Result saveBatchFileEntity(@RequestParam(value = "adminFileIdList") List<String> adminFileIdList,
+                                      @RequestParam(value = "batchId") String batchId) {
+        adminFileService.saveBatchFileEntity(adminFileIdList, batchId);
+        return Result.ok();
+    }
+
+
+    @RequestMapping(value = "/queryFileListByBatchId/{batchId}", method = RequestMethod.POST)
+    @ApiOperation(value = "通过批次ID查询文件列表", httpMethod = "POST")
+    public Result<List<Map>> queryFileListByBatchId(@NotNull @PathVariable String batchId) {
+        List<Map> entityList = adminFileService.queryFileListByBatchId(batchId);
+        return Result.ok(entityList);
+    }
+
+    @RequestMapping(value = "/queryOneByBatchIdAndPath", method = RequestMethod.POST)
+    @ApiOperation(value = "通过批次ID查询单个文件", httpMethod = "POST")
+    public Result<FileEntity> queryOneByBatchIdAndPath(@RequestBody Map map) {
+        FileEntity fileEntity = adminFileService.queryOneByBatchIdAndPath(map);
+        return Result.ok(fileEntity);
+    }
+
+
+
+    @PostMapping("/uploadWx")
+    @ApiOperation("上传文件")
+    public Result<UploadEntity> uploadWx(@RequestParam("file")
+                                       @ApiParam("文件") MultipartFile file,
+                                       @ApiParam("batchId") String batchId,
+                                       @ApiParam("文件类型") String type,
+                                         @ApiParam("文件类型") String tenantId,
+                                       @RequestParam(value = "isPublic",required = false)String isPublic) throws IOException {
+        if (StrUtil.isEmpty(isPublic)){
+            isPublic = "0";
+        }
+        UploadEntity entity = adminFileService.uploadWx(file, batchId, type,isPublic,tenantId);
+        return Result.ok(entity);
+    }
+
+    @RequestMapping(value = "/queryFileListWx", method = RequestMethod.POST)
+    @ApiOperation(value = "通过批次ID查询文件列表", httpMethod = "POST")
+    public Result<List<FileEntity>> queryFileListWx(@Validated @RequestBody AdminFile adminFile) {
+      List <String>batchIds=new ArrayList<>();
+        batchIds.add(adminFile.getBatchId());
+        List<FileEntity> entityList = adminFileService.queryFileListWx(batchIds);
+        return Result.ok(entityList);
+    }
+
+    @RequestMapping(value = "/downWx")
+    public void downWx( Long fileId, HttpServletResponse response) {
+        adminFileService.downWx(response, fileId);
+    }
+
+    @RequestMapping(value = "/add", method = RequestMethod.POST)
+    public void add(@RequestBody  AdminFile adminFile) {
+        adminFileService.add(adminFile);
+    }
+}
+

+ 45 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminInstrumentInfoController.java

@@ -0,0 +1,45 @@
+package com.kakarote.admin.controller;
+
+
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.entity.PO.AdminInstrumentInfo;
+import com.kakarote.admin.entity.PO.AdminMenu;
+import com.kakarote.admin.service.IAdminInstrumentInfoService;
+import com.kakarote.admin.service.IAdminInstrumentRoleService;
+import com.kakarote.core.common.*;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+/**
+ * <p>
+ * 仪表盘名称表 前端控制器
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-08
+ */
+@RestController
+@RequestMapping("/adminInstrument")
+public class AdminInstrumentInfoController {
+
+    @Autowired
+    private IAdminInstrumentInfoService adminInstrumentInfoService;
+
+//    @GetMapping("/getNameByModelId/{modelId}")
+//    @ApiExplain("根据模块ID获取名称")
+//    @OperateLog(detail="根据模块ID获取名称--首页展示用",types= LogTypes.SYS,behavior=LogBehavior.SELECT)
+//    public String getNameByModelId(@PathVariable("modelId") Integer modelId) {
+//
+//        return adminInstrumentInfoService.getNameByModelId(modelId);
+//    }
+
+    @PostMapping("/update")
+    @ApiOperation("更新仪表盘模块名称")
+    @OperateLog(detail="更新仪表盘模块名称--租户管理员用",types= LogTypes.SYS,behavior=LogBehavior.UPDATE)
+    public Result<Integer> updateMenu(@RequestBody AdminInstrumentInfo adminInstrumentInfo) {
+        Integer i = adminInstrumentInfoService.update(adminInstrumentInfo);
+        return Result.ok(i);
+    }
+}
+

+ 59 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminInstrumentRoleController.java

@@ -0,0 +1,59 @@
+package com.kakarote.admin.controller;
+
+
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.service.IAdminInstrumentInfoService;
+import com.kakarote.admin.service.IAdminInstrumentRoleService;
+import com.kakarote.core.common.*;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+
+/**
+ * <p>
+ * 仪表盘权限表 前端控制器
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-08
+ */
+@RestController
+@RequestMapping("/adminInstrumentRole")
+public class AdminInstrumentRoleController {
+
+    @Autowired
+    private IAdminInstrumentRoleService adminInstrumentRoleService;
+
+    @PostMapping("/query/{roleId}")
+    @ApiOperation("查询角色仪表盘设置")
+    @OperateLog(detail = "查询角色仪表盘设置--租户管理员用",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Result<JSONObject> query(@PathVariable("roleId") Integer roleId) {
+        JSONObject object = adminInstrumentRoleService.queryModelSort(roleId);
+        return Result.ok(object);
+    }
+
+    @PostMapping("/setModelSort")
+    @ApiOperation("修改角色仪表盘排序")
+    @OperateLog(detail = "修改角色仪表盘排序--租户管理员用",types= LogTypes.SYS ,behavior = LogBehavior.UPDATE)
+    public Result setModelSort(@RequestBody JSONObject jsonObject) {
+        adminInstrumentRoleService.setModelSort(jsonObject);
+        return R.ok();
+    }
+
+    @PostMapping("/queryModelByRoleIds")
+    @ApiOperation("查询角色仪表盘设置")
+    @OperateLog(detail = "查询角色仪表盘设置--首页展示用",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public JSONObject queryModelByRoleIds(@RequestBody List<Integer> roleIds) {
+        return adminInstrumentRoleService.queryModelByRoleIds(roleIds);
+    }
+
+    @PostMapping("/getMaxDataType")
+    @ApiOperation("根据用户角色获取仪表盘数据权限")
+    @OperateLog(detail = "根据用户角色获取仪表盘数据权限--首页展示用",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Integer getMaxDataType(@RequestBody List<Integer> roleIds) {
+        return adminInstrumentRoleService.getMaxDataType(roleIds);
+    }
+}
+

+ 151 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminMenuController.java

@@ -0,0 +1,151 @@
+package com.kakarote.admin.controller;
+
+
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.common.AdminRoleTypeEnum;
+import com.kakarote.admin.entity.PO.AdminMenu;
+import com.kakarote.admin.entity.VO.AdminMenuVO;
+import com.kakarote.admin.service.IAdminMenuService;
+import com.kakarote.core.common.LogBehavior;
+import com.kakarote.core.common.LogTypes;
+import com.kakarote.core.common.OperateLog;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.entity.UserInfo;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import javax.validation.constraints.NotNull;
+import java.util.List;
+
+/**
+ * <p>
+ * 后台菜单表 前端控制器
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+@RestController
+@RequestMapping("/adminMenu")
+@Api(tags = "菜单模块")
+public class AdminMenuController {
+
+    @Autowired
+    private IAdminMenuService adminMenuService;
+
+    @RequestMapping("/getMenuListByType/{type}")
+    @ApiOperation("根据类型查询菜单")
+    public Result<JSONObject> getMenuListByType(@PathVariable("type") Integer type) {
+        AdminRoleTypeEnum typeEnum = AdminRoleTypeEnum.parse(type);
+        JSONObject byType = adminMenuService.getMenuListByType(typeEnum);
+        return Result.ok(byType);
+    }
+    @RequestMapping("/getMenuListByTenant")
+    @ApiOperation("根据角色所在租户ID查询菜单")
+    @OperateLog(detail = "根据角色所在租户ID查询菜单--租户用",types= LogTypes.SYS ,behavior = LogBehavior.SELECT)
+    public Result<JSONObject> getMenuListByType() {
+        JSONObject byType = adminMenuService.getMenuListByTenant();
+        return Result.ok(byType);
+    }
+
+    @RequestMapping("/getWorkMenuList")
+    @ApiOperation("查询项目管理菜单")
+    public Result<JSONObject> getWorkMenuList() {
+        JSONObject byType = adminMenuService.getMenuListByType(AdminRoleTypeEnum.WORK);
+        return Result.ok(byType);
+    }
+
+    @RequestMapping("/queryMenuId")
+    public Result<Integer> queryMenuId(@RequestParam("realm1") String realm1,@RequestParam("realm2") String realm2,
+                                       @RequestParam("realm3") String realm3){
+        Integer menuId = adminMenuService.queryMenuId(realm1,realm2,realm3);
+        return Result.ok(menuId);
+
+    }
+
+
+    @GetMapping("/queryByParentId/{parentId}")
+    @ApiOperation("根据上级查询菜单")
+    public Result<List<AdminMenu>> queryByParentId(@PathVariable("parentId") Integer parentId) {
+        List<AdminMenu> list = adminMenuService.queryByParentId(parentId);
+        return Result.ok(list);
+    }
+    @GetMapping("/queryByParentIdTenant/{parentId}")
+    @ApiOperation("根据上级查询菜单")
+    @OperateLog(detail="菜单查询",types=LogTypes.SYS,behavior=
+            LogBehavior.SELECT)
+    public Result<List<AdminMenu>> queryByParentIdTenant(@PathVariable("parentId") Integer parentId) {
+        List<AdminMenu> list = adminMenuService.queryByParentIdTenant(parentId);
+        return Result.ok(list);
+    }
+
+    @PostMapping("/saveMenu")
+    @ApiOperation("保存菜单")
+    public Result<Integer> saveMenu(@RequestBody AdminMenu adminMenu) {
+        Integer i = adminMenuService.saveMenu(adminMenu);
+        return Result.ok(i);
+    }
+    @PostMapping("/updateMenu")
+    @ApiOperation("更新菜单")
+    public Result<Integer> updateMenu(@RequestBody AdminMenu adminMenu) {
+        Integer i = adminMenuService.updateMenu(adminMenu);
+        return Result.ok(i);
+    }
+    @GetMapping("/deleteMenu/{menuId}")
+    @ApiOperation("删除菜单")
+    public Result<Object> deleteMenu(@PathVariable String menuId) {
+        return adminMenuService.deleteMenu(menuId);
+    }
+
+    @GetMapping("/getMenuById/{menuId}")
+    @ApiOperation("获取菜单详情")
+    public Result<Object> getMenuById(@PathVariable Integer menuId) {
+        return adminMenuService.getMenuById(menuId);
+    }
+
+    @PostMapping("/queryHeaderMenuList")
+    @ApiOperation("置顶应用")
+    public Result<Object> queryHeaderMenuList() {
+        List<AdminMenu> list = adminMenuService.queryHeaderMenuList(UserUtil.getUserId());
+        return Result.ok(list);
+    }
+
+    @PostMapping("/queryAllMenuList")
+    @ApiOperation("全部应用")
+    public Result<Object> queryAllMenuList() {
+        List<AdminMenu> list = adminMenuService.queryAllAppList();
+        return Result.ok(list);
+    }
+    @PostMapping("/queryAppList")
+    @ApiOperation("应用管理")
+    @OperateLog(detail="应用查询",types=LogTypes.SYS,behavior=
+            LogBehavior.SELECT)
+    public Result<Object> queryAppList() {
+        List<AdminMenu> list = adminMenuService.queryAppList();
+        return Result.ok(list);
+    }
+    @PostMapping("/queryMenuListForLogin")
+    @ApiOperation("所有权限菜单")
+    public Result<Object> querMenuList(@RequestBody UserInfo userInfo) {
+        List<AdminMenu> list = adminMenuService.queryMenuListForLogin(userInfo);
+        return Result.ok(list);
+    }
+
+    @PostMapping("/queryMenuListByAuth")
+    @ApiOperation("所有权限菜单")
+    public Result<Object> queryMenuListByAuth() {
+        List<AdminMenu> list = adminMenuService.queryMenuListForLogin(UserUtil.getUser());
+        return Result.ok(list);
+    }
+
+    @PostMapping("/queryMenuListByPath")
+    @ApiOperation("根据路由查询菜单")
+    public Result<Object> queryMenuListByPath(@RequestBody AdminMenu adminMenu) {
+        List<AdminMenu> list = adminMenuService.queryMenuListByPath(adminMenu);
+        return Result.ok(list);
+    }
+}
+

+ 208 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminMessageController.java

@@ -0,0 +1,208 @@
+package com.kakarote.admin.controller;
+
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.date.DateUtil;
+import cn.hutool.core.io.FileUtil;
+import cn.hutool.extra.servlet.ServletUtil;
+import com.alibaba.fastjson.JSONObject;
+import com.baomidou.mybatisplus.extension.conditions.update.LambdaUpdateChainWrapper;
+import com.kakarote.admin.entity.BO.AdminMessageQueryBO;
+import com.kakarote.admin.entity.PO.AdminMessage;
+import com.kakarote.admin.entity.VO.AdminMessageVO;
+import com.kakarote.admin.service.IAdminMessageService;
+import com.kakarote.core.common.ApiExplain;
+import com.kakarote.core.common.Const;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.feign.admin.entity.AdminMessageBO;
+import com.kakarote.core.redis.Redis;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import javax.servlet.http.HttpServletResponse;
+
+import java.util.Map;
+
+import static com.kakarote.core.common.Const.UPLOAD_EXCEL_MESSAGE_PREFIX;
+
+/**
+ * <p>
+ * 系统消息表 前端控制器
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+@RestController
+@RequestMapping("/adminMessage")
+@Api(tags = "系统消息")
+public class AdminMessageController {
+
+    @Autowired
+    private IAdminMessageService messageService;
+
+    @Autowired
+    private Redis redis;
+
+    @PostMapping("/save")
+    public Result<AdminMessage> save(@RequestBody com.kakarote.core.feign.admin.entity.AdminMessage adminMessage) {
+        AdminMessage adminMessage1 = BeanUtil.copyProperties(adminMessage, AdminMessage.class);
+        if (adminMessage.getCreateTime() != null){
+            adminMessage1.setCreateTime(DateUtil.parseDateTime(adminMessage.getCreateTime()));
+        }
+        messageService.save(adminMessage1);
+        return Result.ok(adminMessage1);
+    }
+
+    @PostMapping("/update")
+    public Result<AdminMessage> update(@RequestBody com.kakarote.core.feign.admin.entity.AdminMessage adminMessage) {
+        AdminMessage adminMessage1 = BeanUtil.copyProperties(adminMessage, AdminMessage.class);
+        if (adminMessage.getCreateTime() != null){
+            adminMessage1.setCreateTime(DateUtil.parseDateTime(adminMessage.getCreateTime()));
+        }
+        messageService.updateById(adminMessage1);
+        return Result.ok(adminMessage1);
+    }
+
+    @PostMapping("/saveOrUpdateMessage")
+    public Result<Long> saveOrUpdateMessage(@RequestBody com.kakarote.core.feign.admin.entity.AdminMessage message) {
+        Long messageId = messageService.saveOrUpdateMessage(message);
+        return Result.ok(messageId);
+    }
+
+    @PostMapping("/queryList")
+    @ApiOperation("查询消息列表")
+    public Result<BasePage<AdminMessage>> queryList(@RequestBody AdminMessageQueryBO adminMessageBO) {
+        BasePage<AdminMessage> adminMessageBasePage = messageService.queryList(adminMessageBO);
+        return Result.ok(adminMessageBasePage);
+    }
+
+    @PostMapping("/readMessage")
+    @ApiOperation("单个标记为已读")
+    public Result readMessage(@RequestParam("messageId") Long messageId) {
+        AdminMessage byId = messageService.getById(messageId);
+        if (byId != null) {
+            byId.setIsRead(1);
+            messageService.updateById(byId);
+        }
+        return Result.ok();
+    }
+
+    @PostMapping("/dtalkReadMessage")
+    @ApiOperation("单个标记为已读")
+    public Result dtalkReadMessage(@RequestBody Map<String, Object> params) {
+        Integer messageId = (Integer) params.get("messageId");
+        AdminMessage byId = messageService.getById(messageId);
+        if (byId != null) {
+            byId.setIsRead(1);
+            messageService.updateById(byId);
+        }
+        return Result.ok();
+    }
+
+    @PostMapping("/readAllMessage")
+    @ApiOperation("全部标记为已读")
+    public Result readAllMessage(Integer label) {
+        LambdaUpdateChainWrapper<AdminMessage> wrapper = messageService.lambdaUpdate();
+        wrapper.set(AdminMessage::getIsRead, 1);
+        wrapper.eq(AdminMessage::getRecipientUser, UserUtil.getUserId());
+        if (label != null) {
+            wrapper.eq(AdminMessage::getLabel, label);
+        }
+        wrapper.update();
+        return Result.ok();
+    }
+
+    @PostMapping("/clear")
+    @ApiOperation("删除已读消息")
+    public Result clear(Integer label) {
+        LambdaUpdateChainWrapper<AdminMessage> wrapper = messageService.lambdaUpdate();
+        wrapper.eq(AdminMessage::getIsRead, 1);
+        wrapper.eq(AdminMessage::getRecipientUser, UserUtil.getUserId());
+        if (label != null) {
+            wrapper.eq(AdminMessage::getLabel, label);
+        }
+        wrapper.remove();
+        return Result.ok();
+    }
+
+    @PostMapping("/getById/{messageId}")
+    public Result<AdminMessage> getById(@PathVariable Long messageId) {
+        AdminMessage adminMessage = messageService.getById(messageId);
+        return Result.ok(adminMessage);
+    }
+
+    @PostMapping("/queryUnreadCount")
+    @ApiOperation("查询未读消息")
+    public Result<AdminMessageVO> queryUnreadCount() {
+        AdminMessageVO messageVO = messageService.queryUnreadCount();
+        return Result.ok(messageVO);
+    }
+
+    @PostMapping("/queryUnreadNoticeCount")
+    @ApiOperation("查询未读公告")
+    public Result<AdminMessageVO> queryUnreadNoticeCount() {
+        AdminMessageVO messageVO = messageService.queryUnreadNoticeCount();
+        return Result.ok(messageVO);
+    }
+    @PostMapping("/queryImportNum")
+    @ApiOperation("查询导入数量")
+    public Result<Integer> queryImportNum(Long messageId) {
+        boolean exists = redis.exists(Const.UPLOAD_EXCEL_MESSAGE_PREFIX + messageId.toString());
+        Integer num = null;
+        if (exists) {
+            num = redis.get(Const.UPLOAD_EXCEL_MESSAGE_PREFIX + messageId.toString());
+        }
+        return Result.ok(num);
+    }
+
+    @PostMapping("/queryImportInfo")
+    @ApiOperation("查询导入信息")
+    public Result<JSONObject> queryImportInfo(@RequestParam("messageId") Long messageId) {
+        AdminMessage adminMessage = messageService.getById(messageId);
+        if (adminMessage != null && adminMessage.getContent() != null) {
+            String[] content = adminMessage.getContent().split(",");
+            JSONObject r = new JSONObject().fluentPut("totalSize", adminMessage.getTitle()).fluentPut("errSize", content[0]);
+            r.put("updateSize", content.length > 1 ? content[1] : 0);
+            return Result.ok(r);
+        } else {
+            return Result.ok(new JSONObject().fluentPut("totalSize", 0).fluentPut("errSize", 0).fluentPut("updateSize", 0));
+        }
+    }
+
+    @PostMapping("/downImportError")
+    @ApiOperation("下载错误模板")
+    public void downImportError(@RequestParam("messageId") Long messageId, HttpServletResponse response) {
+        String str = redis.get(UPLOAD_EXCEL_MESSAGE_PREFIX + "file:" + messageId.toString());
+        final boolean exist = FileUtil.exist(str);
+        if (exist) {
+            ServletUtil.write(response, FileUtil.file(str));
+        }
+    }
+
+    @PostMapping("/sendMessage")
+    @ApiExplain("发送消息")
+    public Result sendMessage(@RequestBody AdminMessageBO adminMessageBO) {
+        messageService.addMessage(adminMessageBO);
+        return Result.ok();
+    }
+
+    @PostMapping("/deleteEventMessage")
+    @ApiExplain("删除日程消息")
+    public Result deleteEventMessage(@RequestParam("eventId")Integer eventId){
+        messageService.deleteEventMessage(eventId);
+        return Result.ok();
+    }
+
+    @PostMapping("/deleteById/{messageId}")
+    @ApiOperation("删除通知")
+    public Result deleteById(@PathVariable("messageId") Integer messageId) {
+        messageService.deleteById(messageId);
+        return Result.ok();
+    }
+}
+

+ 606 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminRoleController.java

@@ -0,0 +1,606 @@
+package com.kakarote.admin.controller;
+
+
+import cn.hutool.core.util.StrUtil;
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.common.AdminRoleTypeEnum;
+import com.kakarote.admin.entity.PO.AdminMenu;
+import com.kakarote.admin.entity.PO.AdminRole;
+import com.kakarote.admin.entity.VO.AdminRoleVO;
+import com.kakarote.admin.service.IAdminMenuService;
+import com.kakarote.admin.service.IAdminRoleService;
+import com.kakarote.core.common.ApiExplain;
+import com.kakarote.core.common.Const;
+import com.kakarote.core.common.R;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import org.apache.commons.lang3.StringUtils;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import javax.validation.constraints.NotNull;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+import java.util.Objects;
+import java.util.stream.Collectors;
+
+/**
+ * <p>
+ * 角色表 前端控制器
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+@RestController
+@RequestMapping("/adminRole")
+@Api(tags = "角色模块")
+public class AdminRoleController {
+    @Autowired
+    private IAdminRoleService adminRoleService;
+    @Autowired
+    private IAdminMenuService adminMenuService;
+
+    @PostMapping("/auth")
+    @ApiOperation("角色权限")
+    public Result<JSONObject> auth() {
+        JSONObject object = adminRoleService.auth(UserUtil.getUserId());
+        return R.ok(object);
+    }
+
+    @PostMapping("/authFromUser")
+    @ApiOperation("角色权限")
+    public Result<JSONObject> authFromUser() {
+        List<AdminMenu> adminMenus = adminMenuService.queryMenuListForLogin(UserUtil.getUser());
+        return R.ok(parseOauthJson(adminMenus, 0));
+    }
+
+    /**
+     * 对权限进行清洗组装
+     * 递归组装
+     * oauth:{crm:true}\{crm:{leaders:true}}\{crm:{leaders:{index:true}}}
+     * router:{
+     * path: '/404',
+     * component: () => import('@/views/404'),
+     * hidden: true,
+     * meta: {
+     * title: '统计分析',
+     * icon: 'results-solid'
+     * }
+     * },
+     *
+     * @return
+     */
+    private JSONObject parseOauthJson(List<AdminMenu> adminAllMenus, Integer parentId) {
+        //权限
+        JSONObject oauthObject = new JSONObject();
+        adminAllMenus.forEach(adminMenu -> {
+            if (Objects.equals(parentId, adminMenu.getParentId())) {
+                JSONObject object = parseOauthJson(adminAllMenus, adminMenu.getMenuId());
+                if (!object.isEmpty()) {
+                    if (parentId == 0) {
+                        oauthObject.put(adminMenu.getRealm(), object);
+                    } else {
+                        oauthObject.put(adminMenu.getRealm(), object);
+                    }
+                } else {
+                    if (parentId == 0) {
+                        oauthObject.put(adminMenu.getRealm(), Boolean.TRUE);
+                    } else {
+                        oauthObject.put(adminMenu.getRealm(), Boolean.TRUE);
+                    }
+                }
+            }
+        });
+        return oauthObject;
+    }
+
+    @PostMapping("/routerForUser")
+    @ApiOperation("用户路由")
+    public Result<JSONObject> routerFromUser() {
+        JSONObject result = new JSONObject();
+        List<AdminMenu> adminMenus = adminMenuService.queryMenuListForLogin(UserUtil.getUser());
+        //菜单路由
+        JSONObject routers = parseMenuJson(adminMenus, 0);
+        result.put("routers", routers);
+        //result.put("firstRoute", getFirstRoute(routers));//初次加载路由
+        //动态路由
+        JSONObject addRouters = parseRoutersJson(adminMenus, 0);
+        result.put("addRouters", addRouters);
+        return R.ok(result);
+    }
+
+    @PostMapping("/routerFromApp")
+    @ApiOperation("APP端用户路由")
+    public Result<JSONObject> routerFromApp() {
+        JSONObject result = new JSONObject();
+        List<AdminMenu> adminMenus = adminMenuService.queryMenuListForAppLogin(UserUtil.getUser());
+        //菜单路由
+//        JSONObject routers = parseMenuJson(adminMenus, 0);
+//        result.put("routers", routers);
+        //result.put("firstRoute", getFirstRoute(routers));//初次加载路由
+        AdminMenu topMenu = adminMenus.stream().filter(m -> m.getMenuType() == 5 && m.getParentId() == 0).findFirst().get();
+        //动态路由
+        List<Object> addRouters = parseRoutersList(adminMenus, topMenu.getMenuId());
+        result.put("addRouters", addRouters);
+        return R.ok(result);
+    }
+    /**
+     * @param adminAllMenus
+     * @param parentId
+     * @return
+     */
+    private JSONObject parseMenuJson(List<AdminMenu> adminAllMenus, Integer parentId) {
+        //路由
+        JSONObject routerObject = new JSONObject(16, true);
+        adminAllMenus.forEach(adminMenu -> {
+            if (Objects.equals(parentId, adminMenu.getParentId())
+                    && (1 == (adminMenu.getMenuType()) || 2 == (adminMenu.getMenuType()))) {
+                JSONObject router = new JSONObject();
+                //处理path
+                String path = adminMenu.getPath();
+                if (!path.startsWith("/")) {
+                    path += "/" + path;
+                }
+                router.put("path", path);
+                if (!StringUtils.isEmpty(adminMenu.getComponent())) {
+                    router.put("component", adminMenu.getComponent());
+                }
+                router.put("sort", adminMenu.getSort());
+                router.put("menuType", adminMenu.getMenuType());
+                router.put("name", adminMenu.getMenuId());
+                //applicationId 应用ID
+                router.put("applicationId", String.valueOf(adminMenu.getMenuId()));
+                //meta
+                JSONObject meta = new JSONObject();
+                //处理hide
+                String hide = adminMenu.getIsHide();
+                if("1".equals(hide)){
+                    router.put("hidden", true);
+                    String activePath = adminMenu.getActivePath();
+                    if(!StringUtils.isEmpty(activePath)){
+                        meta.put("activeMenu", activePath);
+                    }
+                }
+                //处理disabled
+                String isDisabled = adminMenu.getIsDisabled();
+                if("1".equals(isDisabled)){
+                    meta.put("disabled", true);
+                }
+                meta.put("icon", adminMenu.getIcon());
+                meta.put("title", adminMenu.getMenuName());
+                meta.put("realm", adminMenu.getPath());
+                router.put("meta", meta);
+                List<JSONObject> object = new ArrayList<>();
+                object = getMenuChildrenJson(adminAllMenus, adminMenu.getMenuId());
+                if (object.size() > 0) {
+                    router.put("children", object);
+                }
+                routerObject.put(String.valueOf(adminMenu.getMenuId()), router);
+
+            }
+        });
+        return routerObject;
+    }
+
+    /**
+     * 获取孩子菜单
+     *
+     * @param adminAllMenus
+     * @param parentId
+     * @return
+     */
+    private List<JSONObject> getMenuChildrenJson(List<AdminMenu> adminAllMenus, Integer parentId) {
+        //路由
+        List<JSONObject> jsonArray = new ArrayList<>();
+        adminAllMenus.forEach(adminMenu -> {
+            if (Objects.equals(parentId, adminMenu.getParentId())
+                    && (1 == (adminMenu.getMenuType()) || 2 == (adminMenu.getMenuType()))
+                    && !StringUtils.isEmpty(adminMenu.getPath())) {
+                JSONObject router = new JSONObject();
+                //处理path
+                String childPath = adminMenu.getPath();
+                router.put("path", childPath);
+                router.put("name", adminMenu.getMenuId());
+                router.put("menuType", adminMenu.getMenuType());
+                router.put("component", adminMenu.getComponent());
+                //meta
+                JSONObject meta = new JSONObject();
+                //处理hide
+                String hide = adminMenu.getIsHide();
+                if("1".equals(hide)){
+                    router.put("hidden", true);
+                    String activePath = adminMenu.getActivePath();
+                    if(!StringUtils.isEmpty(activePath)){
+                        meta.put("activeMenu", activePath);
+                    }
+                }
+                //处理disabled
+                String isDisabled = adminMenu.getIsDisabled();
+                if("1".equals(isDisabled)){
+                    meta.put("disabled", true);
+                }
+                meta.put("icon", adminMenu.getIcon());
+                meta.put("title", adminMenu.getMenuName());
+                meta.put("realm", adminMenu.getPath());
+                router.put("meta", meta);
+                List<JSONObject> childrenJson = getMenuChildrenJson(adminAllMenus, adminMenu.getMenuId());
+                if (childrenJson.size() > 0) {
+                    router.put("children", childrenJson);
+                    //router.put("hidden",true);
+                }
+                jsonArray.add(router);
+            }
+        });
+        return jsonArray;
+    }
+    /**
+     * @param adminAllMenus
+     * @param parentId
+     * @return
+     */
+    private JSONObject parseRoutersJson(List<AdminMenu> adminAllMenus, Integer parentId) {
+        //路由
+        JSONObject routerObject = new JSONObject(16, true);
+        adminAllMenus.forEach(adminMenu -> {
+            if (Objects.equals(parentId, adminMenu.getParentId())
+                    && (1 == (adminMenu.getMenuType()) || 2 == (adminMenu.getMenuType())
+                        || 5 == (adminMenu.getMenuType()))) {
+                List<JSONObject> jsonArray = new ArrayList<>();
+                JSONObject router = new JSONObject();
+                //处理path
+                String path = adminMenu.getPath();
+                if (!path.startsWith("/")) {
+                    path += "/" + path;
+                }
+                router.put("path", path);
+                if (!StringUtils.isEmpty(adminMenu.getComponent())) {
+                    router.put("component", adminMenu.getComponent());
+                }
+                router.put("name", adminMenu.getMenuId());
+                //applicationId 应用ID
+                router.put("applicationId", String.valueOf(adminMenu.getMenuId()));
+
+                //meta
+                JSONObject meta = new JSONObject();
+                //处理hide
+                String hide = adminMenu.getIsHide();
+                if("1".equals(hide)){
+                    router.put("hidden", true);
+                    String activePath = adminMenu.getActivePath();
+                    if(!StringUtils.isEmpty(activePath)){
+                        meta.put("activeMenu", activePath);
+                    }
+                }
+                //处理disabled
+                String isDisabled = adminMenu.getIsDisabled();
+                if("1".equals(isDisabled)){
+                    meta.put("disabled", true);
+                }
+                meta.put("icon", adminMenu.getIcon());
+                meta.put("title", adminMenu.getMenuName());
+                meta.put("realm", adminMenu.getPath());
+                router.put("meta", meta);
+                List<JSONObject> object = new ArrayList<>();
+                object = getRouterChildrenJson(adminAllMenus, adminMenu.getMenuId(), "");
+                if (object.size() > 0) {
+                    router.put("children", object);
+                }
+                //20210924 By PangZhen 追加:一级菜单为页面时将路由改为二级
+                if(adminMenu.getParentId()==0 && object.size()==0){
+//                    System.out.println("===="+adminMenu.getMenuName());
+                    router.put("path", "/" + adminMenu.getPath());
+                    router.put("component", "layout/CommonLayou");
+                    ArrayList<JSONObject> list = new ArrayList();
+                    JSONObject routeCopy =  (JSONObject) router.clone();
+                    routeCopy.put("path",adminMenu.getPath());
+                    routeCopy.put("component", adminMenu.getComponent());
+                    list.add(routeCopy);
+                    router.put("children", list);
+//                    System.out.println("===="+router.toJSONString());
+                }
+                jsonArray.add(router);
+                routerObject.put(String.valueOf(adminMenu.getMenuId()), jsonArray);
+
+            }
+        });
+        return routerObject;
+    }
+    private List<Object> parseRoutersList(List<AdminMenu> adminAllMenus, Integer parentId) {
+        //路由
+        List<Object> routerObject = new ArrayList<>();
+        adminAllMenus.forEach(adminMenu -> {
+            if (Objects.equals(parentId, adminMenu.getParentId())
+                    && (1 == (adminMenu.getMenuType()) || 2 == (adminMenu.getMenuType())
+                    || 5 == (adminMenu.getMenuType()))) {
+                List<JSONObject> jsonArray = new ArrayList<>();
+                JSONObject router = new JSONObject();
+                //处理path
+                String path = adminMenu.getPath();
+                if (!path.startsWith("/")) {
+                    path += "/" + path;
+                }
+                router.put("path", path);
+                if (!StringUtils.isEmpty(adminMenu.getComponent())) {
+                    router.put("component", adminMenu.getComponent());
+                }
+                router.put("name", adminMenu.getMenuId());
+                //applicationId 应用ID
+                router.put("applicationId", String.valueOf(adminMenu.getMenuId()));
+
+                //meta
+                JSONObject meta = new JSONObject();
+                //处理hide
+                String hide = adminMenu.getIsHide();
+                if("1".equals(hide)){
+                    router.put("hidden", true);
+                    String activePath = adminMenu.getActivePath();
+                    if(!StringUtils.isEmpty(activePath)){
+                        meta.put("activeMenu", activePath);
+                    }
+                }
+                //处理disabled
+                String isDisabled = adminMenu.getIsDisabled();
+                if("1".equals(isDisabled)){
+                    meta.put("disabled", true);
+                }
+                meta.put("icon", adminMenu.getIcon());
+                meta.put("title", adminMenu.getMenuName());
+                meta.put("realm", adminMenu.getPath());
+                router.put("meta", meta);
+                List<JSONObject> object = new ArrayList<>();
+                object = getRouterChildrenJson(adminAllMenus, adminMenu.getMenuId(), "");
+                if (object.size() > 0) {
+                    router.put("children", object);
+                }
+                //20210924 By PangZhen 追加:一级菜单为页面时将路由改为二级
+                if(adminMenu.getParentId()==0 && object.size()==0){
+//                    System.out.println("===="+adminMenu.getMenuName());
+                    router.put("path", "/" + adminMenu.getPath());
+                    router.put("component", "layout/CommonLayou");
+                    ArrayList<JSONObject> list = new ArrayList();
+                    JSONObject routeCopy =  (JSONObject) router.clone();
+                    routeCopy.put("path",adminMenu.getPath());
+                    routeCopy.put("component", adminMenu.getComponent());
+                    list.add(routeCopy);
+                    router.put("children", list);
+//                    System.out.println("===="+router.toJSONString());
+                }
+                jsonArray.add(router);
+                routerObject.add(jsonArray);
+
+            }
+        });
+        return routerObject;
+    }
+    /**
+     * 获取孩子路由
+     *
+     * @param adminAllMenus
+     * @param parentId
+     * @return
+     */
+    private List<JSONObject> getRouterChildrenJson(List<AdminMenu> adminAllMenus, Integer parentId, String path) {
+        //路由
+        List<JSONObject> jsonArray = new ArrayList<>();
+        adminAllMenus.forEach(adminMenu -> {
+            if (Objects.equals(parentId, adminMenu.getParentId())
+                    //&& (1 == (adminMenu.getMenuType()) || 2 == (adminMenu.getMenuType()))
+                    && !StringUtils.isEmpty(adminMenu.getPath())) {
+                JSONObject router = new JSONObject();
+                //处理path
+                String childPath = adminMenu.getPath();
+                if (!"".equals(path) && !childPath.startsWith("/")) {
+                    childPath = path + "/" + childPath;
+                }
+                router.put("path", childPath);
+                if (!StringUtils.isEmpty(adminMenu.getComponent())) {
+                    router.put("component", adminMenu.getComponent());
+                }
+                router.put("name", adminMenu.getMenuId());
+                //meta
+                JSONObject meta = new JSONObject();
+                //处理hide
+                String hide = adminMenu.getIsHide();
+                if("1".equals(hide)){
+                    router.put("hidden", true);
+                    String activePath = adminMenu.getActivePath();
+                    if(!StringUtils.isEmpty(activePath)){
+                        meta.put("activeMenu", activePath);
+                    }
+                }
+                //处理disabled
+                String isDisabled = adminMenu.getIsDisabled();
+                if("1".equals(isDisabled)){
+                    meta.put("disabled", true);
+                }
+                meta.put("icon", adminMenu.getIcon());
+                meta.put("title", adminMenu.getMenuName());
+                meta.put("realm", adminMenu.getPath());
+                router.put("meta", meta);
+                jsonArray.add(router);
+                List<JSONObject> childrenJson = getRouterChildrenJson(adminAllMenus, adminMenu.getMenuId(), childPath);
+                /*if (object.size() > 0) {
+                    router.put("children", object);
+                    //router.put("hidden",true);
+                }*/
+                jsonArray.addAll(childrenJson);
+            }
+        });
+        return jsonArray;
+    }
+
+    @PostMapping("/queryNoAuthMenu")
+    @ApiOperation("获取未授权的菜单")
+    public Result<List<String>> queryNoAuthMenu(@RequestParam("userId") @NotNull Long userId) {
+        return R.ok(adminRoleService.queryNoAuthMenu(userId));
+    }
+
+    @PostMapping("/getAllRoleList")
+    @ApiOperation("全局角色查询")
+    public Result<List<AdminRoleVO>> getAllRoleList() {
+        List<AdminRoleVO> allRoleList = adminRoleService.getAllRoleList();
+        return R.ok(allRoleList);
+    }
+
+    @PostMapping("/getRoleTypeList")
+    @ApiOperation("获取角色类型列表")
+    public Result<List<Map<String, Object>>> getRoleTypeList() {
+        List<Map<String, Object>> data = new ArrayList<>(6);
+        data.add(new JSONObject().fluentPut("name", "系统管理角色").fluentPut("roleType", 1));
+        data.add(new JSONObject().fluentPut("name", "办公管理角色").fluentPut("roleType", 7));
+        data.add(new JSONObject().fluentPut("name", "客户管理角色").fluentPut("roleType", 2));
+        data.add(new JSONObject().fluentPut("name", "项目管理角色").fluentPut("roleType", 8));
+        return R.ok(data);
+    }
+
+    @PostMapping("/getRoleByType/{type}")
+    @ApiOperation("通过角色类型查询角色")
+    public Result<List<AdminRole>> getRoleByType(@PathVariable("type") Integer type) {
+        List<AdminRole> roleByType = adminRoleService.getRoleByType(AdminRoleTypeEnum.parse(type));
+        return R.ok(roleByType);
+    }
+
+//    @PostMapping("/getRoleById") //改为getRoleByIdForRoleAuth
+//    @ApiOperation("通过角色类型查询角色")
+//    public Result<List<AdminRole>> getRoleById() {
+//        List<AdminRole> roleByType = adminRoleService.getRoleById();
+//        return R.ok(roleByType);
+//    }
+
+    @PostMapping("/getRoleByIdForRoleAuth")
+    @ApiOperation("通过角色类型查询角色--角色权限管理用")
+    public Result<List<AdminRole>> getRoleByIdForRoleAuth() {
+        List<AdminRole> roleByType = adminRoleService.getRoleByIdForRoleAuth();
+        return R.ok(roleByType);
+    }
+
+    @PostMapping("/getRoleList")
+    @ApiOperation("查询角色列表")
+    public Result<List<AdminRole>> getRoleList() {
+        List<AdminRole> roleByType = adminRoleService.getRoleList();
+        return R.ok(roleByType);
+    }
+
+    @PostMapping("/queryRoleByRoleType")
+    @ApiExplain("通过角色类型查询角色")
+    public Result<List<Integer>> queryRoleByRoleType(@RequestParam("type") Integer type) {
+        List<AdminRole> recordList = adminRoleService.lambdaQuery().select(AdminRole::getRoleId).eq(AdminRole::getRoleType, type).list();
+        return R.ok(recordList.stream().map(AdminRole::getRoleId).collect(Collectors.toList()));
+    }
+
+    @PostMapping("/queryDataType")
+    @ApiExplain("查询数据权限")
+    public Result<Integer> queryDataType(@RequestParam("userId") Long userId, @RequestParam("menuId") Integer menuId) {
+        Integer dataType = adminRoleService.queryDataType(userId, menuId);
+        return R.ok(dataType);
+    }
+    @PostMapping("/queryDataTypeByRealm")
+    @ApiExplain("查询数据权限")
+    public Result<Integer> queryDataTypeByRealm(@RequestParam("userId") Long userId, @RequestParam("realm") String realm) {
+        Integer dataType = adminRoleService.queryDataTypeByRealm(userId, realm);
+        return R.ok(dataType);
+    }
+
+    @PostMapping("/queryMaxDataType")
+    @ApiExplain("查询数据权限")
+    public Result<Integer> queryMaxDataType(@RequestParam("userId") Long userId, @RequestParam("menuId") Integer menuId) {
+        Integer dataType = adminRoleService.queryMaxDataType(userId, menuId);
+        return R.ok(dataType);
+    }
+
+    @PostMapping("/queryUserByAuth")
+    @ApiExplain("查询数据权限")
+    public Result<List<Long>> queryUserByAuth(@RequestParam("userId") Long userId, @RequestParam("realm") String realm) {
+        List<Long> longs = adminRoleService.queryUserByAuth(userId, realm);
+        return R.ok(longs);
+    }
+
+    @PostMapping("/add")
+    @ApiOperation("添加角色")
+    public Result add(@RequestBody AdminRole adminRole) {
+        adminRoleService.add(adminRole);
+        return R.ok();
+    }
+
+    @PostMapping("/update")
+    @ApiOperation("修改角色")
+    public Result update(@RequestBody AdminRole adminRole) {
+        adminRoleService.add(adminRole);
+        return R.ok();
+    }
+
+    @PostMapping("/delete")
+    @ApiOperation("删除角色")
+    public Result delete(@RequestParam("roleId") Integer roleId) {
+        adminRoleService.delete(roleId);
+        return R.ok();
+    }
+
+    @PostMapping("/copy")
+    @ApiOperation("复制角色")
+    public Result copy(@RequestParam("roleId") Integer roleId) {
+        adminRoleService.copy(roleId);
+        return R.ok();
+    }
+
+    @PostMapping("/relatedUser")
+    @ApiOperation("角色关联员工")
+    public Result relatedUser(@RequestParam("userIds") String userIds, @RequestParam("roleIds") String roleIds) {
+        adminRoleService.relatedUser(StrUtil.splitTrim(userIds, Const.SEPARATOR), StrUtil.splitTrim(roleIds, Const.SEPARATOR));
+        return R.ok();
+    }
+
+    @PostMapping("/unbindingUser")
+    @ApiOperation("取消角色关联员工")
+    public Result unbindingUser(@RequestParam("userId") Long userId, @RequestParam("roleId") Integer roleId) {
+        adminRoleService.unbindingUser(userId, roleId);
+        return R.ok();
+    }
+
+    @PostMapping("/updateRoleMenu")
+    @ApiOperation("保存角色菜单关系")
+    public Result updateRoleMenu(@RequestBody AdminRole adminRole) {
+        adminRoleService.updateRoleMenu(adminRole);
+        return R.ok();
+    }
+
+    @PostMapping(value = "/queryWorkRole")
+    @ApiExplain("查询项目管理角色")
+    public Result<Integer> queryWorkRole(@RequestParam("label") Integer label) {
+        Integer role = adminRoleService.queryWorkRole(label);
+        return R.ok(role);
+    }
+
+    @PostMapping(value = "/setWorkRole")
+    @ApiExplain("设置项目管理角色")
+    public Result setWorkRole(@RequestBody JSONObject object) {
+        adminRoleService.setWorkRole(object);
+        return R.ok();
+    }
+
+    @PostMapping(value = "/deleteWorkRole")
+    @ApiExplain("删除项目管理角色")
+    public Result deleteWorkRole(@RequestParam("roleId") Integer roleId) {
+        adminRoleService.deleteWorkRole(roleId);
+        return R.ok();
+    }
+
+    @PostMapping(value = "/queryProjectRoleList")
+    @ApiOperation("查询项目管理角色列表")
+    public Result<List<AdminRole>> queryProjectRoleList() {
+        List<AdminRole> adminRoles = adminRoleService.queryProjectRoleList();
+        return R.ok(adminRoles);
+    }
+
+    @PostMapping(value = "/queryWorkRoleList")
+    @ApiOperation("查询项目管理角色列表")
+    public Result<List<AdminRole>> queryWorkRoleList() {
+        List<AdminRole> adminRoles = adminRoleService.queryRoleList();
+        return R.ok(adminRoles);
+    }
+}
+

+ 50 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminRoleMenuDpController.java

@@ -0,0 +1,50 @@
+package com.kakarote.admin.controller;
+
+
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.service.IAdminRoleMenuDpService;
+import com.kakarote.core.common.R;
+import com.kakarote.core.common.Result;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ *  前端控制器
+ * </p>
+ *
+ * @author shz
+ * @since 2022-09-07
+ */
+@RestController
+@RequestMapping("/adminRoleMenuDp")
+public class AdminRoleMenuDpController {
+
+    @Autowired
+    private IAdminRoleMenuDpService adminRoleMenuDpService;
+
+    @PostMapping("/updateRoleMenu")
+    @ApiOperation("保存角色菜单关系")
+    public Result updateRoleMenu(@RequestBody Map map) {
+        adminRoleMenuDpService.updateRoleMenu(map);
+        return R.ok();
+    }
+
+    @GetMapping("/getByRoleId/{roleId}")
+    @ApiOperation("获取角色权限")
+    public Result getByRoleId(@PathVariable("roleId") Long roleId){
+        JSONObject object = new JSONObject().fluentPut("role_id", roleId);
+        return R.ok(adminRoleMenuDpService.listByMap(object));
+    }
+
+    @GetMapping("/getByUser")
+    @ApiOperation("获取角色权限")
+    public Result getByUser(String platform){
+        return R.ok(adminRoleMenuDpService.getByUser());
+    }
+}
+

+ 91 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminTenantController.java

@@ -0,0 +1,91 @@
+package com.kakarote.admin.controller;
+
+
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.entity.BO.AdminDeptBO;
+import com.kakarote.admin.entity.BO.AdminUserBO;
+import com.kakarote.admin.entity.PO.AdminDept;
+import com.kakarote.admin.entity.VO.AdminDeptVO;
+import com.kakarote.admin.entity.VO.AdminUserVO;
+import com.kakarote.admin.service.IAdminMenuService;
+import com.kakarote.admin.service.IAdminTenantService;
+import com.kakarote.core.common.*;
+import com.kakarote.core.entity.BasePage;
+import io.seata.spring.annotation.GlobalTransactional;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.web.bind.annotation.*;
+
+import javax.validation.Valid;
+import java.util.List;
+
+@RestController
+@RequestMapping("/adminTenant")
+@Api(tags = "租户模块")
+public class AdminTenantController {
+
+    @Autowired
+    private IAdminMenuService adminMenuService;
+    @Autowired
+    private IAdminTenantService adminTenantService;
+
+    @PostMapping("/queryDeptList")
+    @ApiOperation("查询部门列表")
+    @OperateLog(detail="查询部门列表",types= LogTypes.SYS,behavior=LogBehavior.SELECT)
+    public Result<List<AdminDeptVO>> queryDeptList() {
+        List<AdminDeptVO> deptList = adminTenantService.queryDeptList();
+        return Result.ok(deptList);
+    }
+
+    @PostMapping("/queryUserList")
+    @ApiOperation("查询员工列表")
+    @OperateLog(detail="查询员工列表",types= LogTypes.SYS,behavior=LogBehavior.SELECT)
+    public Result<BasePage<AdminUserVO>> queryUserList(@RequestBody AdminUserBO adminUserBO) {
+        return R.ok(adminTenantService.queryUserList(adminUserBO));
+    }
+
+    @RequestMapping("/getMenuList/{tenantId}")
+    @ApiOperation("查询全部菜单--租户权限分配用")
+    @OperateLog(detail="查询全部菜单--租户权限分配用",types= LogTypes.SYS,behavior=LogBehavior.SELECT)
+    public Result<JSONObject> getMenuListByType(@PathVariable("tenantId") Integer tenantId) {
+        JSONObject byType = adminMenuService.getAllMenuList(tenantId);
+        return Result.ok(byType);
+    }
+
+    @PostMapping("/getRoleByType")
+    @ApiOperation("通过部门Id查询权限")
+    @OperateLog(detail="通过部门Id查询权限",types= LogTypes.SYS,behavior=LogBehavior.SELECT)
+    public Result<List<AdminDept>> getRoleByType() {
+        List<AdminDept> DeptByType = adminTenantService.getRoleByType();
+        return R.ok(DeptByType);
+    }
+
+    @PostMapping("/updateTenantMenu")
+    @ApiOperation("保存部门(租户)菜单关系")
+    @OperateLog(detail="保存部门(租户)菜单关系",types= LogTypes.SYS,behavior=LogBehavior.UPDATE)
+    public Result updateTenantMenu(@RequestBody AdminDept adminDept){
+        adminTenantService.updateDeptMenu(adminDept);
+        return R.ok();
+    }
+
+    @PostMapping("/addTenant")
+    @ApiOperation("新增租户")
+    @OperateLog(detail="新增租户",types= LogTypes.SYS,behavior=LogBehavior.INSERT)
+    @Transactional(rollbackFor = Exception.class)
+    public Result addTenant(@RequestBody @Valid AdminDeptBO adminDept) {
+        adminTenantService.addTenant(adminDept);
+        return R.ok();
+    }
+
+    @PostMapping("/addTenantAdmin")
+    @ApiOperation("新增租户管理员")
+    @OperateLog(detail="新增租户管理员",types= LogTypes.SYS,behavior=LogBehavior.INSERT)
+    @GlobalTransactional(rollbackFor = Exception.class,timeoutMills = 120000)
+    public Result addTenantAdmin(@RequestBody AdminUserVO adminUserVO) {
+        adminTenantService.addTenantAdmin(adminUserVO);
+        return R.ok();
+    }
+}
+

+ 502 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminUserController.java

@@ -0,0 +1,502 @@
+package com.kakarote.admin.controller;
+
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.io.FileUtil;
+import cn.hutool.core.io.IoUtil;
+import cn.hutool.core.util.ObjectUtil;
+import cn.hutool.extra.servlet.ServletUtil;
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONObject;
+import com.kakarote.admin.common.AdminCodeEnum;
+import com.kakarote.admin.entity.BO.*;
+import com.kakarote.admin.entity.PO.AdminConfig;
+import com.kakarote.admin.entity.PO.AdminUser;
+import com.kakarote.admin.entity.PO.AdminUserConfig;
+import com.kakarote.admin.entity.VO.AdminUserVO;
+import com.kakarote.admin.entity.VO.HrmSimpleUserVO;
+import com.kakarote.admin.service.*;
+import com.kakarote.core.common.*;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.entity.UserInfo;
+import com.kakarote.core.exception.NoLoginException;
+import com.kakarote.core.feign.admin.entity.SimpleUser;
+import com.kakarote.core.feign.build.BuildService;
+import com.kakarote.core.feign.crm.service.CrmService;
+import com.kakarote.core.feign.email.EmailService;
+import com.kakarote.core.servlet.ApplicationContextHolder;
+import com.kakarote.core.servlet.upload.UploadEntity;
+import com.kakarote.core.utils.UserCacheUtil;
+import com.kakarote.core.utils.UserUtil;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.validation.annotation.Validated;
+import org.springframework.web.bind.annotation.*;
+import org.springframework.web.multipart.MultipartFile;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import javax.validation.constraints.NotNull;
+import java.io.BufferedInputStream;
+import java.io.File;
+import java.io.IOException;
+import java.util.*;
+import java.util.stream.Collectors;
+
+/**
+ * <p>
+ * 用户表 前端控制器
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+@RestController
+@RequestMapping("/adminUser")
+@Api(tags = "员工管理相关接口")
+@Slf4j
+public class AdminUserController {
+
+    @Autowired
+    private IAdminUserService adminUserService;
+
+    @Autowired
+    private IAdminUserConfigService adminUserConfigService;
+
+    @Autowired
+    private IAdminFileService adminFileService;
+
+    @Autowired
+    private CrmService crmService;
+
+    @Autowired
+    private IAdminUserRoleService adminUserRoleService;
+
+    @Autowired
+    private BuildService buildService;
+
+    @RequestMapping("/findByUsername")
+    @ApiOperation(value = "通过name查询用户", httpMethod = "POST")
+    public Result<List<Map<String, Object>>> findByUsername(String username) {
+        List<Map<String, Object>> userInfoList = adminUserService.findByUsername(username);
+        return Result.ok(userInfoList);
+    }
+
+    @RequestMapping("/findByUsernameByTenantID")
+    @ApiOperation(value = "通过name查询用户", httpMethod = "POST")
+    public Result<Map<String, Object>> findByUsernameByTenantID(String username, Integer tenantId) {
+        List<AdminUser> adminUsers = adminUserService.lambdaQuery().eq(AdminUser::getUsername, username).eq(AdminUser::getTenantId, tenantId).list();
+        if (adminUsers.size() < 1) {
+            return Result.error(1, "账号或密码错误");
+        }
+        Map<String, Object> map = BeanUtil.beanToMap(adminUsers.get(0));
+        return Result.ok(map);
+    }
+
+    @RequestMapping("/findByNameConfig")
+    @ApiOperation(value = "通过name及配置Id查询用户", httpMethod = "POST")
+    public Result<List<Map<String, Object>>> findByNameConfig(@RequestParam("username") String username, @RequestParam("configId") String configId) {
+        List<Map<String, Object>> userInfoList = adminUserService.findByNameConfig(username, configId);
+        return Result.ok(userInfoList);
+    }
+
+    @ApiOperation("通过条件分页查询员工列表")
+    @PostMapping("/queryUserList")
+    public Result<BasePage<AdminUserVO>> queryUserList(@RequestBody AdminUserBO adminUserBO) {
+        return R.ok(adminUserService.queryUserList(adminUserBO));
+    }
+
+    @ApiExplain("通过条件分页查询员工列表")
+    @PostMapping("/queryAllUserList")
+    public Result<List<Long>> queryAllUserList() {
+        List<AdminUserVO> adminUserBOList = adminUserService.queryUserList(null).getList();
+        return R.ok(adminUserBOList.stream().map(AdminUserVO::getUserId).collect(Collectors.toList()));
+    }
+
+    @PostMapping("/setUser")
+    @ApiOperation("修改用户")
+    public Result setUser(@RequestBody AdminUserVO adminUserVO) {
+        adminUserService.setUser(adminUserVO);
+        return R.ok();
+    }
+
+    @PostMapping("/addUser")
+    @ApiOperation("新增用户")
+    @OperateLog(detail = "新增用户", types = LogTypes.SYS, behavior = LogBehavior.INSERT)
+    public Result addUser(@RequestBody AdminUserVO adminUserVO) {
+        return R.ok(adminUserService.addUser(adminUserVO));
+    }
+
+    @GetMapping("/delUser/{userId}")
+    @ApiOperation("删除用户")
+    @OperateLog(detail = "删除用户/租户管理员--系统管理员用", types = LogTypes.SYS, behavior = LogBehavior.DELETE)
+    public Result delUser(@PathVariable("userId") Long userId) {
+
+        adminUserService.delUser(userId);
+        return R.ok();
+    }
+
+    @PostMapping("/usernameEdit")
+    @ApiOperation("重置登录账号")
+    public Result<Integer> usernameEdit(@RequestParam("id") Integer id, @RequestParam("username") String username, @RequestParam("password") String password) {
+        Integer integer = adminUserService.usernameEdit(id, username, password);
+        return R.ok(integer);
+    }
+
+    @PostMapping("/excelImport")
+    @ApiOperation("excel导入员工")
+    public Result<JSONObject> excelImport(@RequestParam("file") MultipartFile file) {
+        JSONObject object = adminUserService.excelImport(file);
+        return R.ok(object);
+    }
+
+    @PostMapping("/downExcel")
+    @ApiOperation("excel下载错误数据")
+    public void downExcel(@RequestParam("token") String token, HttpServletResponse response) {
+        String path = FileUtil.getTmpDirPath() + "/" + token;
+        if (FileUtil.exist(path)) {
+            File file = FileUtil.file(path);
+            final String fileName = file.getName();
+            final String contentType = ObjectUtil.defaultIfNull(FileUtil.getMimeType(fileName), "application/octet-stream");
+            BufferedInputStream in = null;
+            try {
+                in = FileUtil.getInputStream(file);
+                ServletUtil.write(response, in, contentType, "import_error.xls");
+            } finally {
+                IoUtil.close(in);
+            }
+            FileUtil.del(path);
+        }
+    }
+
+    @PostMapping("/hrmAddUser")
+    @ApiOperation("从人力资源添加员工")
+    public Result hrmAddUser(@RequestBody HrmAddUserBO hrmAddUserBO) {
+        adminUserService.hrmAddUser(hrmAddUserBO);
+        return R.ok();
+    }
+
+    @PostMapping("/setUserStatus")
+    @ApiOperation("禁用启用")
+    public Result setUserStatus(@RequestBody AdminUserStatusBO adminUserStatusBO) {
+        adminUserService.setUserStatus(adminUserStatusBO);
+        return R.ok();
+    }
+
+    @PostMapping("/resetPassword")
+    @ApiOperation("重置密码")
+    public Result resetPassword(@RequestBody AdminUserStatusBO adminUserStatusBO) {
+        adminUserService.resetPassword(adminUserStatusBO);
+        return R.ok();
+    }
+
+    @PostMapping("/updateImg")
+    @ApiOperation("修改头像")
+    public Result updateImg(@RequestParam("file") MultipartFile file) throws IOException {
+        UploadEntity img = adminFileService.upload(file, null, "img", "0");
+        AdminUser byId = adminUserService.getById(UserUtil.getUserId());
+        byId.setImg(img.getUrl());
+        adminUserService.updateById(byId);
+        return R.ok();
+    }
+
+    @PostMapping("/updatePassword")
+    @ApiOperation("修改登录密码")
+    public Result updatePassword(@RequestParam("oldPwd") String oldPass, @RequestParam("newPwd") String newPass) {
+        AdminUser adminUser = adminUserService.getById(UserUtil.getUserId());
+        if (!UserUtil.verify(adminUser.getUsername() + oldPass, adminUser.getSalt(), adminUser.getPassword())) {
+            return R.error(AdminCodeEnum.ADMIN_PASSWORD_ERROR);
+        }
+        adminUser.setPassword(newPass);
+        return updateUser(adminUser);
+    }
+
+    @PostMapping("/updateUser")
+    @ApiOperation("修改用户信息")
+    public Result updateUser(@RequestBody AdminUser adminUser) {
+        adminUserService.updateUser(adminUser);
+        return R.ok();
+    }
+
+    @Autowired
+    private IAdminDeptService deptService;
+
+    @PostMapping("/queryLoginUser")
+    @ApiOperation("查询当前登录用户")
+    public Result<AdminUserVO> queryLoginUser(HttpServletRequest request) {
+        String name = "readNotice";
+        AdminUser user = adminUserService.getById(UserUtil.getUser().getUserId());
+        if (user == null) {
+            throw new NoLoginException();
+        }
+        AdminUserVO adminUser = BeanUtil.copyProperties(user, AdminUserVO.class);
+        adminUser.setIsAdmin(UserUtil.isAdmin());
+        AdminUserConfig userConfig = adminUserConfigService.queryUserConfigByName(name);
+        adminUser.setIsReadNotice(userConfig != null ? userConfig.getStatus() : 0);
+        adminUser.setPassword(null);
+        String deptName = deptService.getNameByDeptId(adminUser.getDeptId());
+        adminUser.setDeptName(deptName);
+        adminUser.setParentName(UserCacheUtil.getUserName(adminUser.getParentId()));
+        AdminConfig config = ApplicationContextHolder.getBean(IAdminConfigService.class).queryConfigByName("email");
+        if (config != null && config.getStatus() == 1) {
+            Integer data = ApplicationContextHolder.getBean(EmailService.class).getEmailId(adminUser.getUserId()).getData();
+            adminUser.setEmailId(data);
+        }
+        //更新下用户信息
+        String token = request.getHeader(Const.TOKEN_NAME);
+        Integer projectId = user.getProjectId();
+        UserInfo userInfo = UserUtil.getUser();
+        if (projectId != null) {
+            userInfo.setProjectId(Long.valueOf(projectId.toString()));
+        } else {
+            userInfo.setProjectId(null);
+        }
+        UserUtil.userToken(token, userInfo);
+        /*UserInfo userInfo = UserUtil.getUser();
+        adminUser.setOauth(userInfo.getOauth());
+        adminUser.setRouters(userInfo.getRouters());*/
+        //20201214:登录后保存CRM自定义字段数据至es
+        try {
+            //todo 屏蔽ES 22.03.15
+            //crmService.initFieldDataToEs();
+        } catch (Exception e) {
+            //crm未启动时不应报错
+            log.warn("登录后保存CRM自定义字段数据至es:失败");
+        }
+
+        adminUser.setDeptParentId(userInfo.getDeptParentId());
+        adminUser.setWxappOpenId(userInfo.getWxappOpenId());
+
+        // 获取用户角色类型
+        List<Integer> roleTypeList = adminUserRoleService.selectRoleTypeByUserId(adminUser.getUserId());
+        adminUser.setRoleTypeList(roleTypeList);
+        //2022-09-05 邵化振 添加用户工种信息
+        try {
+            Result res = buildService.getInfocollectionByPhone(user.getMobile());
+            Map map = (Map)res.getData();
+            if(map != null){
+                adminUser.setWorkTypeId((Integer) map.get("workTypeId"));
+            }
+        }catch (Exception e){
+            e.printStackTrace();
+        }
+        return R.ok(adminUser);
+    }
+
+    /**
+     * @description
+     * @author wnj58 
+     * @Params []
+     * @updateTime 2022/4/11 10:08
+     * @return com.kakarote.core.common.Result
+     * @throws 
+     */
+    @PostMapping("/queryLoginUserFast")
+    @ApiOperation("查询当前登录用户信息-快速")
+    public Result queryLoginUserFast() {
+      String js=  JSON.toJSONString(UserUtil.getUser());
+      JSONObject jss=JSON.parseObject(js);
+        return R.ok(jss);
+    }
+
+    @PostMapping("/queryLoginUserQuick")
+    @ApiOperation("查询当前登录用户ID-快速")
+    public Result<Long> queryLoginUserQuick() {
+        return R.ok(UserUtil.getUserId());
+    }
+
+    @RequestMapping("/queryUserRoleIds")
+    @ApiExplain("查询用户角色列表")
+    public Result<List<Integer>> queryUserRoleIds(@RequestParam("userId") @NotNull Long userId) {
+        return R.ok(adminUserService.queryUserRoleIds(userId));
+    }
+
+    @RequestMapping("/queryListName")
+    @ApiExplain("查询通讯录")
+    public Result queryListName(@RequestBody UserBookBO userBookBO) {
+        return R.ok(adminUserService.queryListName(userBookBO));
+    }
+
+    @RequestMapping("/attention")
+    @ApiExplain("切换关注状态")
+    public Result attention(@RequestParam("userId") Long userId) {
+        adminUserService.attention(userId);
+        return R.ok();
+    }
+
+    @RequestMapping("/getNameByUserId")
+    @ApiExplain("根据用户ID获取用户名称")
+    public Result getNameByUserId(@NotNull Long userId) {
+        return R.ok(adminUserService.getNameByUserId(userId));
+    }
+
+    @RequestMapping("/queryChildUserId")
+    @ApiExplain("根据用户ID下的子用户")
+    public Result<List<Long>> queryChildUserId(@NotNull Long userId) {
+        List<Long> longList = adminUserService.queryChildUserId(userId);
+        return R.ok(longList);
+    }
+
+    @RequestMapping("/queryUserInfo")
+    @ApiOperation("查询用户信息")
+    public Result<AdminUser> queryUserInfo(@RequestParam("userId") Long userId) {
+        AdminUser byId = adminUserService.getById(userId);
+        String nameByDeptId = ApplicationContextHolder.getBean(IAdminDeptService.class).getNameByDeptId(byId.getDeptId());
+        byId.setDeptName(nameByDeptId);
+        byId.setSalt(null);
+        byId.setPassword(null);
+        return R.ok(byId);
+    }
+
+    @RequestMapping("/queryInfoByUserId")
+    @ApiExplain("根据用户ID获取用户")
+    public Result<UserInfo> queryInfoByUserId(@NotNull Long userId) {
+        AdminUser byId = adminUserService.getById(userId);
+        UserInfo userInfo = null;
+        if (byId != null && byId.getDeptId() != null) {
+            userInfo = BeanUtil.copyProperties(byId, UserInfo.class);
+            String nameByDeptId = ApplicationContextHolder.getBean(IAdminDeptService.class).getNameByDeptId(byId.getDeptId());
+            userInfo.setDeptName(nameByDeptId);
+        }
+        return R.ok(userInfo);
+    }
+
+    @PostMapping("/queryUserByIds")
+    @ApiExplain("根据用户ID获取用户")
+    public Result<List<SimpleUser>> queryUserByIds(@RequestBody List<Long> ids) {
+        List<SimpleUser> simpleUsers = adminUserService.queryUserByIds(ids);
+        return R.ok(simpleUsers);
+    }
+
+    @PostMapping("/queryUserById")
+    @ApiExplain("根据用户ID获取用户")
+    public Result<SimpleUser> queryUserById(@RequestParam("userId") Long userId) {
+        AdminUser adminUser = adminUserService.getById(userId);
+        return R.ok(BeanUtil.copyProperties(adminUser, SimpleUser.class));
+    }
+
+    @PostMapping("/queryUserByDeptIds")
+    @ApiExplain("根据部门ID获取用户ids")
+    public Result<List<Long>> queryUserByDeptIds(@RequestBody List<Integer> ids) {
+        List<Long> userIds = adminUserService.queryUserByDeptIds(ids);
+        return R.ok(userIds);
+    }
+
+    @PostMapping("/readNotice")
+    @ApiOperation("设置更新日志为已读")
+    public Result readNotice() {
+        Long userId = UserUtil.getUserId();
+        String name = "readNotice";
+        Integer count = adminUserConfigService.lambdaQuery().eq(AdminUserConfig::getUserId, userId).eq(AdminUserConfig::getName, name).count();
+        if (count > 1) {
+            adminUserConfigService.lambdaUpdate().set(AdminUserConfig::getStatus, 1).eq(AdminUserConfig::getUserId, userId).eq(AdminUserConfig::getName, name).update();
+        } else {
+            AdminUserConfig adminUserConfig = new AdminUserConfig();
+            adminUserConfig.setValue("");
+            adminUserConfig.setName(name);
+            adminUserConfig.setUserId(userId);
+            adminUserConfig.setStatus(1);
+            adminUserConfig.setDescription("升级日志阅读状态");
+            adminUserConfigService.save(adminUserConfig);
+        }
+        return R.ok();
+    }
+
+
+    @PostMapping("/queryAuthUserList")
+    @ApiOperation("查询权限下用户")
+    public Result<List<SimpleUser>> queryAuthUserList() {
+        List<SimpleUser> userList = new ArrayList<>();
+        if (UserUtil.isAdmin()) {
+            userList.addAll(adminUserService.list().stream().map(user -> BeanUtil.copyProperties(user, SimpleUser.class)).collect(Collectors.toList()));
+        } else {
+            List<Long> childUserId = adminUserService.queryChildUserId(UserUtil.getUserId());
+            userList.addAll(adminUserService.queryUserByIds(childUserId));
+        }
+        return R.ok(userList);
+    }
+
+    @PostMapping("/queryDeptUserList/{deptId}")
+    @ApiOperation("查询部门用户列表(表单使用)")
+    public Result<DeptUserListVO> queryDeptUserList(@PathVariable Integer deptId) {
+        DeptUserListVO deptUserListVO = adminUserService.queryDeptUserList(deptId);
+        return Result.ok(deptUserListVO);
+    }
+
+    @PostMapping("/queryDeptUserListByHrm")
+    @ApiOperation("查询部门用户列表(hrm添加员工使用)")
+    public Result<Set<HrmSimpleUserVO>> queryDeptUserListByHrm(@RequestBody DeptUserListByHrmBO deptUserListByHrmBO) {
+        Set<HrmSimpleUserVO> userList = adminUserService.queryDeptUserListByHrm(deptUserListByHrmBO);
+        return Result.ok(userList);
+    }
+
+    @PostMapping("/queryUserIdByRealName")
+    @ApiOperation("查询用户id根据真实姓名")
+    public Result<List<Long>> queryUserIdByRealName(@RequestParam("realNames") List<String> realNames) {
+        List<Long> userIdList = adminUserService.queryUserIdByRealName(realNames);
+        return Result.ok(userIdList);
+    }
+
+    @PostMapping("/queryLoginUserInfo")
+    @ApiExplain("模拟查询登陆用户信息")
+    public Result<UserInfo> queryLoginUserInfo(@RequestParam("userId") Long userId) {
+        UserInfo userInfo = adminUserService.queryLoginUserInfo(userId);
+        return Result.ok(userInfo);
+    }
+
+    @PostMapping("/querySystemStatus")
+    @ApiOperation("查询当前系统初始状态")
+    @ParamAspect
+    public Result<Integer> querySystemStatus() {
+        Integer status = adminUserService.querySystemStatus();
+        return R.ok(status);
+    }
+
+    @PostMapping("/initUser")
+    @ApiOperation("初始化系统用户")
+    @ParamAspect
+    public Result initUser(@Validated @RequestBody SystemUserBO systemUserBO) {
+        adminUserService.initUser(systemUserBO);
+        return R.ok();
+    }
+
+    @RequestMapping("/findTenantList")
+    @ApiOperation(value = "通过name查询用户", httpMethod = "POST")
+    public Result<List<Map<String, Object>>> findTenantList(String username) {
+        List<Map<String, Object>> userInfoList = adminUserService.findTenantList(username);
+        return Result.ok(userInfoList);
+    }
+
+    /**
+     * 只修改密码,不做其他操作
+     *
+     * @param oldPass
+     * @param newPass
+     * @return
+     */
+    @PostMapping("/newUpdatePassword")
+    @ApiOperation("修改登录密码")
+    public Result newUpdatePassword(@RequestParam("oldPwd") String oldPass, @RequestParam("newPwd") String newPass) {
+        AdminUser adminUser = adminUserService.getById(UserUtil.getUserId());
+        if (!UserUtil.verify(adminUser.getUsername() + oldPass, adminUser.getSalt(), adminUser.getPassword())) {
+            return R.error(AdminCodeEnum.ADMIN_PASSWORD_ERROR);
+        }
+        adminUser.setPassword(newPass);
+        adminUserService.newUpdateUser(adminUser);
+        return R.ok();
+    }
+
+    @PostMapping("/addUserMap")
+    @ApiOperation("同步账号:新增用户")
+    @OperateLog(detail = "同步账号:新增用户", types = LogTypes.SYS, behavior = LogBehavior.INSERT)
+    public Integer addUserMap(@RequestBody Map map) {
+        AdminUserVO adminUserVO = new AdminUserVO();
+        BeanUtil.copyProperties(map, adminUserVO);
+        Long userId = adminUserService.addUser(adminUserVO);
+        return Integer.valueOf(userId.toString());
+    }
+
+}
+

+ 38 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/AdminUserHisTableController.java

@@ -0,0 +1,38 @@
+package com.kakarote.admin.controller;
+
+import com.kakarote.admin.service.IAdminUserHisTableService;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.feign.admin.entity.CallUser;
+import io.swagger.annotations.Api;
+import io.swagger.annotations.ApiOperation;
+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.RequestMapping;
+import org.springframework.web.bind.annotation.RestController;
+
+/**
+ * @author Ian
+ * @date 2020/8/28
+ */
+@RestController
+@Api(tags = "授权坐席相关接口")
+@RequestMapping("/adminUserHisTable")
+public class AdminUserHisTableController {
+
+    @Autowired
+    private IAdminUserHisTableService adminUserHisTableService;
+
+    @PostMapping("/authorize")
+    @ApiOperation("员工坐席授权")
+    public Result<Boolean> authorize(@RequestBody CallUser callUser){
+        return Result.ok(adminUserHisTableService.authorize(callUser.getUserIds(),callUser.getState()));
+    }
+
+    @PostMapping("/checkAuth")
+    @ApiOperation("判断用户是否为坐席")
+    public Result<Boolean> checkAuth() {
+        return Result.ok(adminUserHisTableService.checkAuth());
+    }
+
+}

+ 44 - 0
admin/admin/src/main/java/com/kakarote/admin/controller/SysAreaController.java

@@ -0,0 +1,44 @@
+package com.kakarote.admin.controller;
+
+
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.kakarote.admin.entity.BO.SysAreaBO;
+import com.kakarote.admin.entity.PO.SysArea;
+import com.kakarote.admin.service.ISysAreaService;
+import com.kakarote.core.common.Result;
+import io.swagger.annotations.ApiOperation;
+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.RequestMapping;
+
+import org.springframework.web.bind.annotation.RestController;
+
+import java.util.List;
+
+/**
+ * <p>
+ * 区划表 前端控制器
+ * </p>
+ *
+ * @author lzy
+ * @since 2021-03-18
+ */
+@RestController
+@RequestMapping("/sysArea")
+public class SysAreaController {
+
+    @Autowired
+    private ISysAreaService sysAreaService;
+
+    /**
+     * 区划查询
+     */
+    @ApiOperation("区划查询")
+    @PostMapping("/list")
+    public Result<List<SysArea>> list(@RequestBody SysAreaBO sysAreaBO){
+        List<SysArea> list = sysAreaService.selectAreaList(sysAreaBO);
+        return Result.ok(list);
+    }
+}
+

+ 87 - 0
admin/admin/src/main/java/com/kakarote/admin/demo/controller/WfDemoController.java

@@ -0,0 +1,87 @@
+package com.kakarote.admin.demo.controller;
+
+
+import cn.hutool.core.util.IdUtil;
+import com.kakarote.admin.demo.entity.BO.WfDemoBO;
+import com.kakarote.admin.demo.entity.PO.WfDemo;
+import com.kakarote.admin.demo.service.IWfDemoService;
+import com.kakarote.core.common.Result;
+import com.kakarote.core.utils.UserUtil;
+import com.kakarote.core.workflow.WfAnnotation;
+import io.seata.spring.annotation.GlobalTransactional;
+import io.swagger.annotations.ApiParam;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+
+import javax.servlet.http.HttpServletRequest;
+import java.util.List;
+
+/**
+ * <p>
+ * DEMO表 前端控制器
+ * </p>
+ *
+ * @author wudw
+ * @since 2021-03-15
+ */
+@RestController
+@RequestMapping("/adminDemo")
+public class WfDemoController {
+
+    @Autowired
+    private IWfDemoService demoService;
+
+    /**
+     * 分页列表
+     */
+    @PostMapping("/list")
+    public Result list(@RequestBody WfDemoBO wfDemo) {
+        return Result.ok(demoService.selectByPage(wfDemo));
+    }
+
+    /**
+     * 获取详情
+     */
+    @PostMapping("/getById/{id}")
+    public Result getById(@PathVariable String id) {
+        return Result.ok(demoService.getById(id));
+    }
+
+    /**
+     * 新增/修改
+     */
+    @PostMapping("/saveOrUpdate")
+    @WfAnnotation
+    public Result saveOrUpdate(@RequestBody WfDemo wfDemo) {
+        if (wfDemo.getId() == null) {
+            wfDemo.setId(IdUtil.randomUUID());
+            wfDemo.setOwnerUserId(UserUtil.getUserId());
+            demoService.save(wfDemo);
+        }else{
+            demoService.updateById(wfDemo);
+        }
+        //throw new RuntimeException();
+        return Result.ok();
+    }
+
+    /**
+     * 物理删除
+     */
+    @PostMapping("/delTrueByIds")
+    public Result delete(@ApiParam(name = "ids", value = "id列表") @RequestBody List<String> ids) {
+        for (String id : ids) {
+            demoService.removeById(id);
+        }
+        return Result.ok();
+    }
+
+    /**
+     * 逻辑删除
+     */
+    @PostMapping("/delLogicByIds")
+    public Result del() {
+        //更新check_status 为 7
+        return Result.ok();
+    }
+}
+

+ 70 - 0
admin/admin/src/main/java/com/kakarote/admin/demo/entity/BO/WfDemoBO.java

@@ -0,0 +1,70 @@
+package com.kakarote.admin.demo.entity.BO;
+
+import com.baomidou.mybatisplus.annotation.FieldFill;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.kakarote.core.entity.PageEntity;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * <p>
+ * DEMO表
+ * </p>
+ *
+ * @author wudw
+ * @since 2021-03-15
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@ApiModel("DEMO查询对象")
+public class WfDemoBO extends PageEntity {
+
+    @ApiModelProperty(value = "search")
+    private String search;
+
+    @ApiModelProperty(value = "编号")
+    private String number;
+
+    @ApiModelProperty(value = "内容")
+    private String content;
+
+    @ApiModelProperty(value = "创建人ID")
+    @TableField(fill = FieldFill.INSERT)
+    private Long createUserId;
+
+    @ApiModelProperty(value = "负责人ID")
+    private Long ownerUserId;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    @ApiModelProperty(value = "更新时间")
+    @TableField(fill = FieldFill.UPDATE)
+    private Date updateTime;
+
+    @ApiModelProperty(value = "备注")
+    private String remarks;
+
+    @ApiModelProperty(value = "0待审核、1通过、2拒绝、3审核中 4:撤回 5 未提交")
+    private Integer checkStatus;
+
+    @ApiModelProperty(value = "审核记录ID")
+    private Integer examineRecordId;
+
+    @ApiModelProperty(value = "批次")
+    private String batchId;
+
+    private Integer tenantId;
+
+    private String projectId;
+
+
+}

+ 76 - 0
admin/admin/src/main/java/com/kakarote/admin/demo/entity/PO/WfDemo.java

@@ -0,0 +1,76 @@
+package com.kakarote.admin.demo.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.TableName;
+import java.util.Date;
+import com.baomidou.mybatisplus.annotation.FieldFill;
+import com.baomidou.mybatisplus.annotation.TableField;
+import java.io.Serializable;
+
+import com.kakarote.core.feign.wf.entity.WfVO;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+/**
+ * <p>
+ * DEMO表
+ * </p>
+ *
+ * @author wudw
+ * @since 2021-03-15
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("qdoner_wf_demo")
+@ApiModel(value="WfDemo对象", description="DEMO表")
+public class WfDemo implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @ApiModelProperty(value = "ID")
+    private String id;
+
+    @ApiModelProperty(value = "编号")
+    private String number;
+
+    @ApiModelProperty(value = "内容")
+    private String content;
+
+    @ApiModelProperty(value = "创建人ID")
+    @TableField(fill = FieldFill.INSERT)
+    private Long createUserId;
+
+    @ApiModelProperty(value = "负责人ID")
+    private Long ownerUserId;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    @ApiModelProperty(value = "更新时间")
+    @TableField(fill = FieldFill.UPDATE)
+    private Date updateTime;
+
+    @ApiModelProperty(value = "备注")
+    private String remarks;
+
+    @ApiModelProperty(value = "0待审核、1通过、2拒绝、3审核中 4:撤回 5 未提交")
+    private Integer checkStatus;
+
+    @ApiModelProperty(value = "审核记录ID")
+    private Integer examineRecordId;
+
+    @ApiModelProperty(value = "批次")
+    private String batchId;
+
+    private Integer tenantId;
+
+    private String projectId;
+
+    //Copy 审批
+    @TableField(exist = false)
+    WfVO wfVO;
+}

+ 19 - 0
admin/admin/src/main/java/com/kakarote/admin/demo/mapper/WfDemoMapper.java

@@ -0,0 +1,19 @@
+package com.kakarote.admin.demo.mapper;
+
+import com.kakarote.admin.demo.entity.BO.WfDemoBO;
+import com.kakarote.admin.demo.entity.PO.WfDemo;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.servlet.BaseMapper;
+import org.apache.ibatis.annotations.Param;
+
+/**
+ * <p>
+ * DEMO表 Mapper 接口
+ * </p>
+ *
+ * @author wudw
+ * @since 2021-03-15
+ */
+public interface WfDemoMapper extends BaseMapper<WfDemo> {
+    BasePage<WfDemo> selectByPage(BasePage<WfDemo> parse, @Param("data") WfDemoBO planBO);
+}

+ 21 - 0
admin/admin/src/main/java/com/kakarote/admin/demo/mapper/xml/WfDemoMapper.xml

@@ -0,0 +1,21 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.kakarote.admin.demo.mapper.WfDemoMapper">
+
+    <select id="selectByPage" resultType="com.kakarote.admin.demo.entity.PO.WfDemo">
+        select a.*
+        from qdoner_wf_demo a
+        <where>
+           1=1
+            <if test="data.search != null and data.search != ''">
+                AND (a.number like concat('%', #{data.search}, '%')
+                  OR
+                    a.content like concat('%', #{data.search}, '%')
+                  )
+            </if>
+        </where>
+        order by a.create_time desc
+    </select>
+
+
+</mapper>

+ 18 - 0
admin/admin/src/main/java/com/kakarote/admin/demo/service/IWfDemoService.java

@@ -0,0 +1,18 @@
+package com.kakarote.admin.demo.service;
+
+import com.kakarote.admin.demo.entity.BO.WfDemoBO;
+import com.kakarote.admin.demo.entity.PO.WfDemo;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.servlet.BaseService;
+
+/**
+ * <p>
+ * DEMO表 服务类
+ * </p>
+ *
+ * @author wudw
+ * @since 2021-03-15
+ */
+public interface IWfDemoService extends BaseService<WfDemo> {
+    BasePage<WfDemo> selectByPage(WfDemoBO demoBO);
+}

+ 27 - 0
admin/admin/src/main/java/com/kakarote/admin/demo/service/impl/WfDemoServiceImpl.java

@@ -0,0 +1,27 @@
+package com.kakarote.admin.demo.service.impl;
+
+import com.kakarote.admin.demo.entity.BO.WfDemoBO;
+import com.kakarote.admin.demo.entity.PO.WfDemo;
+import com.kakarote.admin.demo.mapper.WfDemoMapper;
+import com.kakarote.admin.demo.service.IWfDemoService;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.servlet.BaseServiceImpl;
+import org.springframework.stereotype.Service;
+
+/**
+ * <p>
+ * DEMO表 服务实现类
+ * </p>
+ *
+ * @author wudw
+ * @since 2021-03-15
+ */
+@Service
+public class WfDemoServiceImpl extends BaseServiceImpl<WfDemoMapper, WfDemo> implements IWfDemoService {
+
+    @Override
+    public BasePage<WfDemo> selectByPage(WfDemoBO demoBO) {
+        BasePage<WfDemo> serviceBasePage = baseMapper.selectByPage(demoBO.parse(), demoBO);
+        return serviceBasePage;
+    }
+}

+ 24 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminCompanyBO.java

@@ -0,0 +1,24 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import javax.validation.constraints.NotEmpty;
+
+/**
+ * @author zhangzhiwei
+ * BO业务逻辑代码
+ */
+@Data
+@ToString
+@ApiModel(value="AdminCompany对象", description="云平台公司配置表")
+public class AdminCompanyBO {
+    @ApiModelProperty(value = "企业名称",required = true,example = "良心企业")
+    @NotEmpty
+    private String companyName;
+
+    @ApiModelProperty(value = "企业LOGO", example = "/logo")
+    private String companyLogo;
+}

+ 15 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDeleteByBatchIdBO.java

@@ -0,0 +1,15 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Getter;
+import lombok.Setter;
+
+@Getter
+@Setter
+public class AdminDeleteByBatchIdBO {
+
+    private String batchId;
+
+    @ApiModelProperty("1 附件 2 图片")
+    private Integer type;
+}

+ 43 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDeptBO.java

@@ -0,0 +1,43 @@
+package com.kakarote.admin.entity.BO;
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import javax.validation.constraints.NotNull;
+import javax.validation.constraints.Size;
+import java.util.Date;
+
+/**
+ * @author zhangzhiwei
+ */
+@Data
+@ToString
+@ApiModel(value="部门编辑对象", description="部门对象")
+public class AdminDeptBO {
+
+    @ApiModelProperty(value = "部门ID")
+    private Integer deptId;
+
+    @ApiModelProperty(value = "上级部门ID,0为最上级")
+    @NotNull
+    private Integer pid;
+
+    @ApiModelProperty(value = "部门名称")
+    @NotNull
+    @Size(max = 20)
+    private String name;
+
+    @ApiModelProperty("状态:0停用,1启用")
+    private String status;
+
+    @ApiModelProperty("有效开始日期'")
+    @JsonFormat(pattern = "yyyy-MM-dd")
+    private Date effectiveStartDate;
+
+    @ApiModelProperty("有效结束日期''")
+    @JsonFormat(pattern = "yyyy-MM-dd")
+    private Date effectiveEndDate;
+}

+ 44 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDeptConfigBO.java

@@ -0,0 +1,44 @@
+package com.kakarote.admin.entity.BO;
+
+import com.baomidou.mybatisplus.annotation.FieldFill;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.kakarote.core.entity.PageEntity;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.ToString;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * <p>
+ * 
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-16
+ */
+@Data
+@ToString
+@EqualsAndHashCode(callSuper = false)
+@ApiModel("租户对接配置列表查询")
+public class AdminDeptConfigBO extends PageEntity {
+
+    @ApiModelProperty(value = "配置类型(10:钉钉内部应用、20:企业微信内部应用、……)")
+    private String type;
+
+    private String name;
+
+    private String params;
+
+    @ApiModelProperty(value = "状态 0:禁用  1:启用")
+    private String status;
+
+    private String messageType;
+
+    private Integer tenantId;
+}

+ 22 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDeptQueryBO.java

@@ -0,0 +1,22 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import io.swagger.annotations.ApiParam;
+import lombok.Data;
+import lombok.ToString;
+
+/**
+ * @author zhangzhiwei
+ */
+@Data
+@ToString
+@ApiModel(value="部门编辑对象", description="部门对象")
+public class AdminDeptQueryBO {
+
+    @ApiParam(name = "id", value = "父级ID", required = true, example = "0")
+    private Integer id;
+
+    @ApiModelProperty(value = "类型")
+    private String type;
+}

+ 27 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDictMathBO.java

@@ -0,0 +1,27 @@
+package com.kakarote.admin.entity.BO;
+
+import com.kakarote.core.entity.PageEntity;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+
+/**
+ * <p>
+ * 监测点设置
+ * </p>
+ *
+ * @author lzy
+ * @since 2021-05-18
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@ApiModel("维护计划列表查询对象")
+public class AdminDictMathBO extends PageEntity {
+
+    @ApiModelProperty(value = "本系统字典类型")
+    private String selfDict;
+
+    @ApiModelProperty(value = "本系统字典值")
+    private String selfDictValue;
+}

+ 47 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminDictTypeBO.java

@@ -0,0 +1,47 @@
+package com.kakarote.admin.entity.BO;
+
+import com.fasterxml.jackson.annotation.JsonFormat;
+import com.kakarote.core.entity.PageEntity;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import org.apache.commons.lang3.builder.ToStringBuilder;
+import org.apache.commons.lang3.builder.ToStringStyle;
+
+import javax.validation.constraints.NotBlank;
+import javax.validation.constraints.Size;
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * 字典类型表 sys_dict_type
+ * 
+ * @author ruoyi
+ */
+@Data
+@ApiModel("字典表查询对象")
+public class AdminDictTypeBO  extends PageEntity
+{
+
+    /** 字典名称 */
+    @ApiModelProperty("字典名称")
+    private String dictName;
+
+    /** 字典类型 */
+    @ApiModelProperty("字典类型")
+    private String dictType;
+
+    /** 状态(0正常 1停用) */
+    @ApiModelProperty("状态")
+    private String status;
+
+    /** 创建时间 */
+    @ApiModelProperty("创建时间")
+    @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss")
+    private Date createTime;
+
+    /** 备注 */
+    @ApiModelProperty("备注")
+    private String remark;
+
+}

+ 23 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminMessageQueryBO.java

@@ -0,0 +1,23 @@
+package com.kakarote.admin.entity.BO;
+
+import com.kakarote.core.entity.PageEntity;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+@Data
+@ApiModel("消息列表查询对象")
+public class AdminMessageQueryBO extends PageEntity {
+
+    @ApiModelProperty("是否已读")
+    private Integer isRead;
+
+    @ApiModelProperty("label")
+    private Integer label;
+
+    @ApiModelProperty("用户ID")
+    private Long userId;
+
+    @ApiModelProperty("type")
+    private Integer type;
+}

+ 44 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminUserBO.java

@@ -0,0 +1,44 @@
+package com.kakarote.admin.entity.BO;
+
+import com.kakarote.core.entity.PageEntity;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.ToString;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * @author zhangzhiwe
+ * 用户列表业务对象
+ */
+@Data
+@ToString
+@EqualsAndHashCode(callSuper = false)
+@ApiModel("用户列表查询")
+public class AdminUserBO extends PageEntity {
+
+    @ApiModelProperty(value = "类型", required = true, allowableValues = "0,1,2,3,4", example = "0")
+    private Integer label;
+
+    @ApiModelProperty("昵称")
+    private String realname;
+
+    @ApiModelProperty("昵称")
+    private Integer status;
+
+    @ApiModelProperty("角色ID")
+    private Integer roleId;
+
+    @ApiModelProperty("部门ID")
+    private Integer deptId;
+
+    @ApiModelProperty("部门ID列表")
+    private List<Integer> deptIdList = new ArrayList<>();
+
+    @ApiModelProperty("角色类型")
+    private Integer roleType;
+
+}

+ 28 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/AdminUserStatusBO.java

@@ -0,0 +1,28 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import java.util.List;
+
+/**
+ * @author zhangzhiwe
+ * 用户状态修改
+ */
+@Data
+@ToString
+@ApiModel("用户状态修改BO")
+public class AdminUserStatusBO {
+
+    @ApiModelProperty("ids")
+    private List<Long> ids;
+
+    @ApiModelProperty("状态")
+    private Integer status;
+
+    @ApiModelProperty("密码")
+    private String password;
+
+}

+ 15 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/DeptUserListByHrmBO.java

@@ -0,0 +1,15 @@
+package com.kakarote.admin.entity.BO;
+
+import lombok.Getter;
+import lombok.Setter;
+
+import java.util.List;
+
+@Getter
+@Setter
+public class DeptUserListByHrmBO {
+
+    private List<Long> userIdList;
+
+    private List<Integer> deptIdList;
+}

+ 17 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/DeptUserListVO.java

@@ -0,0 +1,17 @@
+package com.kakarote.admin.entity.BO;
+
+import com.kakarote.admin.entity.VO.HrmSimpleUserVO;
+import lombok.Getter;
+import lombok.Setter;
+
+import java.util.List;
+
+@Getter
+@Setter
+public class DeptUserListVO {
+
+
+    private List<DeptVO> deptList;
+
+    private List<HrmSimpleUserVO> userList;
+}

+ 26 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/DeptVO.java

@@ -0,0 +1,26 @@
+package com.kakarote.admin.entity.BO;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Getter;
+import lombok.Setter;
+
+@Getter
+@Setter
+public class DeptVO {
+
+
+    @ApiModelProperty(value = "部门id")
+    private Integer deptId;
+
+    @ApiModelProperty(value = "父级ID 顶级部门为0")
+    private Integer pid;
+
+    @ApiModelProperty(value = "部门名称")
+    private String name;
+
+    @ApiModelProperty("在职人数")
+    private Integer allNum;
+
+    @ApiModelProperty("是否有下级部门 0 否 1 是")
+    private Integer hasChildren;
+
+}

+ 29 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/HrmAddUserBO.java

@@ -0,0 +1,29 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Getter;
+import lombok.Setter;
+
+import java.util.List;
+
+@Getter
+@Setter
+public class HrmAddUserBO {
+
+    @ApiModelProperty(value = "密码")
+    private String password;
+
+    @ApiModelProperty(value = "部门ID")
+    private Integer deptId;
+
+    @ApiModelProperty("角色id")
+    private String roleId;
+
+    @ApiModelProperty(value = "上级ID")
+    private Long parentId;
+
+    @ApiModelProperty("员工id")
+    private List<Integer> employeeIds;
+
+
+}

+ 29 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/LogWelcomeSpeechBO.java

@@ -0,0 +1,29 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import javax.validation.constraints.NotNull;
+import javax.validation.constraints.Size;
+
+/**
+ * @author zhangzhiwei
+ * 模块设置VO
+ */
+@ToString
+@Data
+@ApiModel("日志欢迎语对象")
+public class LogWelcomeSpeechBO {
+
+    @ApiModelProperty(value = "设置ID", required = true)
+    @NotNull
+    private Integer settingId;
+
+    @ApiModelProperty(value = "日志欢迎语", required = true)
+    @NotNull
+    @Size(max = 100)
+    private String value;
+
+}

+ 34 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/ModuleSettingBO.java

@@ -0,0 +1,34 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import javax.validation.constraints.Max;
+import javax.validation.constraints.Min;
+import javax.validation.constraints.NotNull;
+
+/**
+ * @author zhangzhiwei
+ * 模块设置VO
+ */
+@ToString
+@Data
+@ApiModel("应用管理设置")
+public class ModuleSettingBO {
+
+    @ApiModelProperty(value = "设置ID", required = true)
+    @NotNull
+    private Integer settingId;
+
+    @ApiModelProperty(value = "状态 1:启用 0:停用", required = true,allowableValues = "0,1")
+    @NotNull(message = "状态不能为空")
+    @Max(1)
+    @Min(0)
+    private Integer status;
+
+    @ApiModelProperty(value = "名称")
+    private String name;
+
+}

+ 16 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/RenameFileBO.java

@@ -0,0 +1,16 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Getter;
+import lombok.Setter;
+
+@Getter
+@Setter
+public class RenameFileBO {
+
+    @ApiModelProperty(value = "附件id")
+    private Long fileId;
+
+    @ApiModelProperty(value = "附件名称")
+    private String name;
+}

+ 22 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/SysAreaBO.java

@@ -0,0 +1,22 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import javax.validation.constraints.NotNull;
+
+/**
+ * @author zhangzhiwei
+ * BO业务逻辑代码
+ */
+@Data
+@ApiModel(value="SysArea查询对象")
+public class SysAreaBO {
+    @ApiModelProperty(value = "级别:1、省级 2、市级 3、区县")
+    private Integer level;
+
+    @ApiModelProperty(value = "父级id")
+    private Integer parentId;
+}

+ 26 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/SystemUserBO.java

@@ -0,0 +1,26 @@
+package com.kakarote.admin.entity.BO;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import javax.validation.constraints.NotNull;
+import java.io.Serializable;
+
+/**
+ * 初始话用户BO
+ */
+@Data
+public class SystemUserBO implements Serializable {
+
+    @ApiModelProperty("用户名")
+    @NotNull
+    private String username;
+
+    @ApiModelProperty("凭证")
+    @NotNull
+    private String code;
+
+    @ApiModelProperty("密码")
+    @NotNull
+    private String password;
+}

+ 33 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/BO/UserBookBO.java

@@ -0,0 +1,33 @@
+package com.kakarote.admin.entity.BO;
+
+import com.kakarote.core.entity.PageEntity;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+/**
+ * @author wyq
+ */
+@Data
+@ApiModel("通讯录查询")
+public class UserBookBO extends PageEntity {
+
+    @ApiModelProperty("搜索关键字")
+    private String search;
+
+    @ApiModelProperty("排列顺序 2倒序 其他是正序")
+    private Integer initial;
+
+    @ApiModelProperty("部门id")
+    private Integer deptId;
+
+    @ApiModelProperty(value = "关注状态,0未关注,1已关注")
+    private Integer status;
+
+    @ApiModelProperty(value = "用户ID")
+    private Long userId;
+
+    @ApiModelProperty("tenantId")
+    private Long tenantId;
+
+}

+ 39 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminAttention.java

@@ -0,0 +1,39 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 通讯录用户关注表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_attention")
+@ApiModel(value="AdminAttention对象", description="通讯录用户关注表")
+public class AdminAttention implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "attention_id", type = IdType.AUTO)
+    private Integer attentionId;
+
+    @ApiModelProperty(value = "被关注人")
+    private Long beUserId;
+
+    @ApiModelProperty(value = "关注人")
+    private Long attentionUserId;
+}

+ 51 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminConfig.java

@@ -0,0 +1,51 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 客户规则
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_config")
+@ApiModel(value="AdminConfig对象", description="客户规则")
+public class AdminConfig implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "setting_id", type = IdType.AUTO)
+    private Integer settingId;
+
+    @ApiModelProperty(value = "状态,0:不启用 1 : 启用")
+    private Integer status;
+
+    @ApiModelProperty(value = "设置名称")
+    private String name;
+
+    @ApiModelProperty(value = "值")
+    private String value;
+
+    @ApiModelProperty(value = "描述")
+    private String description;
+
+    @TableField(select = false)
+    @ApiModelProperty(value = "租户ID")
+    private Integer tenantId;
+
+}

+ 74 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDept.java

@@ -0,0 +1,74 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ * 部门表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_dept")
+@ApiModel(value="AdminDept对象", description="部门表")
+public class AdminDept implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "dept_id", type = IdType.AUTO)
+    private Integer deptId;
+
+    @ApiModelProperty(value = "父级ID 顶级部门为0")
+    private Integer pid;
+
+    @ApiModelProperty(value = "部门名称")
+    private String name;
+
+    @ApiModelProperty(value = "排序 越大越靠后")
+    private Integer num;
+
+    @ApiModelProperty(value = "部门备注")
+    private String remark;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "菜单列表")
+    private Map<String, List<Integer>> rules;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "菜单id列表")
+    private List<Integer> menuIds = new ArrayList<>();
+
+    @TableField(select = false)
+    @ApiModelProperty(value = "租户ID")
+    private Integer tenantId;
+
+    @ApiModelProperty("状态:0停用,1启用")
+    private String status;
+
+    @ApiModelProperty("有效开始日期'")
+    @JsonFormat(pattern = "yyyy-MM-dd")
+    private Date effectiveStartDate;
+
+    @ApiModelProperty("有效结束日期''")
+    @JsonFormat(pattern = "yyyy-MM-dd")
+    private Date effectiveEndDate;
+}

+ 51 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDeptConfig.java

@@ -0,0 +1,51 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.TableName;
+import java.util.Date;
+import com.baomidou.mybatisplus.annotation.FieldFill;
+import com.baomidou.mybatisplus.annotation.TableField;
+import java.io.Serializable;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+/**
+ * <p>
+ * 
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-16
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_dept_config")
+@ApiModel(value="AdminDeptConfig对象", description="")
+public class AdminDeptConfig implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    private String id;
+
+    @ApiModelProperty(value = "配置类型(10:钉钉内部应用、20:企业微信内部应用、……)")
+    private String type;
+
+    private String name;
+
+    private String params;
+
+    @ApiModelProperty(value = "状态 0:禁用  1:启用")
+    private String status;
+
+    private String messageType;
+
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    private Integer tenantId;
+
+
+}

+ 46 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDeptMenu.java

@@ -0,0 +1,46 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 部门(租户)菜单对应关系表
+ * </p>
+ *
+ * @author pangzhen
+ * @since 2020-11-24
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_dept_menu")
+@ApiModel(value="AdminDeptMenu对象", description="部门(租户)菜单对应关系表")
+public class AdminDeptMenu implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "部门(租户)ID")
+    private Integer deptId;
+
+    @ApiModelProperty(value = "菜单ID")
+    private Integer menuId;
+
+    @TableField(select = false)
+    @ApiModelProperty(value = "租户ID")
+    private Integer tenantId;
+
+
+}

+ 270 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDictData.java

@@ -0,0 +1,270 @@
+package com.kakarote.admin.entity.PO;
+
+import javax.validation.constraints.NotBlank;
+import javax.validation.constraints.Size;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+import org.apache.commons.lang3.builder.ToStringBuilder;
+import org.apache.commons.lang3.builder.ToStringStyle;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * 字典数据表 sys_dict_data
+ * 
+ * @author ruoyi
+ */
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_dict_data")
+@ApiModel(value="AdminDictData", description="字典数据")
+public class AdminDictData implements Serializable
+{
+    private static final long serialVersionUID = 1L;
+
+    /** 字典编码 */
+    @TableId(value = "dict_code", type = IdType.AUTO)
+    private Long dictCode;
+
+    /** 字典排序 */
+    private Long dictSort;
+
+    /** 字典标签 */
+    private String dictLabel;
+
+    /** 字典键值 */
+    private String dictValue;
+
+    /** 字典类型 */
+    private String dictType;
+
+    /** 样式属性(其他样式扩展) */
+    private String cssClass;
+
+    /** 表格字典样式 */
+    private String listClass;
+
+    /** 是否默认(Y是 N否) */
+    private String isDefault;
+
+    /** 状态(0正常 1停用) */
+    private String status;
+
+    /** 创建者 */
+    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;
+
+    @TableField(select = false)
+    private Long tenantId;//租户ID
+
+    private Long copyId;//复制ID
+
+    public Long getCopyId() {
+        return copyId;
+    }
+
+    public void setCopyId(Long copyId) {
+        this.copyId = copyId;
+    }
+
+    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 "1".equals(this.isDefault) ? true : false;
+    }
+
+    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;
+    }
+
+    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 Long getTenantId() {
+        return tenantId;
+    }
+
+    public void setTenantId(Long tenantId) {
+        this.tenantId = tenantId;
+    }
+
+//    @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();
+    }
+}

+ 66 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDictMatch.java

@@ -0,0 +1,66 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.baomidou.mybatisplus.annotation.IdType;
+import java.util.Date;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.FieldFill;
+import com.baomidou.mybatisplus.annotation.TableField;
+import java.io.Serializable;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+/**
+ * <p>
+ * 
+ * </p>
+ *
+ * @author lzy
+ * @since 2021-11-30
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_dict_match")
+@ApiModel(value="AdminDictMatch对象", description="")
+public class AdminDictMatch implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "本系统字典类型")
+    private String selfDict;
+
+    @ApiModelProperty(value = "本系统字典值")
+    private String selfDictValue;
+
+    @ApiModelProperty(value = "对应系统编码")
+    private String matchSystem;
+
+    @ApiModelProperty(value = "对应系统字典类型")
+    private String matchDict;
+
+    @ApiModelProperty(value = "对应系统值")
+    private String matchValue;
+
+    @ApiModelProperty(value = "对应系统名称")
+    private String matchSysName;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    @ApiModelProperty(value = "创建人")
+    private String createBy;
+
+    private Integer tenantId;
+
+    @ApiModelProperty(value = "备注")
+    private String remarks;
+
+}

+ 194 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminDictType.java

@@ -0,0 +1,194 @@
+package com.kakarote.admin.entity.PO;
+
+import javax.validation.constraints.NotBlank;
+import javax.validation.constraints.Size;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+import org.apache.commons.lang3.builder.ToStringBuilder;
+import org.apache.commons.lang3.builder.ToStringStyle;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * 字典类型表 sys_dict_type
+ * 
+ * @author ruoyi
+ */
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_dict_type")
+@ApiModel(value="AdminDictType", description="字典类型")
+public class AdminDictType implements Serializable
+{
+    private static final long serialVersionUID = 1L;
+
+    /** 字典主键 */
+    @TableId(value = "dict_id", type = IdType.AUTO)
+    private Long dictId;
+
+    /** 字典名称 */
+    private String dictName;
+
+    /** 字典类型 */
+    private String dictType;
+
+    /** 状态(0正常 1停用) */
+    private String status;
+
+    /** 创建者 */
+    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;
+
+    @TableField(select = false)
+    private Long tenantId;//租户ID
+
+    private Long copyId;//复制ID
+
+    public Long getCopyId() {
+        return copyId;
+    }
+
+    public void setCopyId(Long copyId) {
+        this.copyId = copyId;
+    }
+
+    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个字符")
+    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;
+    }
+
+
+    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 Long getTenantId() {
+        return tenantId;
+    }
+
+    public void setTenantId(Long tenantId) {
+        this.tenantId = tenantId;
+    }
+
+    //    @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();
+    }
+}

+ 70 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminFile.java

@@ -0,0 +1,70 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.*;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * <p>
+ * 附件表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_file")
+@ApiModel(value="AdminFile对象", description="附件表")
+public class AdminFile implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "file_id", type = IdType.ASSIGN_ID)
+    private Long fileId;
+
+    @ApiModelProperty(value = "附件名称")
+    private String name;
+
+    @ApiModelProperty(value = "附件大小(字节)")
+    private Long size;
+
+    @ApiModelProperty(value = "创建人ID")
+    @TableField(fill = FieldFill.INSERT)
+    private Long createUserId;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    @ApiModelProperty(value = "文件真实路径")
+    private String path;
+
+    @ApiModelProperty(value = "文件类型,file,img")
+    private String fileType;
+
+    @ApiModelProperty(value = "1 本地 2 阿里云oss")
+    private Integer type;
+
+    @ApiModelProperty(value = "来源 0 默认 1 admin 2 crm 3 work 4 oa 5 进销存 6 hrm")
+    private Integer source;
+
+    @ApiModelProperty(value = "1 公有访问 0 私有访问")
+    private Integer isPublic;
+
+    @ApiModelProperty(value = "批次id")
+    private String batchId;
+
+    @ApiModelProperty(value = "租户id")
+    private String tenantId;
+
+
+
+}

+ 61 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminInstrumentInfo.java

@@ -0,0 +1,61 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import java.io.Serializable;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+/**
+ * <p>
+ * 仪表盘名称表
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-08
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_instrument_info")
+@ApiModel(value="AdminInstrumentInfo对象", description="仪表盘名称表")
+public class AdminInstrumentInfo implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "仪表盘id")
+    private Integer modelId;
+
+    @ApiModelProperty(value = "仪表盘名称 1、合同金额目标及完成情况 2、数据汇总 4、业绩指标完成率 5、销售漏斗 6、遗忘提醒 7、排行榜")
+    private String modelName;
+
+    @ApiModelProperty
+    private String icon;
+    @ApiModelProperty
+    private String iconColor;
+    @ApiModelProperty
+    private String img;
+
+    @ApiModelProperty(value = "列 1左侧 2右侧")
+    private Integer list;
+
+    @ApiModelProperty(value = "排序")
+    private Integer sort;
+
+    @ApiModelProperty(value = "是否隐藏 0显示 1隐藏")
+    private Integer isHidden;
+
+    @TableField(select = false)
+    @ApiModelProperty(value = "租户ID")
+    private Integer tenantId;
+
+
+}

+ 52 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminInstrumentRole.java

@@ -0,0 +1,52 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import java.io.Serializable;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+/**
+ * <p>
+ * 仪表盘权限表
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-08
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_instrument_role")
+@ApiModel(value="AdminInstrumentRole对象", description="仪表盘权限表")
+public class AdminInstrumentRole implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "角色id")
+    private Integer roleId;
+
+    @ApiModelProperty(value = "模块id 1、合同金额目标及完成情况 2、数据汇总 4、业绩指标完成率 5、销售漏斗 6、遗忘提醒 7、排行榜")
+    private Integer modelId;
+
+    @ApiModelProperty(value = "数据权限 1、本人,2、本人及下属,3、本部门,4、本部门及下属部门,5、全部 ")
+    private Integer dataType;
+
+    @ApiModelProperty(value = "列 1左侧 2右侧")
+    private Integer list;
+
+    @ApiModelProperty(value = "排序")
+    private Integer sort;
+
+    @ApiModelProperty(value = "是否隐藏 0显示 1隐藏")
+    private Integer isHidden;
+
+}

+ 109 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminMenu.java

@@ -0,0 +1,109 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.Objects;
+
+/**
+ * <p>
+ * 后台菜单表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_menu")
+@ApiModel(value="AdminMenu对象", description="后台菜单表")
+public class AdminMenu implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @ApiModelProperty(value = "菜单ID")
+    @TableId(value = "menu_id", type = IdType.AUTO)
+    private Integer menuId;
+
+    @ApiModelProperty(value = "上级菜单ID")
+    private Integer parentId;
+
+    @ApiModelProperty(value = "图标")
+    private String icon;
+
+    @ApiModelProperty(value = "名称")
+    private String menuName;
+
+    @ApiModelProperty(value = "权限标识")
+    private String realm;
+
+    @ApiModelProperty(value = "权限URL")
+    private String realmUrl;
+
+    @ApiModelProperty(value = "所属模块")
+    private String realmModule;
+
+    @ApiModelProperty(value = "路由")
+    private String path;
+
+    @ApiModelProperty(value = "强制活跃路由")
+    private String activePath;
+
+    @ApiModelProperty(value = "前端组件")
+    private String component;
+
+    @ApiModelProperty(value = "是否禁用")
+    private String isDisabled;
+
+    @ApiModelProperty(value = "类型  1目录 2 菜单 3 按钮 4特殊")
+    private Integer menuType;
+
+    @ApiModelProperty(value = "是否隐藏")
+    private String isHide;
+
+    @ApiModelProperty(value = "排序(同级有效)")
+    private Integer sort;
+
+    @ApiModelProperty(value = "状态 1 启用 0 禁用")
+    private Integer status;
+
+    @ApiModelProperty(value = "菜单说明")
+    private String remarks;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "数据权限")
+    private Integer dataType;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "是否存在下级节点")
+    private boolean hasChildren;
+
+    @TableField(select = false)
+    @ApiModelProperty(value = "租户ID")
+    private Integer tenantId;
+
+    @ApiModelProperty(value = "复制ID")
+    private Integer copyId;
+
+    @Override
+    public boolean equals(Object o) {
+        if (this == o) return true;
+        if (o == null || getClass() != o.getClass()) return false;
+        AdminMenu adminMenu = (AdminMenu) o;
+        return Objects.equals(menuId, adminMenu.menuId);
+    }
+
+    @Override
+    public int hashCode() {
+        return Objects.hash(menuId);
+    }
+}

+ 72 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminMessage.java

@@ -0,0 +1,72 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.*;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * <p>
+ * 系统消息表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_message")
+@ApiModel(value="AdminMessage对象", description="系统消息表")
+public class AdminMessage implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @ApiModelProperty(value = "消息ID")
+    @TableId(value = "message_id", type = IdType.AUTO)
+    private Long messageId;
+
+    @ApiModelProperty(value = "消息标题")
+    private String title;
+
+    @ApiModelProperty(value = "内容")
+    private String content;
+
+    @ApiModelProperty(value = "消息大类 1 任务 2 日志 3 oa审批 4公告 5 日程 6 crm消息")
+    private Integer label;
+
+    @ApiModelProperty(value = "消息类型 详见AdminMessageEnum")
+    private Integer type;
+
+    @ApiModelProperty(value = "关联ID")
+    private Object typeId;
+
+    @ApiModelProperty(value = "消息创建者 0为系统")
+    private Long createUser;
+
+    @ApiModelProperty(value = "接收人")
+    private Long recipientUser;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    @ApiModelProperty(value = "是否已读 0 未读 1 已读")
+    private Integer isRead;
+
+    @ApiModelProperty(value = "已读时间")
+    private Date readTime;
+    @ApiModelProperty(value = "valid")
+    @TableField(exist = false)
+    private Integer valid;
+
+    @ApiModelProperty(value = "昵称")
+    @TableField(exist = false)
+    private String realname;
+
+}

+ 51 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminModelSort.java

@@ -0,0 +1,51 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 客户管理导航栏排序表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_model_sort")
+@ApiModel(value="AdminModelSort对象", description="客户管理导航栏排序表")
+public class AdminModelSort implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "导航类型 1头部导航 2客户管理左侧导航")
+    private Integer type;
+
+    @ApiModelProperty(value = "模块  1仪表盘 2待办事项 3线索 4客户 5联系人 6商机 7合同 8回款 9发票 10回访 11产品 12市场活动")
+    private String model;
+
+    @ApiModelProperty(value = "排序")
+    private Integer sort;
+
+    @ApiModelProperty(value = "是否隐藏  0不隐藏 1隐藏")
+    private Integer isHidden;
+
+    @ApiModelProperty(value = "用户id")
+    private Long userId;
+
+
+
+}

+ 59 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminOfficialImg.java

@@ -0,0 +1,59 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.*;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * <p>
+ * 官网图片
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_official_img")
+@ApiModel(value="AdminOfficialImg对象", description="官网图片")
+public class AdminOfficialImg implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "official_img_id", type = IdType.AUTO)
+    private Integer officialImgId;
+
+    @ApiModelProperty(value = "附件大小(字节)")
+    private Long size;
+
+    @ApiModelProperty(value = "创建人ID")
+    @TableField(fill = FieldFill.INSERT)
+    private Long createUserId;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    @ApiModelProperty(value = "文件真实路径")
+    private String path;
+
+    @ApiModelProperty(value = "文件路径")
+    private String filePath;
+
+    @ApiModelProperty(value = "1.官网设置 2.名片海报")
+    private Integer type;
+
+    private String name;
+
+    @ApiModelProperty(value = "0")
+    private Integer tactic;
+
+
+}

+ 71 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminRole.java

@@ -0,0 +1,71 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ * 角色表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_role")
+@ApiModel(value="AdminRole对象", description="角色表")
+public class AdminRole implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "role_id", type = IdType.AUTO)
+    private Integer roleId;
+
+    @ApiModelProperty(value = "名称")
+    private String roleName;
+
+    @ApiModelProperty(value = "0、自定义角色1、管理角色 2、客户管理角色 3、人事角色 4、财务角色 5、项目角色 8、项目自定义角色")
+    private Integer roleType;
+
+    @ApiModelProperty(value = "备注")
+    private String remark;
+
+    @ApiModelProperty(value = "1 启用 0 禁用")
+    private Integer status;
+
+    @ApiModelProperty(value = "数据权限 1、本人,2、本人及下属,3、本部门,4、本部门及下属部门,5、全部 ")
+    private Integer dataType;
+
+    @ApiModelProperty(value = "0 隐藏 1 不隐藏")
+    private Integer isHidden;
+
+    @ApiModelProperty(value = "1 系统项目管理员角色 2 项目管理角色 3 项目编辑角色 4 项目只读角色")
+    private Integer label;
+
+    @TableField(select = false)
+    @ApiModelProperty()
+    private Integer tenantId;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "菜单列表")
+    private Map<String,List<Integer>> rules;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "菜单id列表")
+    private List<Integer> menuIds = new ArrayList<>();
+
+}

+ 42 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminRoleMenu.java

@@ -0,0 +1,42 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 角色菜单对应关系表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_role_menu")
+@ApiModel(value="AdminRoleMenu对象", description="角色菜单对应关系表")
+public class AdminRoleMenu implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "角色ID")
+    private Integer roleId;
+
+    @ApiModelProperty(value = "菜单ID")
+    private Integer menuId;
+
+
+
+}

+ 45 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminRoleMenuDp.java

@@ -0,0 +1,45 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import java.io.Serializable;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+/**
+ * <p>
+ * 
+ * </p>
+ *
+ * @author shz
+ * @since 2022-09-07
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_role_menu_dp")
+@ApiModel(value="AdminRoleMenuDp对象", description="")
+public class AdminRoleMenuDp implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "角色ID")
+    private Integer roleId;
+
+    @ApiModelProperty(value = "角色ID")
+    private String platform;
+
+    @ApiModelProperty(value = "菜单")
+    private String menu;
+
+    private Integer tenantId;
+
+
+}

+ 95 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminUser.java

@@ -0,0 +1,95 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.*;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * <p>
+ * 用户表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_user")
+@ApiModel(value="AdminUser对象", description="用户表")
+public class AdminUser implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @ApiModelProperty(value = "主键")
+    @TableId(value = "user_id", type = IdType.AUTO)
+    private Long userId;
+
+    @ApiModelProperty(value = "用户名")
+    private String username;
+
+    @ApiModelProperty(value = "密码")
+    private String password;
+
+    @ApiModelProperty(value = "安全符")
+    private String salt;
+
+    @ApiModelProperty(value = "头像")
+    private String img;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    @ApiModelProperty(value = "真实姓名")
+    private String realname;
+
+    @ApiModelProperty(value = "员工编号")
+    private String num;
+
+    @ApiModelProperty(value = "手机号")
+    private String mobile;
+
+    @ApiModelProperty(value = "邮箱")
+    private String email;
+
+    @ApiModelProperty(value = "0 未选择 1 男 2 女 ")
+    private Integer sex;
+
+    @ApiModelProperty(value = "部门")
+    private Integer deptId;
+
+    @ApiModelProperty(value = "部门名称")
+    @TableField(exist = false)
+    private String deptName;
+
+    @ApiModelProperty(value = "岗位")
+    private String post;
+
+    @ApiModelProperty(value = "状态,0禁用,1正常,2未激活")
+    private Integer status;
+
+    @ApiModelProperty(value = "直属上级ID")
+    private Long parentId;
+
+    @ApiModelProperty(value = "最后登录时间")
+    private Date lastLoginTime;
+
+    @ApiModelProperty(value = "最后登录IP 注意兼容IPV6")
+    private String lastLoginIp;
+
+
+    @TableField(exist = false)
+    private String companyName;
+
+    @ApiModelProperty()
+    private Integer tenantId;
+
+    private Integer projectId;
+}

+ 54 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminUserConfig.java

@@ -0,0 +1,54 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.NoArgsConstructor;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 用户配置表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@NoArgsConstructor
+@AllArgsConstructor
+@TableName("wk_admin_user_config")
+@ApiModel(value="AdminUserConfig对象", description="用户配置表")
+public class AdminUserConfig implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "setting_id", type = IdType.AUTO)
+    private Integer settingId;
+
+    private Long userId;
+
+    @ApiModelProperty(value = "状态,0:不启用 1 : 启用")
+    private Integer status;
+
+    @ApiModelProperty(value = "设置名称")
+    private String name;
+
+    @ApiModelProperty(value = "值")
+    private String value;
+
+    @ApiModelProperty(value = "描述")
+    private String description;
+
+
+
+}

+ 44 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminUserHisTable.java

@@ -0,0 +1,44 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 授权坐席
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_user_his_table")
+@ApiModel(value="AdminUserHisTable对象", description="授权坐席")
+public class AdminUserHisTable implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "his_table_id", type = IdType.AUTO)
+    private Integer hisTableId;
+
+    private Long userId;
+
+    @ApiModelProperty(value = "0 没有 1 有")
+    private Integer hisTable;
+
+
+    @ApiModelProperty(value = "1.坐席授权 2.设置默认名片 3.关联员工")
+    private Integer type;
+
+
+}

+ 44 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminUserRole.java

@@ -0,0 +1,44 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 用户角色对应关系表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_user_role")
+@ApiModel(value="AdminUserRole对象", description="用户角色对应关系表")
+public class AdminUserRole implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "用户ID")
+    private Long userId;
+
+    @ApiModelProperty(value = "角色ID")
+    private Integer roleId;
+    private Integer label;
+
+    @ApiModelProperty()
+    private Integer tenantId;
+
+}

+ 72 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/AdminVisitingCard.java

@@ -0,0 +1,72 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.*;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * <p>
+ * 名片表
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-06-03
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("wk_admin_visiting_card")
+@ApiModel(value="AdminVisitingCard对象", description="名片表")
+public class AdminVisitingCard implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @TableId(value = "card_id", type = IdType.AUTO)
+    private Integer cardId;
+
+    @ApiModelProperty(value = "名片名称")
+    private String cardName;
+
+    @ApiModelProperty(value = "创建人")
+    @TableField(fill = FieldFill.INSERT)
+    private Long createUserId;
+
+    @ApiModelProperty(value = "创建时间")
+    @TableField(fill = FieldFill.INSERT)
+    private Date createTime;
+
+    @ApiModelProperty(value = "关联员工id")
+    private Long userId;
+
+    @ApiModelProperty(value = "备注")
+    private String remark;
+
+
+    private String openid;
+
+    @ApiModelProperty(value = "微信号")
+    private String wechatNumber;
+
+    @ApiModelProperty(value = "网址")
+    private String url;
+
+    @ApiModelProperty(value = "地址")
+    private String address;
+
+    @ApiModelProperty(value = "简介")
+    private String intro;
+
+    @ApiModelProperty(value = "微信小程序码")
+    private String weixinImg;
+
+    @ApiModelProperty(value = "海报名片")
+    private String officialImg;
+
+
+}

+ 51 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/PO/SysArea.java

@@ -0,0 +1,51 @@
+package com.kakarote.admin.entity.PO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import java.io.Serializable;
+
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+/**
+ * <p>
+ * 区划表
+ * </p>
+ *
+ * @author lzy
+ * @since 2021-03-18
+ */
+@Data
+@EqualsAndHashCode(callSuper = false)
+@Accessors(chain = true)
+@TableName("sys_area")
+@ApiModel(value="SysArea对象", description="区划表")
+public class SysArea implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @ApiModelProperty(value = "主键")
+    @TableId(value = "id", type = IdType.AUTO)
+    private Integer id;
+
+    @ApiModelProperty(value = "父级id")
+    private Integer parentId;
+
+    @ApiModelProperty(value = "名称")
+    private String name;
+
+    @ApiModelProperty(value = "排序")
+    private Integer sort;
+
+    @ApiModelProperty(value = "行政编码")
+    private String code;
+
+    @ApiModelProperty(value = "级别:1、省级 2、市级 3、区县")
+    private Integer level;
+
+
+}

+ 82 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminDeptVO.java

@@ -0,0 +1,82 @@
+package com.kakarote.admin.entity.VO;
+
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.fasterxml.jackson.annotation.JsonFormat;
+import com.fasterxml.jackson.annotation.JsonInclude;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import java.util.Date;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * @author zhangzhiwei
+ */
+@Data
+@ToString
+@ApiModel(value="部门查询对象", description="部门对象")
+public class AdminDeptVO {
+
+    @ApiModelProperty(value = "部门ID")
+    private Integer deptId;
+
+    @ApiModelProperty(value = "部门ID2")
+    private Integer id;
+
+    @ApiModelProperty(value = "上级部门ID,0为最上级")
+    private Integer pid;
+
+    @ApiModelProperty(value = "部门名称")
+    private String name;
+
+    @ApiModelProperty(value = "部门label")
+    private String label;
+
+    @TableField(exist = false)
+    @ApiModelProperty(value = "菜单列表")
+    private Map<String, List<Integer>> rules;
+
+    public String getName() {
+        return name;
+    }
+
+    public void setName(String name) {
+        this.name = name;
+        this.label = name;
+    }
+
+    public String getLabel() {
+        return label;
+    }
+
+    public void setLabel(String label) {
+        this.label = label;
+    }
+
+    public Integer getDeptId() {
+        return deptId;
+    }
+
+    public void setDeptId(Integer deptId) {
+        this.deptId = deptId;
+        this.id = deptId;
+    }
+
+    @ApiModelProperty(value = "下级部门列表")
+    @JsonInclude(JsonInclude.Include.NON_EMPTY)
+    private List<AdminDeptVO> children;
+
+    @ApiModelProperty("状态:0停用,1启用")
+    private String status;
+
+    @ApiModelProperty("有效开始日期'")
+    @JsonFormat(pattern = "yyyy-MM-dd")
+    private Date effectiveStartDate;
+
+    @ApiModelProperty("有效结束日期''")
+    @JsonFormat(pattern = "yyyy-MM-dd")
+    private Date effectiveEndDate;
+}

+ 54 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminInstrumentRoleVO.java

@@ -0,0 +1,54 @@
+package com.kakarote.admin.entity.VO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.experimental.Accessors;
+
+import java.io.Serializable;
+
+/**
+ * <p>
+ * 仪表盘权限表
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-08
+ */
+@Data
+@ApiModel(value="AdminInstrumentRole对象", description="仪表盘权限表")
+public class AdminInstrumentRoleVO {
+
+    @ApiModelProperty(value = "角色id")
+    private Integer roleId;
+
+    @ApiModelProperty(value = "模块id 1、合同金额目标及完成情况 2、数据汇总 4、业绩指标完成率 5、销售漏斗 6、遗忘提醒 7、排行榜")
+    private Integer modelId;
+
+    @ApiModelProperty(value = "仪表盘名称 1、合同金额目标及完成情况 2、数据汇总 4、业绩指标完成率 5、销售漏斗 6、遗忘提醒 7、排行榜")
+    private String modelName;
+
+    @ApiModelProperty
+    private String icon;
+    @ApiModelProperty
+    private String iconColor;
+    @ApiModelProperty
+    private String img;
+
+    @ApiModelProperty(value = "数据权限 1、本人,2、本人及下属,3、本部门,4、本部门及下属部门,5、全部 ")
+    private Integer dataType;
+
+    @ApiModelProperty(value = "列 1左侧 2右侧")
+    private Integer list;
+
+    @ApiModelProperty(value = "排序")
+    private Integer sort;
+
+    @ApiModelProperty(value = "是否隐藏 0显示 1隐藏")
+    private Integer isHidden;
+
+}

+ 39 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminMenuVO.java

@@ -0,0 +1,39 @@
+package com.kakarote.admin.entity.VO;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import java.util.List;
+
+/**
+ * @author zhangzhiwei
+ * 菜单相关VO
+ */
+@Data
+@ToString
+@ApiModel("角色列表返回")
+public class AdminMenuVO {
+    @ApiModelProperty(value = "菜单ID")
+    @TableId(value = "menu_id", type = IdType.AUTO)
+    private Integer menuId;
+
+    @ApiModelProperty(value = "上级菜单ID")
+    private Integer parentId;
+
+    @ApiModelProperty(value = "菜单名称")
+    private String menuName;
+
+    @ApiModelProperty(value = "权限标识")
+    private String realm;
+
+    @ApiModelProperty(value = "菜单类型  1目录 2 菜单 3 按钮 4特殊")
+    private Integer menuType;
+
+    @ApiModelProperty(value = "子菜单")
+    private List<AdminMenuVO> childMenu;
+
+}

+ 38 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminMessageVO.java

@@ -0,0 +1,38 @@
+package com.kakarote.admin.entity.VO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+@Data
+@ApiModel("消息数量VO")
+@AllArgsConstructor
+@NoArgsConstructor
+public class AdminMessageVO {
+
+    @ApiModelProperty("全部数量")
+    private Integer allCount;
+
+    @ApiModelProperty("公告数量")
+    private Integer announceCount;
+
+    @ApiModelProperty("审批数量")
+    private Integer examineCount;
+
+    @ApiModelProperty("任务数量")
+    private Integer taskCount;
+
+    @ApiModelProperty("日志数量")
+    private Integer logCount;
+
+    @ApiModelProperty("CRM数量")
+    private Integer crmCount;
+
+    @ApiModelProperty("日程数量")
+    private Integer eventCount;
+
+    @ApiModelProperty("知识库通知数量")
+    private Integer knowledgeCount;
+}

+ 28 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminRoleVO.java

@@ -0,0 +1,28 @@
+package com.kakarote.admin.entity.VO;
+
+import com.kakarote.admin.entity.PO.AdminRole;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import java.util.List;
+
+/**
+ * @author zhangzhiwei
+ * 查询角色功能
+ */
+@Data
+@ToString
+@ApiModel("查询角色功能")
+public class AdminRoleVO {
+
+    @ApiModelProperty("pid")
+    private Integer pid;
+
+    @ApiModelProperty("名称")
+    private String name;
+
+    @ApiModelProperty("角色列表")
+    private List<AdminRole> list;
+}

+ 107 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/AdminUserVO.java

@@ -0,0 +1,107 @@
+package com.kakarote.admin.entity.VO;
+
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+import java.util.Date;
+import java.util.List;
+
+/**
+ * @author zhangzhiwei
+ * 查询列表
+ */
+@Data
+@ToString
+@ApiModel("用户列表查询返回")
+public class AdminUserVO {
+
+    @ApiModelProperty("姓名")
+    private String realname;
+
+    @ApiModelProperty("用户名")
+    private String username;
+
+    @ApiModelProperty(value = "用户ID", required = true)
+    private Long userId;
+
+    @ApiModelProperty(value = "性别,0 未选择 1、男 2、女", required = true, allowableValues = "0,1,2")
+    private Integer sex;
+
+    @ApiModelProperty(value = "手机号")
+    private String mobile;
+
+    @ApiModelProperty(value = "密码")
+    private String password;
+
+    @ApiModelProperty(value = "邮箱")
+    private String email;
+
+    @ApiModelProperty(value = "部门ID")
+    private Integer deptId;
+
+    @ApiModelProperty(value = "部门名称")
+    private String deptName;
+
+    @ApiModelProperty(value = "状态,0禁用,1正常,2未激活")
+    private Integer status;
+
+    @ApiModelProperty(value = "创建时间")
+    private Date createTime;
+
+    @ApiModelProperty(value = "岗位")
+    private String post;
+
+    @ApiModelProperty(value = "上级ID")
+    private Long parentId;
+
+    @ApiModelProperty(value = "上级名称")
+    private String parentName;
+
+    @ApiModelProperty(value = "角色ID")
+    private String roleId;
+
+    @ApiModelProperty(value = "角色ID")
+    private String roleIds;
+
+    @ApiModelProperty(value = "角色ID")
+    private List<Integer> roleTypeList;
+
+    @ApiModelProperty(value = "角色名称")
+    private String roleName;
+
+    @ApiModelProperty(value = "用户头像")
+    private String img;
+
+    private Boolean isAdmin;
+
+    private Integer isReadNotice;
+
+    private Integer emailId;
+
+    /**
+     * 数据权限 父子JSON
+     */
+    private JSONObject oauth;
+
+    /**
+     * 所有父子路由JSON
+     */
+    private JSONObject routers;
+
+    private Integer tenantId;
+
+    private Integer projectId;
+
+    private Integer deptParentId;
+
+    /**
+     * 小程序用户openId
+     */
+    private String wxappOpenId;
+
+    private Integer workTypeId;
+}

+ 31 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/CloudConfigVO.java

@@ -0,0 +1,31 @@
+package com.kakarote.admin.entity.VO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+/**
+ * @author zhangzhiwei
+ * 云平台账号配置
+ */
+@ToString
+@Data
+@ApiModel("云平台账号配置")
+public class CloudConfigVO {
+
+    @ApiModelProperty("开始时间")
+    private String startTime;
+
+    @ApiModelProperty("结束时间")
+    private String endTime;
+
+    @ApiModelProperty("可用人数")
+    private Integer allNum;
+
+    @ApiModelProperty("创建时间")
+    private String createTime;
+
+    @ApiModelProperty("已使用人数")
+    private Integer usingNum;
+}

+ 36 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/HrmSimpleUserVO.java

@@ -0,0 +1,36 @@
+package com.kakarote.admin.entity.VO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.io.Serializable;
+
+/**
+ * @author zhangzhiwei
+ * 简单的用户对象
+ */
+@Data
+@ApiModel("用户对象")
+public class HrmSimpleUserVO implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @ApiModelProperty("用户ID")
+    private Long userId;
+
+    @ApiModelProperty("头像")
+    private String img;
+
+    @ApiModelProperty("昵称")
+    private String realname;
+
+    @ApiModelProperty("岗位")
+    private String post;
+
+    @ApiModelProperty("手机号")
+    private String mobile;
+
+    @ApiModelProperty("性别")
+    private Integer sex;
+}

+ 31 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/ModuleSettingVO.java

@@ -0,0 +1,31 @@
+package com.kakarote.admin.entity.VO;
+
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+import lombok.ToString;
+
+/**
+ * @author zhangzhiwei
+ * 模块设置VO
+ */
+@ToString
+@Data
+@ApiModel("应用管理设置")
+public class ModuleSettingVO {
+
+    @ApiModelProperty(value = "设置ID", required = true)
+    private Integer settingId;
+
+    @ApiModelProperty(value = "模块", required = true)
+    private String module;
+
+    @ApiModelProperty(value = "状态 1:启用 0:停用", required = true,allowableValues = "0,1")
+    private Integer status;
+
+    @ApiModelProperty(value = "类型 1:普通应用 2:增值应用 3:未发布应用", required = true,allowableValues = "1,2,3")
+    private String type;
+
+    @ApiModelProperty(value = "名称", required = true)
+    private String name;
+}

+ 67 - 0
admin/admin/src/main/java/com/kakarote/admin/entity/VO/UserBookVO.java

@@ -0,0 +1,67 @@
+package com.kakarote.admin.entity.VO;
+
+import io.swagger.annotations.ApiModelProperty;
+import lombok.Data;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * @author zhangzhiwei
+ */
+@Data
+public class UserBookVO implements Serializable {
+
+    private static final long serialVersionUID=1L;
+
+    @ApiModelProperty("姓名")
+    private String realname;
+
+    @ApiModelProperty("用户名")
+    private String username;
+
+    @ApiModelProperty(value = "用户ID", required = true)
+    private Long userId;
+
+    @ApiModelProperty(value = "性别,0 未选择 1、男 2、女", required = true, allowableValues = "0,1,2")
+    private Integer sex;
+
+    @ApiModelProperty(value = "手机号")
+    private String mobile;
+
+    @ApiModelProperty(value = "邮箱")
+    private String email;
+
+    @ApiModelProperty(value = "部门ID")
+    private Integer deptId;
+
+    @ApiModelProperty(value = "部门名称")
+    private String deptName;
+
+    @ApiModelProperty(value = "关注状态,0未关注,1已关注")
+    private Integer status;
+
+    @ApiModelProperty(value = "状态,0禁用,1正常,2未激活")
+    private Integer userStatus;
+
+    @ApiModelProperty(value = "创建时间")
+    private Date createTime;
+
+    @ApiModelProperty(value = "岗位")
+    private String post;
+
+    @ApiModelProperty(value = "上级ID")
+    private Long parentId;
+
+    @ApiModelProperty(value = "上级名称")
+    private String parentName;
+
+    @ApiModelProperty(value = "角色ID")
+    private String roleId;
+
+    @ApiModelProperty(value = "角色名称")
+    private String roleName;
+
+    @ApiModelProperty("首字母")
+    private String initial;
+}

+ 16 - 0
admin/admin/src/main/java/com/kakarote/admin/mapper/AdminAttentionMapper.java

@@ -0,0 +1,16 @@
+package com.kakarote.admin.mapper;
+
+import com.kakarote.admin.entity.PO.AdminAttention;
+import com.kakarote.core.servlet.BaseMapper;
+
+/**
+ * <p>
+ * 通讯录用户关注表 Mapper 接口
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+public interface AdminAttentionMapper extends BaseMapper<AdminAttention> {
+
+}

+ 21 - 0
admin/admin/src/main/java/com/kakarote/admin/mapper/AdminConfigMapper.java

@@ -0,0 +1,21 @@
+package com.kakarote.admin.mapper;
+
+import com.baomidou.mybatisplus.annotation.SqlParser;
+import com.kakarote.admin.entity.PO.AdminConfig;
+import com.kakarote.core.servlet.BaseMapper;
+import org.apache.ibatis.annotations.Param;
+
+/**
+ * <p>
+ * 客户规则 Mapper 接口
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+
+public interface AdminConfigMapper extends BaseMapper<AdminConfig> {
+
+//    @SqlParser(filter = true)
+    void updateAdminConfigNoTenantId(@Param("data") AdminConfig adminConfig);
+}

+ 24 - 0
admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDeptConfigMapper.java

@@ -0,0 +1,24 @@
+package com.kakarote.admin.mapper;
+
+import com.kakarote.admin.entity.BO.AdminDeptConfigBO;
+import com.kakarote.admin.entity.PO.AdminDeptConfig;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.servlet.BaseMapper;
+import org.apache.ibatis.annotations.Param;
+
+import java.util.List;
+
+/**
+ * <p>
+ *  Mapper 接口
+ * </p>
+ *
+ * @author author
+ * @since 2020-12-16
+ */
+public interface AdminDeptConfigMapper extends BaseMapper<AdminDeptConfig> {
+
+    BasePage<AdminDeptConfig> queryList(BasePage<AdminDeptConfig> page, @Param("data") AdminDeptConfigBO adminDeptConfigBO);
+
+    List<AdminDeptConfig> checkList(AdminDeptConfig adminDeptConfig);
+}

+ 20 - 0
admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDeptMapper.java

@@ -0,0 +1,20 @@
+package com.kakarote.admin.mapper;
+
+import com.kakarote.admin.entity.BO.DeptVO;
+import com.kakarote.admin.entity.PO.AdminDept;
+import com.kakarote.core.servlet.BaseMapper;
+
+import java.util.List;
+
+/**
+ * <p>
+ * 部门表 Mapper 接口
+ * </p>
+ *
+ * @author zhangzhiwei
+ * @since 2020-04-27
+ */
+public interface AdminDeptMapper extends BaseMapper<AdminDept> {
+
+    List<DeptVO> queryDeptUserList();
+}

+ 13 - 0
admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDeptMenuMapper.java

@@ -0,0 +1,13 @@
+package com.kakarote.admin.mapper;
+
+import com.kakarote.admin.entity.PO.AdminDeptMenu;
+import com.kakarote.core.servlet.BaseMapper;
+import org.apache.ibatis.annotations.Param;
+
+import java.util.List;
+
+public interface AdminDeptMenuMapper extends BaseMapper<AdminDeptMenu> {
+    public List<Integer> getDeptMenu(@Param("parentId") Integer parentId, @Param("deptId") Integer deptId);
+    public List<Integer> getDeptMenu2(@Param("parentId") Integer parentId, @Param("deptId") Integer deptId);
+
+}

+ 97 - 0
admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDictDataMapper.java

@@ -0,0 +1,97 @@
+package com.kakarote.admin.mapper;
+
+import java.util.List;
+
+import com.kakarote.admin.entity.PO.AdminDictData;
+import com.kakarote.core.servlet.BaseMapper;
+import org.apache.ibatis.annotations.Param;
+
+/**
+ * 字典表 数据层
+ * 
+ * @author ruoyi
+ */
+public interface AdminDictDataMapper extends BaseMapper<AdminDictData>
+{
+    /**
+     * 根据条件分页查询字典数据
+     * 
+     * @param dictData 字典数据信息
+     * @return 字典数据集合信息
+     */
+    List<AdminDictData> selectDictDataList(AdminDictData dictData);
+
+    /**
+     * 根据字典类型查询字典数据
+     * 
+     * @param dictType 字典类型
+     * @return 字典数据集合信息
+     */
+    List<AdminDictData> selectDictDataByType(@Param("dictType") String dictType, @Param("tenantId") Long tenantId);
+
+    /**
+     * 根据字典类型和字典键值查询字典数据信息
+     * 
+     * @param dictType 字典类型
+     * @param dictValue 字典键值
+     * @return 字典标签
+     */
+    String selectDictLabel(@Param("dictType") String dictType, @Param("dictValue") String dictValue);
+
+    /**
+     * 根据字典数据ID查询信息
+     * 
+     * @param dictCode 字典数据ID
+     * @return 字典数据
+     */
+    AdminDictData selectDictDataById(Long dictCode);
+
+    /**
+     * 查询字典数据
+     * 
+     * @param dictType 字典类型
+     * @return 字典数据
+     */
+    int countDictDataByType(String dictType);
+
+    /**
+     * 通过字典ID删除字典数据信息
+     * 
+     * @param dictCode 字典数据ID
+     * @return 结果
+     */
+    int deleteDictDataById(Long dictCode);
+
+    /**
+     * 批量删除字典数据信息
+     * 
+     * @param dictCodes 需要删除的字典数据ID
+     * @return 结果
+     */
+    int deleteDictDataByIds(Long[] dictCodes);
+
+    /**
+     * 新增字典数据信息
+     * 
+     * @param dictData 字典数据信息
+     * @return 结果
+     */
+    int insertDictData(AdminDictData dictData);
+
+    /**
+     * 修改字典数据信息
+     * 
+     * @param dictData 字典数据信息
+     * @return 结果
+     */
+    int updateDictData(AdminDictData dictData);
+
+    /**
+     * 同步修改字典类型
+     * 
+     * @param oldDictType 旧字典类型
+     * @param newDictType 新旧字典类型
+     * @return 结果
+     */
+    int updateDictDataType(@Param("oldDictType") String oldDictType, @Param("newDictType") String newDictType);
+}

+ 29 - 0
admin/admin/src/main/java/com/kakarote/admin/mapper/AdminDictMatchMapper.java

@@ -0,0 +1,29 @@
+package com.kakarote.admin.mapper;
+
+import com.kakarote.admin.entity.BO.AdminDictMathBO;
+import com.kakarote.admin.entity.PO.AdminDictMatch;
+import com.kakarote.core.entity.BasePage;
+import com.kakarote.core.servlet.BaseMapper;
+import org.apache.ibatis.annotations.Param;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * <p>
+ *  Mapper 接口
+ * </p>
+ *
+ * @author lzy
+ * @since 2021-11-30
+ */
+public interface AdminDictMatchMapper extends BaseMapper<AdminDictMatch> {
+
+    BasePage<AdminDictMatch> selectByPage(BasePage<Object> parse, @Param("data") AdminDictMathBO adminDictMathBO);
+
+    List<Map<String, Object>> selectSuggestList(@Param("data") Map<String, Object> params);
+
+    Map selectDictMatchByType(@Param("matchDict") String matchDict, @Param("value") String value, @Param("tenantId") Integer tenantId);
+
+    List<AdminDictMatch> selectAll();
+}

Algúns arquivos non se mostraron porque demasiados arquivos cambiaron neste cambio