From ce3e802edcac28d4e8fba0d3b77e111197f40421 Mon Sep 17 00:00:00 2001 From: mula Date: Wed, 9 Apr 2025 08:45:38 +0000 Subject: [PATCH] 0.1.0 --- .vscode/extensions.json | 7 + configs/config.yaml | 16 + db-init.sql | 172 ++++++++++ entrypoint.sh | 1 + hello.sh | 5 + pom.xml | 100 ++++++ project.md | 312 ++++++++++++++++++ .../com/unissense/sip/UnisSipApplication.java | 14 + .../unissense/sip/config/SecurityConfig.java | 13 + .../sip/controller/AuthController.java | 48 +++ .../sip/controller/SysDeptController.java | 32 ++ .../sip/controller/SysDictDataController.java | 80 +++++ .../sip/controller/SysDictTypeController.java | 71 ++++ .../sip/controller/SysMenuController.java | 40 +++ .../sip/controller/SysRoleController.java | 26 ++ .../sip/controller/SysUserController.java | 32 ++ .../sip/controller/SysUserRoleController.java | 36 ++ .../com/unissense/sip/dto/LoginRequest.java | 10 + .../com/unissense/sip/dto/LoginResponse.java | 15 + .../com/unissense/sip/entity/SysDept.java | 46 +++ .../com/unissense/sip/entity/SysDictData.java | 40 +++ .../com/unissense/sip/entity/SysDictType.java | 32 ++ .../com/unissense/sip/entity/SysMenu.java | 50 +++ .../com/unissense/sip/entity/SysRole.java | 40 +++ .../com/unissense/sip/entity/SysRoleMenu.java | 18 + .../com/unissense/sip/entity/SysUser.java | 31 ++ .../com/unissense/sip/entity/SysUserRole.java | 18 + .../unissense/sip/mapper/SysDeptMapper.java | 9 + .../sip/mapper/SysDictDataMapper.java | 9 + .../sip/mapper/SysDictTypeMapper.java | 9 + .../unissense/sip/mapper/SysMenuMapper.java | 9 + .../unissense/sip/mapper/SysRoleMapper.java | 9 + .../sip/mapper/SysRoleMenuMapper.java | 9 + .../unissense/sip/mapper/SysUserMapper.java | 9 + .../sip/mapper/SysUserRoleMapper.java | 9 + .../unissense/sip/service/SysDeptService.java | 20 ++ .../sip/service/SysDictDataService.java | 29 ++ .../sip/service/SysDictTypeService.java | 18 + .../unissense/sip/service/SysMenuService.java | 29 ++ .../sip/service/SysRoleMenuService.java | 30 ++ .../unissense/sip/service/SysRoleService.java | 14 + .../sip/service/SysUserRoleService.java | 45 +++ .../unissense/sip/service/SysUserService.java | 46 +++ .../sip/service/impl/SysDeptServiceImpl.java | 27 ++ .../service/impl/SysDictDataServiceImpl.java | 34 ++ .../service/impl/SysDictTypeServiceImpl.java | 22 ++ .../sip/service/impl/SysMenuServiceImpl.java | 36 ++ .../service/impl/SysRoleMenuServiceImpl.java | 51 +++ .../sip/service/impl/SysRoleServiceImpl.java | 20 ++ .../service/impl/SysUserRoleServiceImpl.java | 97 ++++++ .../sip/service/impl/SysUserServiceImpl.java | 94 ++++++ .../com/unissense/sip/utils/CaptchaUtils.java | 43 +++ .../com/unissense/sip/utils/JwtUtils.java | 49 +++ src/main/resources/application.yml | 26 ++ target/classes/application.yml | 26 ++ .../compile/default-compile/inputFiles.lst | 45 +++ template/index.html | 228 +++++++++++++ template/js/auth.js | 94 ++++++ template/login.html | 136 ++++++++ 59 files changed, 2636 insertions(+) create mode 100755 .vscode/extensions.json create mode 100644 configs/config.yaml create mode 100644 db-init.sql create mode 100755 entrypoint.sh create mode 100755 hello.sh create mode 100644 pom.xml create mode 100644 project.md create mode 100644 src/main/java/com/unissense/sip/UnisSipApplication.java create mode 100644 src/main/java/com/unissense/sip/config/SecurityConfig.java create mode 100644 src/main/java/com/unissense/sip/controller/AuthController.java create mode 100644 src/main/java/com/unissense/sip/controller/SysDeptController.java create mode 100644 src/main/java/com/unissense/sip/controller/SysDictDataController.java create mode 100644 src/main/java/com/unissense/sip/controller/SysDictTypeController.java create mode 100644 src/main/java/com/unissense/sip/controller/SysMenuController.java create mode 100644 src/main/java/com/unissense/sip/controller/SysRoleController.java create mode 100644 src/main/java/com/unissense/sip/controller/SysUserController.java create mode 100644 src/main/java/com/unissense/sip/controller/SysUserRoleController.java create mode 100644 src/main/java/com/unissense/sip/dto/LoginRequest.java create mode 100644 src/main/java/com/unissense/sip/dto/LoginResponse.java create mode 100644 src/main/java/com/unissense/sip/entity/SysDept.java create mode 100644 src/main/java/com/unissense/sip/entity/SysDictData.java create mode 100644 src/main/java/com/unissense/sip/entity/SysDictType.java create mode 100644 src/main/java/com/unissense/sip/entity/SysMenu.java create mode 100644 src/main/java/com/unissense/sip/entity/SysRole.java create mode 100644 src/main/java/com/unissense/sip/entity/SysRoleMenu.java create mode 100644 src/main/java/com/unissense/sip/entity/SysUser.java create mode 100644 src/main/java/com/unissense/sip/entity/SysUserRole.java create mode 100644 src/main/java/com/unissense/sip/mapper/SysDeptMapper.java create mode 100644 src/main/java/com/unissense/sip/mapper/SysDictDataMapper.java create mode 100644 src/main/java/com/unissense/sip/mapper/SysDictTypeMapper.java create mode 100644 src/main/java/com/unissense/sip/mapper/SysMenuMapper.java create mode 100644 src/main/java/com/unissense/sip/mapper/SysRoleMapper.java create mode 100644 src/main/java/com/unissense/sip/mapper/SysRoleMenuMapper.java create mode 100644 src/main/java/com/unissense/sip/mapper/SysUserMapper.java create mode 100644 src/main/java/com/unissense/sip/mapper/SysUserRoleMapper.java create mode 100644 src/main/java/com/unissense/sip/service/SysDeptService.java create mode 100644 src/main/java/com/unissense/sip/service/SysDictDataService.java create mode 100644 src/main/java/com/unissense/sip/service/SysDictTypeService.java create mode 100644 src/main/java/com/unissense/sip/service/SysMenuService.java create mode 100644 src/main/java/com/unissense/sip/service/SysRoleMenuService.java create mode 100644 src/main/java/com/unissense/sip/service/SysRoleService.java create mode 100644 src/main/java/com/unissense/sip/service/SysUserRoleService.java create mode 100644 src/main/java/com/unissense/sip/service/SysUserService.java create mode 100644 src/main/java/com/unissense/sip/service/impl/SysDeptServiceImpl.java create mode 100644 src/main/java/com/unissense/sip/service/impl/SysDictDataServiceImpl.java create mode 100644 src/main/java/com/unissense/sip/service/impl/SysDictTypeServiceImpl.java create mode 100644 src/main/java/com/unissense/sip/service/impl/SysMenuServiceImpl.java create mode 100644 src/main/java/com/unissense/sip/service/impl/SysRoleMenuServiceImpl.java create mode 100644 src/main/java/com/unissense/sip/service/impl/SysRoleServiceImpl.java create mode 100644 src/main/java/com/unissense/sip/service/impl/SysUserRoleServiceImpl.java create mode 100644 src/main/java/com/unissense/sip/service/impl/SysUserServiceImpl.java create mode 100644 src/main/java/com/unissense/sip/utils/CaptchaUtils.java create mode 100644 src/main/java/com/unissense/sip/utils/JwtUtils.java create mode 100644 src/main/resources/application.yml create mode 100644 target/classes/application.yml create mode 100644 target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst create mode 100644 template/index.html create mode 100644 template/js/auth.js create mode 100644 template/login.html diff --git a/.vscode/extensions.json b/.vscode/extensions.json new file mode 100755 index 0000000..87ebf2a --- /dev/null +++ b/.vscode/extensions.json @@ -0,0 +1,7 @@ +{ + "recommendations": [ + "pomdtr.excalidraw-editor", + "editorconfig.editorconfig", + "lokalise.i18n-ally" + ] +} \ No newline at end of file diff --git a/configs/config.yaml b/configs/config.yaml new file mode 100644 index 0000000..1034dfd --- /dev/null +++ b/configs/config.yaml @@ -0,0 +1,16 @@ +server: + addr: ":8080" + mode: "debug" + +database: + driver: "mysql" + host: "unis-sip-mysql.ns-dv9ov434.svc" + port: 3306 + username: "root" + password: "5tzz94jd" + dbname: "unis_sip" + charset: "utf8mb4" + +jwt: + secret: "unis-sip-secret-key" + expiretime: 86400 # 24小时 \ No newline at end of file diff --git a/db-init.sql b/db-init.sql new file mode 100644 index 0000000..1b22a67 --- /dev/null +++ b/db-init.sql @@ -0,0 +1,172 @@ +-- 创建系统用户表 +CREATE TABLE sys_user ( + user_id BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '主键,用户ID', + dept_id BIGINT(20) DEFAULT NULL COMMENT '部门ID', + login_name VARCHAR(30) NOT NULL COMMENT '登录账号', + user_name VARCHAR(30) DEFAULT '' COMMENT '用户昵称', + email VARCHAR(50) DEFAULT '' COMMENT '用户邮箱', + phonenumber VARCHAR(11) DEFAULT '' COMMENT '手机号码', + sex CHAR(1) DEFAULT '0' COMMENT '用户性别(0男 1女 2未知)', + avatar VARCHAR(100) DEFAULT '' COMMENT '头像路径', + password VARCHAR(50) DEFAULT '' COMMENT '密码', + salt VARCHAR(20) DEFAULT '' COMMENT '盐加密', + status CHAR(1) DEFAULT '0' COMMENT '帐号状态(0正常 1停用)', + login_ip VARCHAR(128) DEFAULT '' COMMENT '最后登录IP', + login_date DATETIME DEFAULT NULL COMMENT '最后登录时间', + create_at DATETIME NOT NULL COMMENT '创建时间', + update_at DATETIME NOT NULL COMMENT '更新时间', + delete_at DATETIME DEFAULT NULL COMMENT '删除时间,软删除', + PRIMARY KEY (user_id) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='系统用户表'; + +-- 创建系统角色表 +CREATE TABLE sys_role ( + role_id BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '主键,角色ID', + role_name VARCHAR(30) NOT NULL COMMENT '角色名称', + role_key VARCHAR(100) NOT NULL COMMENT '角色权限字符串', + data_scope CHAR(1) DEFAULT '1' COMMENT '数据范围(1:全部数据权限 2:自定数据权限 3:本部门数据权限 4:本部门及以下数据权限)', + status CHAR(1) NOT NULL COMMENT '角色状态(0正常 1停用)', + create_time DATETIME DEFAULT NULL COMMENT '创建时间', + update_time DATETIME DEFAULT NULL COMMENT '更新时间', + delete_at DATETIME DEFAULT NULL COMMENT '删除时间', + PRIMARY KEY (role_id) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='系统角色表'; + +-- 初始化角色数据 +INSERT INTO sys_role (role_id, role_name, role_key, data_scope, status, create_time) VALUES +(1, '超级管理员', 'admin', '1', '0', NOW()), +(2, '普通角色', 'common', '2', '0', NOW()); + +-- 初始化用户数据 +INSERT INTO sys_user (user_id, login_name, user_name, password, salt, status, create_at, update_at) VALUES +(1, 'admin', 'admin', '123456', 'salt', '0', NOW(), NOW()), +(2, 'mula', 'mula', '123456', 'salt', '0', NOW(), NOW()), +(3, 'jsm', 'jsm', '123456', 'salt', '0', NOW(), NOW()); + +-- 创建用户角色关系表 +CREATE TABLE sys_user_role ( + id BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '主键ID', + user_id BIGINT(20) NOT NULL COMMENT '用户ID', + role_id BIGINT(20) NOT NULL COMMENT '角色ID', + PRIMARY KEY (id) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='用户角色关系表'; + +-- 初始化用户角色关联关系 +INSERT INTO sys_user_role (user_id, role_id) VALUES +(1, 1), -- admin用户关联超级管理员角色 +(2, 2), -- mula用户关联普通角色 +(3, 2); -- jsm用户关联普通角色 + +-- 创建部门表 +CREATE TABLE sys_dept ( + dept_id BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '部门id', + parent_id BIGINT(20) DEFAULT 0 COMMENT '父部门id', + dept_name VARCHAR(30) DEFAULT '' COMMENT '部门名称', + order_num INT(4) DEFAULT 0 COMMENT '显示顺序', + leader VARCHAR(20) DEFAULT NULL COMMENT '负责人', + phone VARCHAR(11) DEFAULT NULL COMMENT '联系电话', + email VARCHAR(50) DEFAULT NULL COMMENT '邮箱', + status CHAR(1) DEFAULT '0' COMMENT '部门状态(0正常 1停用)', + create_time DATETIME DEFAULT NULL COMMENT '创建时间', + update_time DATETIME DEFAULT NULL COMMENT '更新时间', + delete_at DATETIME DEFAULT NULL COMMENT '删除时间', + PRIMARY KEY (dept_id) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='部门表'; + +-- 创建菜单权限表 +CREATE TABLE sys_menu ( + menu_id BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '菜单ID', + menu_name VARCHAR(50) NOT NULL COMMENT '菜单名称', + parent_id BIGINT(20) DEFAULT 0 COMMENT '父菜单ID', + order_num INT(4) DEFAULT 0 COMMENT '显示顺序', + path VARCHAR(200) DEFAULT '' COMMENT '路由地址', + component VARCHAR(255) DEFAULT NULL COMMENT '组件路径', + is_frame INT(1) DEFAULT 1 COMMENT '是否为外链(0是 1否)', + menu_type CHAR(1) DEFAULT '' COMMENT '菜单类型(M目录 C菜单 F按钮)', + visible CHAR(1) DEFAULT '0' COMMENT '菜单状态(0显示 1隐藏)', + perms VARCHAR(100) DEFAULT NULL COMMENT '权限标识', + icon VARCHAR(100) DEFAULT '#' COMMENT '菜单图标', + status CHAR(1) DEFAULT '0' COMMENT '菜单状态(0正常 1停用)', + create_time DATETIME DEFAULT NULL COMMENT '创建时间', + update_time DATETIME DEFAULT NULL COMMENT '更新时间', + delete_at DATETIME DEFAULT NULL COMMENT '删除时间', + PRIMARY KEY (menu_id) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='菜单权限表'; + +-- 创建角色菜单关系表 +CREATE TABLE sys_role_menu ( + id BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '主键ID', + role_id BIGINT(20) NOT NULL COMMENT '角色ID', + menu_id BIGINT(20) NOT NULL COMMENT '菜单ID', + PRIMARY KEY(id) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='角色和菜单关系表'; + +-- 初始化部门数据 +INSERT INTO sys_dept (dept_id, parent_id, dept_name, order_num, create_time) VALUES +(1, 0, '紫光汇智', 1, NOW()), +(2, 1, 'VDI事业部门', 1, NOW()), +(3, 1, '营销中心', 2, NOW()), +(4, 1, '产品中心', 3, NOW()); + +-- 初始化菜单数据 +INSERT INTO sys_menu (menu_id, menu_name, parent_id, order_num, path, component, menu_type, visible, perms, icon, create_time) VALUES +-- 一级菜单 +(1, '系统管理', 0, 1, 'system', NULL, 'M', '0', '', 'system', NOW()), +(2, '项目管理', 0, 2, 'project', NULL, 'M', '0', '', 'project', NOW()), +-- 系统管理子菜单 +(100, '用户管理', 1, 1, 'user', 'system/user/index', 'C', '0', 'system:user:list', 'user', NOW()), +(101, '角色管理', 1, 2, 'role', 'system/role/index', 'C', '0', 'system:role:list', 'role', NOW()), +(102, '菜单管理', 1, 3, 'menu', 'system/menu/index', 'C', '0', 'system:menu:list', 'menu', NOW()), +-- 项目管理子菜单 +(200, '项目信息管理', 2, 1, 'info', 'project/info/index', 'C', '0', 'project:info:list', 'info', NOW()), +(201, '合同信息管理', 2, 2, 'contract', 'project/contract/index', 'C', '0', 'project:contract:list', 'contract', NOW()); + +-- 初始化角色菜单关系 +INSERT INTO sys_role_menu (role_id, menu_id) VALUES +-- admin角色系统管理权限 +(1, 1), (1, 100), (1, 101), (1, 102), +-- common角色项目管理权限 +(2, 2), (2, 200), (2, 201); + +-- 创建字典类型表 +CREATE TABLE sys_dict_type ( + dict_id BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '字典主键', + dict_name VARCHAR(100) DEFAULT '' COMMENT '字典名称', + dict_type VARCHAR(100) DEFAULT '' COMMENT '字典类型', + status CHAR(1) DEFAULT '0' COMMENT '状态(0正常 1停用)', + create_time DATETIME DEFAULT NULL COMMENT '创建时间', + update_time DATETIME DEFAULT NULL COMMENT '更新时间', + delete_at DATETIME DEFAULT NULL COMMENT '删除时间', + PRIMARY KEY (dict_id), + UNIQUE KEY dict_type (dict_type) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='字典类型表'; + +-- 创建字典数据表 +CREATE TABLE sys_dict_data ( + dict_code BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '字典编码', + dict_sort INT(4) DEFAULT 0 COMMENT '字典排序', + dict_label VARCHAR(100) DEFAULT '' COMMENT '字典标签', + dict_value VARCHAR(100) DEFAULT '' COMMENT '字典键值', + dict_type VARCHAR(100) DEFAULT '' COMMENT '字典类型', + status CHAR(1) DEFAULT '0' COMMENT '状态(0正常 1停用)', + create_time DATETIME DEFAULT NULL COMMENT '创建时间', + update_time DATETIME DEFAULT NULL COMMENT '更新时间', + delete_at DATETIME DEFAULT NULL COMMENT '删除时间', + PRIMARY KEY (dict_code) +) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='字典数据表'; + +-- 初始化字典类型数据 +INSERT INTO sys_dict_type (dict_id, dict_name, dict_type, status, create_time) VALUES +(1, '用户性别', 'sys_user_sex', '0', NOW()), +(2, '合同类别', 'contract_type', '0', NOW()); + +-- 初始化字典数据 +INSERT INTO sys_dict_data (dict_sort, dict_label, dict_value, dict_type, status, create_time) VALUES +-- 用户性别数据 +(1, '男', '0', 'sys_user_sex', '0', NOW()), +(2, '女', '1', 'sys_user_sex', '0', NOW()), +(3, '未知', '2', 'sys_user_sex', '0', NOW()), +-- 合同类别数据 +(1, '直签', '1', 'contract_type', '0', NOW()), +(2, '代理商签', '2', 'contract_type', '0', NOW()); + diff --git a/entrypoint.sh b/entrypoint.sh new file mode 100755 index 0000000..5fddb40 --- /dev/null +++ b/entrypoint.sh @@ -0,0 +1 @@ +./hello.sh \ No newline at end of file diff --git a/hello.sh b/hello.sh new file mode 100755 index 0000000..2b2fb28 --- /dev/null +++ b/hello.sh @@ -0,0 +1,5 @@ +#!/bin/bash + +while :; do + { echo -ne "HTTP/1.1 200 OK\r\nContent-Length: $(echo -n "Hello, World!")\r\n\r\nHello, World!"; } | nc -l -p 8080 -q 1 +done diff --git a/pom.xml b/pom.xml new file mode 100644 index 0000000..68780d6 --- /dev/null +++ b/pom.xml @@ -0,0 +1,100 @@ + + + 4.0.0 + + + org.springframework.boot + spring-boot-starter-parent + 2.7.0 + + + + com.unissense.sip + unis-sip + 1.0.0 + unis-sip + Unis Service Information Platform + + + 11 + 3.5.2 + 8.0.31 + 0.9.1 + 1.18.24 + + + + + + org.springframework.boot + spring-boot-starter-web + + + + + com.baomidou + mybatis-plus-boot-starter + ${mybatis-plus.version} + + + + + mysql + mysql-connector-java + ${mysql.version} + + + + + io.jsonwebtoken + jjwt + ${jwt.version} + + + + + org.projectlombok + lombok + ${lombok.version} + true + + + + + org.springframework.boot + spring-boot-starter-test + test + + + + + org.springframework.boot + spring-boot-starter-security + + + + + org.springframework.boot + spring-boot-starter-data-redis + + + + + + + org.springframework.boot + spring-boot-maven-plugin + + + + org.projectlombok + lombok + + + + + + + \ No newline at end of file diff --git a/project.md b/project.md new file mode 100644 index 0000000..89dd51b --- /dev/null +++ b/project.md @@ -0,0 +1,312 @@ +> SIP是售后服务平台(Service Information Platform) + +# 系统架构 +后端采用Spring Boot+JWT+Mybatis-Plus+Redis+Mysql +前端采用vue3 + element-plus + ts + + +# 数据库设计 +采用mysql数据库,采用ORM框架进行数据库操作。数据库版本为8.0.31。 +测试的数据库连接信息如下:mysql://root:5tzz94jd@unis-sip-mysql.ns-dv9ov434.svc:3306/unis_sip?charset=utf8mb4&parseTime=True&loc=Local + +## 系统表 + +### 系统用户表(sys_user) +主要用于管理系统用户账号信息,包含用户的基本信息、登录信息和状态等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| user_id | bigint | 20 | 否 | - | 主键,用户ID,自增 | +| dept_id | bigint | 20 | 是 | null | 部门ID | +| login_name | varchar | 30 | 否 | - | 登录账号 | +| user_name | varchar | 30 | 是 | '' | 用户昵称 | +| email | varchar | 50 | 是 | '' | 用户邮箱 | +| phonenumber | varchar | 11 | 是 | '' | 手机号码 | +| sex | char | 1 | 是 | '0' | 用户性别(0男 1女 2未知) | +| avatar | varchar | 100 | 是 | '' | 头像路径 | +| password | varchar | 50 | 是 | '' | 密码 | +| salt | varchar | 20 | 是 | '' | 盐加密 | +| status | char | 1 | 是 | '0' | 帐号状态(0正常 1停用) | +| login_ip | varchar | 128 | 是 | '' | 最后登录IP | +| login_date | datetime | - | 是 | null | 最后登录时间 | +| create_at | datetime | - | 否 | - | 创建时间 | +| update_at | datetime | - | 否 | - | 更新时间 | +| delete_at | datetime | - | 是 | null | 删除时间,软删除 | + +索引: +- PRIMARY KEY (user_id) + +### 字典类型表(sys_dict_type) +主要用于管理系统中的各种码表类型定义,包括字典名称、类型和状态等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| dict_id | bigint | 20 | 否 | - | 主键,字典ID,自增 | +| dict_name | varchar | 100 | 是 | '' | 字典名称 | +| dict_type | varchar | 100 | 是 | '' | 字典类型 | +| status | char | 1 | 是 | '0' | 状态(0正常 1停用) | +| create_at | datetime | - | 否 | - | 创建时间 | +| update_at | datetime | - | 否 | - | 更新时间 | +| delete_at | datetime | - | 是 | null | 删除时间,软删除 | +| remark | varchar | 500 | 是 | null | 备注 | + +索引: +- PRIMARY KEY (dict_id) +- UNIQUE KEY idx_dict_type (dict_type) + +### 字典数据表(sys_dict_data) +主要用于存储字典类型下的字典项数据,包括字典标签、键值和排序等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| dict_code | bigint | 20 | 否 | - | 主键,字典编码,自增 | +| dict_sort | int | 4 | 是 | 0 | 字典排序 | +| dict_label | varchar | 100 | 是 | '' | 字典标签 | +| dict_value | varchar | 100 | 是 | '' | 字典键值 | +| dict_type | varchar | 100 | 是 | '' | 字典类型 | +| css_class | varchar | 100 | 是 | null | 样式属性(其他样式扩展) | +| is_default | char | 1 | 是 | 'N' | 是否默认(Y是 N否) | +| status | char | 1 | 是 | '0' | 状态(0正常 1停用) | +| create_at | datetime | - | 否 | - | 创建时间 | +| update_at | datetime | - | 否 | - | 更新时间 | +| remark | varchar | 500 | 是 | null | 备注 | + +索引: +- PRIMARY KEY (dict_code) +- KEY idx_dict_type (dict_type) + +### 系统角色表(sys_role) +主要用于管理系统角色权限,包含角色的基本信息、数据权限范围和状态等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| role_id | bigint | 20 | 否 | - | 主键,角色ID,自增 | +| role_name | varchar | 30 | 否 | - | 角色名称 | +| role_key | varchar | 100 | 否 | - | 角色权限字符串 | +| data_scope | char | 1 | 是 | '1' | 数据范围(1:全部数据权限 2:自定数据权限 3:本部门数据权限 4:本部门及以下数据权限) | +| status | char | 1 | 否 | - | 角色状态(0正常 1停用) | +| create_time | datetime | - | 是 | null | 创建时间 | +| update_time | datetime | - | 是 | null | 更新时间 | +| delete_at | datetime | - | 是 | null | 删除时间 | + +索引: +- PRIMARY KEY (role_id) + +### 用户角色关系表(sys_user_role) +主要用于管理用户和角色的多对多关联关系。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| id | bigint | 20 | 否 | - | 主键ID,自增 | +| user_id | bigint | 20 | 否 | - | 用户ID | +| role_id | bigint | 20 | 否 | - | 角色ID | + +索引: +- PRIMARY KEY (id) + +### 部门信息表(sys_dept) +主要用于管理组织架构,包含部门的基本信息、层级关系和联系方式等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| dept_id | bigint | 20 | 否 | - | 主键,部门id,自增 | +| parent_id | bigint | 20 | 是 | 0 | 父部门id | +| ancestors | varchar | 50 | 是 | '' | 祖级列表 | +| dept_name | varchar | 30 | 是 | '' | 部门名称 | +| order_num | int | 4 | 是 | 0 | 显示顺序 | +| contact_person | varchar | 20 | 是 | null | 联系人 | +| contact_phone | varchar | 11 | 是 | null | 联系电话 | +| contact_email | varchar | 50 | 是 | null | 联系邮箱 | +| status | char | 1 | 是 | '0' | 部门状态:0-正常,1-停用 | +| create_at | datetime | - | 否 | - | 创建时间 | +| update_at | datetime | - | 否 | - | 更新时间 | +| delete_at | datetime | - | 是 | null | 删除时间,软删除 | + +索引: +- PRIMARY KEY (dept_id) + +### 菜单权限表(sys_menu) +主要用于管理系统菜单权限,包含菜单的基本信息、层级关系和权限标识等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| menu_id | bigint | 20 | 否 | - | 主键,菜单ID,自增 | +| menu_name | varchar | 50 | 否 | - | 菜单名称 | +| parent_id | bigint | 20 | 是 | 0 | 父菜单ID | +| order_num | int | 4 | 是 | 0 | 显示顺序 | +| url | varchar | 200 | 是 | '#' | 路由地址 | +| target | varchar | 20 | 是 | '' | 打开方式(menuItem页签 menuBlank新窗口) | +| menu_type | char | 1 | 是 | '' | 菜单类型(M模块 C菜单 F按钮) | +| perms | varchar | 100 | 是 | null | 权限标识 | +| icon | varchar | 100 | 是 | '#' | 菜单图标 | +| create_at | datetime | - | 否 | - | 创建时间 | +| update_at | datetime | - | 否 | - | 更新时间 | +| delete_at | datetime | - | 是 | null | 删除时间 | +| remark | varchar | 500 | 是 | '' | 备注 | + +索引: +- PRIMARY KEY (menu_id) + +### 角色菜单关系表(sys_role_menu) +主要用于管理角色和菜单的多对多关联关系。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| id | bigint | 20 | 否 | - | 主键ID,自增 | +| role_id | bigint | 20 | 否 | - | 角色ID | +| menu_id | bigint | 20 | 否 | - | 菜单ID | + +索引: +- PRIMARY KEY (id) + + +## 业务表 + +### 产品编码表(product_code) +主要用于存储产品的基本信息,包括产品型号、规格等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| id | bigint | - | 否 | - | 主键,自增 | +| product_code | varchar | 64 | 否 | - | 产品编码,唯一 | +| product_name | varchar | 128 | 否 | - | 产品名称 | +| model | varchar | 64 | 否 | - | 产品代码 | +| description | text | - | 是 | null | 产品描述 | +| unit | varchar | 16 | 否 | '个' | 单位 | +| remark | varchar | 512 | 是 | null | 备注 | +| created_at | datetime | - | 否 | CURRENT_TIMESTAMP | 创建时间 | +| updated_at | datetime | - | 否 | CURRENT_TIMESTAMP | 更新时间 | +| deleted_at | datetime | - | 是 | null | 删除时间,软删除 | + +索引: +- PRIMARY KEY (id) +- UNIQUE KEY idx_product_code (product_code) +- KEY idx_model (model) + +### 项目信息表(project_info) +主要用于存储项目的基本信息,包括项目状态、客户信息等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| id | bigint | - | 否 | - | 主键,自增 | +| project_code | varchar | 32 | 否 | - | 项目编号,唯一 | +| project_name | varchar | 128 | 否 | - | 项目名称 | +| customer_name | varchar | 64 | 否 | - | 客户名称 | +| customer_contact | varchar | 32 | 是 | null | 客户联系人 | +| customer_phone | varchar | 20 | 是 | null | 客户联系电话 | +| customer_email | varchar | 64 | 是 | null | 客户邮箱 | +| project_status | tinyint | - | 否 | 1 | 项目状态:1-进行中,2-已签合同,3-已交付,99-已终止 | +| bg_property | tinyint | - | 否 | - | BG属性:1-商业,2-行业 | +| industry_code | tinyint | - | 否 | - | 行业编码 | +| project_manager | varchar | 32 | 否 | - | 项目经理 | +| project_manager_phone | varchar | 20 | 是 | null | 项目经理电话 | +| project_manager_email | varchar | 64 | 是 | null | 项目经理邮箱 | +| start_date | date | - | 否 | - | 项目开始日期 | +| description | text | - | 是 | null | 项目描述 | +| created_at | datetime | - | 否 | CURRENT_TIMESTAMP | 创建时间 | +| updated_at | datetime | - | 否 | CURRENT_TIMESTAMP | 更新时间 | +| deleted_at | datetime | - | 是 | null | 删除时间,软删除 | + +索引: +- PRIMARY KEY (id) +- UNIQUE KEY idx_project_code (project_code) +- KEY idx_customer_name (customer_name) +- KEY idx_project_status (project_status) + +### 合同信息表(order_info) +主要用于存储项目的合同信息,与项目信息表为一对多关系。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| id | bigint | - | 否 | - | 主键,自增 | +| project_code | varchar | 32 | 否 | - | 关联项目编号 | +| order_code | varchar | 32 | 否 | - | 合同编号,唯一 | +| order_name | varchar | 128 | 否 | - | 合同名称 | +| customer_name | varchar | 64 | 否 | - | 客户名称 | +| customer_contact | varchar | 32 | 是 | null | 客户联系人 | +| customer_phone | varchar | 20 | 是 | null | 客户联系电话 | +| customer_email | varchar | 64 | 是 | null | 客户邮箱 | +| order_type | tinyint | - | 否 | - | 合同类型:1-直签合同,2-代理商合同 | +| order_dept | varchar | 32 | 否 | - | 归属代表处编码 | +| partener_dept | varchar | 32 | 否 | - | 代理商编码 | +| order_date | date | - | 否 | - | 合同签定日期 | +| order_status | tinyint | - | 否 | 1 | 合同状态:1-待审核,2-已审核,3-已驳回 | +| remark | varchar | 512 | 是 | null | 备注 | +| created_at | datetime | - | 否 | CURRENT_TIMESTAMP | 创建时间 | +| updated_at | datetime | - | 否 | CURRENT_TIMESTAMP | 更新时间 | +| deleted_at | datetime | - | 是 | null | 删除时间,软删除 | + +索引: +- PRIMARY KEY (id) +- UNIQUE KEY idx_order_code (order_code) + +### 合同清单表(order_list) +主要用于记录合同包含的产品信息,包括产品编码、单价和数量等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| id | bigint | - | 否 | - | 主键,自增 | +| order_code | varchar | 32 | 否 | - | 关联合同编号 | +| product_code | varchar | 64 | 否 | - | 产品编码,关联产品编码表 | +| quantity | int | - | 否 | 1 | 数量 | +| price | decimal | 10,2 | 否 | 0 | 单价 | +| amount | decimal | 10,2 | 否 | 0 | 总价 | +| remark | varchar | 512 | 是 | null | 备注 | +| created_at | datetime | - | 否 | CURRENT_TIMESTAMP | 创建时间 | +| updated_at | datetime | - | 否 | CURRENT_TIMESTAMP | 更新时间 | +| deleted_at | datetime | - | 是 | null | 删除时间,软删除 | + +索引: +- PRIMARY KEY (id) +- KEY idx_order_id (order_id) +- KEY idx_product_code (product_code) + +### 发货记录表(order_delivery) +主要用于记录产品的发货信息,包括发货时间、物流信息等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| id | bigint | - | 否 | - | 主键,自增 | +| order_code | varchar | 32 | 否 | - | 关联合同编号 | +| delivery_code | varchar | 32 | 否 | - | 发货单号,唯一 | +| delivery_date | date | - | 否 | - | 发货日期 | +| delivery_type | tinyint | - | 否 | 1 | 发货方式:1-快递,2-物流,3-自提 | +| logistics_company | varchar | 64 | 是 | null | 物流公司 | +| logistics_code | varchar | 32 | 是 | null | 物流单号 | +| receiver_name | varchar | 32 | 否 | - | 收货人姓名 | +| receiver_phone | varchar | 20 | 否 | - | 收货人电话 | +| receiver_address | varchar | 256 | 否 | - | 收货地址 | +| delivery_status | tinyint | - | 否 | 1 | 发货状态:1-待发货,2-已发货,3-已签收 | +| sign_time | datetime | - | 是 | null | 签收时间 | +| remark | varchar | 512 | 是 | null | 备注 | +| created_at | datetime | - | 否 | CURRENT_TIMESTAMP | 创建时间 | +| updated_at | datetime | - | 否 | CURRENT_TIMESTAMP | 更新时间 | +| deleted_at | datetime | - | 是 | null | 删除时间,软删除 | + +索引: +- PRIMARY KEY (id) +- UNIQUE KEY idx_delivery_code (delivery_code) +- KEY idx_order_id (order_id) +- KEY idx_delivery_status (delivery_status) + +### 发货清单表(delivery_list) +主要用于记录每个发货单包含的具体产品信息,包括产品编码和序列号等。 + +| 字段名 | 类型 | 长度 | 允许空 | 默认值 | 说明 | +|--------|------|------|--------|--------|------| +| id | bigint | - | 否 | - | 主键,自增 | +| delivery_code | varchar | 32 | 否 | - | 关联发货单编号 | +| product_code | varchar | 64 | 否 | - | 产品编码,关联产品编码表 | +| serial_number | varchar | 64 | 否 | - | 产品序列号 | +| remark | varchar | 512 | 是 | null | 备注 | +| created_at | datetime | - | 否 | CURRENT_TIMESTAMP | 创建时间 | +| updated_at | datetime | - | 否 | CURRENT_TIMESTAMP | 更新时间 | +| deleted_at | datetime | - | 是 | null | 删除时间,软删除 | + +索引: +- PRIMARY KEY (id) +- KEY idx_delivery_id (delivery_id) +- KEY idx_product_code (product_code) +- UNIQUE KEY idx_serial_number (serial_number) + + diff --git a/src/main/java/com/unissense/sip/UnisSipApplication.java b/src/main/java/com/unissense/sip/UnisSipApplication.java new file mode 100644 index 0000000..bff41dd --- /dev/null +++ b/src/main/java/com/unissense/sip/UnisSipApplication.java @@ -0,0 +1,14 @@ +package com.unissense.sip; + +import org.mybatis.spring.annotation.MapperScan; +import org.springframework.boot.SpringApplication; +import org.springframework.boot.autoconfigure.SpringBootApplication; + +@SpringBootApplication +@MapperScan("com.unissense.sip.mapper") +public class UnisSipApplication { + + public static void main(String[] args) { + SpringApplication.run(UnisSipApplication.class, args); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/config/SecurityConfig.java b/src/main/java/com/unissense/sip/config/SecurityConfig.java new file mode 100644 index 0000000..c964921 --- /dev/null +++ b/src/main/java/com/unissense/sip/config/SecurityConfig.java @@ -0,0 +1,13 @@ +package com.unissense.sip.config; + +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; + +@Configuration +public class SecurityConfig { + @Bean + public BCryptPasswordEncoder passwordEncoder() { + return new BCryptPasswordEncoder(); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/controller/AuthController.java b/src/main/java/com/unissense/sip/controller/AuthController.java new file mode 100644 index 0000000..0a47207 --- /dev/null +++ b/src/main/java/com/unissense/sip/controller/AuthController.java @@ -0,0 +1,48 @@ +package com.unissense.sip.controller; + +import com.unissense.sip.dto.LoginRequest; +import com.unissense.sip.dto.LoginResponse; +import com.unissense.sip.service.SysUserService; +import com.unissense.sip.utils.CaptchaUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.data.redis.core.StringRedisTemplate; +import org.springframework.http.MediaType; +import org.springframework.web.bind.annotation.*; + +import javax.imageio.ImageIO; +import javax.servlet.http.HttpServletResponse; +import java.awt.image.BufferedImage; +import java.io.ByteArrayOutputStream; +import java.util.concurrent.TimeUnit; + +@RestController +@RequestMapping("/api") +public class AuthController { + + @Autowired + private SysUserService userService; + + @Autowired + private StringRedisTemplate redisTemplate; + + @GetMapping("/captcha") + public void getCaptcha(@RequestParam String username, HttpServletResponse response) throws Exception { + StringBuilder captcha = new StringBuilder(); + BufferedImage image = CaptchaUtils.generateCaptchaImage(captcha); + + // 将验证码存入Redis,设置60秒过期 + String captchaKey = "captcha:" + username; + redisTemplate.opsForValue().set(captchaKey, captcha.toString(), 60, TimeUnit.SECONDS); + + // 输出图片 + response.setContentType(MediaType.IMAGE_PNG_VALUE); + ByteArrayOutputStream os = new ByteArrayOutputStream(); + ImageIO.write(image, "png", os); + response.getOutputStream().write(os.toByteArray()); + } + + @PostMapping("/login") + public LoginResponse login(@RequestBody LoginRequest loginRequest) { + return userService.login(loginRequest); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/controller/SysDeptController.java b/src/main/java/com/unissense/sip/controller/SysDeptController.java new file mode 100644 index 0000000..d77b2d1 --- /dev/null +++ b/src/main/java/com/unissense/sip/controller/SysDeptController.java @@ -0,0 +1,32 @@ +package com.unissense.sip.controller; + +import com.unissense.sip.entity.SysDept; +import com.unissense.sip.service.SysDeptService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.*; + +@RestController +@RequestMapping("/api/depts") +public class SysDeptController { + + @Autowired + private SysDeptService sysDeptService; + + @GetMapping("/{deptCode}") + public ResponseEntity getDeptByCode(@PathVariable String deptCode) { + SysDept dept = sysDeptService.getByDeptCode(deptCode); + return dept != null ? ResponseEntity.ok(dept) : ResponseEntity.notFound().build(); + } + + @PostMapping + public ResponseEntity createDept(@RequestBody SysDept dept) { + boolean success = sysDeptService.createDept(dept); + return success ? ResponseEntity.ok(true) : ResponseEntity.badRequest().build(); + } + + @GetMapping + public ResponseEntity listDepts() { + return ResponseEntity.ok(sysDeptService.list()); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/controller/SysDictDataController.java b/src/main/java/com/unissense/sip/controller/SysDictDataController.java new file mode 100644 index 0000000..98a81fd --- /dev/null +++ b/src/main/java/com/unissense/sip/controller/SysDictDataController.java @@ -0,0 +1,80 @@ +package com.unissense.sip.controller; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.plugins.pagination.Page; +import com.unissense.sip.entity.SysDictData; +import com.unissense.sip.service.SysDictDataService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.*; + +import java.time.LocalDateTime; +import java.util.List; + +/** + * 字典数据Controller + */ +@RestController +@RequestMapping("/system/dict/data") +public class SysDictDataController { + + @Autowired + private SysDictDataService dictDataService; + + /** + * 获取字典数据列表 + */ + @GetMapping("/list") + public Page list( + @RequestParam(value = "pageNum", defaultValue = "1") Integer pageNum, + @RequestParam(value = "pageSize", defaultValue = "10") Integer pageSize, + SysDictData dictData) { + LambdaQueryWrapper wrapper = new LambdaQueryWrapper<>(); + wrapper.eq(dictData.getDictType() != null, SysDictData::getDictType, dictData.getDictType()) + .like(dictData.getDictLabel() != null, SysDictData::getDictLabel, dictData.getDictLabel()) + .eq(dictData.getStatus() != null, SysDictData::getStatus, dictData.getStatus()) + .orderByAsc(SysDictData::getDictSort); + return dictDataService.page(new Page<>(pageNum, pageSize), wrapper); + } + + /** + * 根据字典类型查询字典数据信息 + */ + @GetMapping(value = "/type/{dictType}") + public List dictType(@PathVariable String dictType) { + return dictDataService.selectDictDataByType(dictType); + } + + /** + * 获取字典数据详细信息 + */ + @GetMapping("/{dictCode}") + public SysDictData getInfo(@PathVariable Long dictCode) { + return dictDataService.getById(dictCode); + } + + /** + * 新增字典数据 + */ + @PostMapping + public boolean add(@RequestBody SysDictData dict) { + dict.setCreateTime(LocalDateTime.now()); + return dictDataService.save(dict); + } + + /** + * 修改字典数据 + */ + @PutMapping + public boolean edit(@RequestBody SysDictData dict) { + dict.setUpdateTime(LocalDateTime.now()); + return dictDataService.updateById(dict); + } + + /** + * 删除字典数据 + */ + @DeleteMapping("/{dictCode}") + public boolean remove(@PathVariable Long dictCode) { + return dictDataService.removeById(dictCode); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/controller/SysDictTypeController.java b/src/main/java/com/unissense/sip/controller/SysDictTypeController.java new file mode 100644 index 0000000..aa30bb6 --- /dev/null +++ b/src/main/java/com/unissense/sip/controller/SysDictTypeController.java @@ -0,0 +1,71 @@ +package com.unissense.sip.controller; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.plugins.pagination.Page; +import com.unissense.sip.entity.SysDictType; +import com.unissense.sip.service.SysDictTypeService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.web.bind.annotation.*; + +import java.time.LocalDateTime; + +/** + * 字典类型Controller + */ +@RestController +@RequestMapping("/system/dict/type") +public class SysDictTypeController { + + @Autowired + private SysDictTypeService dictTypeService; + + /** + * 获取字典类型列表 + */ + @GetMapping("/list") + public Page list( + @RequestParam(value = "pageNum", defaultValue = "1") Integer pageNum, + @RequestParam(value = "pageSize", defaultValue = "10") Integer pageSize, + SysDictType dictType) { + LambdaQueryWrapper wrapper = new LambdaQueryWrapper<>(); + wrapper.like(dictType.getDictName() != null, SysDictType::getDictName, dictType.getDictName()) + .like(dictType.getDictType() != null, SysDictType::getDictType, dictType.getDictType()) + .eq(dictType.getStatus() != null, SysDictType::getStatus, dictType.getStatus()) + .orderByAsc(SysDictType::getDictId); + return dictTypeService.page(new Page<>(pageNum, pageSize), wrapper); + } + + /** + * 获取字典类型详细信息 + */ + @GetMapping("/{dictId}") + public SysDictType getInfo(@PathVariable Long dictId) { + return dictTypeService.getById(dictId); + } + + /** + * 新增字典类型 + */ + @PostMapping + public boolean add(@RequestBody SysDictType dict) { + dict.setCreateTime(LocalDateTime.now()); + return dictTypeService.save(dict); + } + + /** + * 修改字典类型 + */ + @PutMapping + public boolean edit(@RequestBody SysDictType dict) { + dict.setUpdateTime(LocalDateTime.now()); + return dictTypeService.updateById(dict); + } + + /** + * 删除字典类型 + */ + @DeleteMapping("/{dictId}") + public boolean remove(@PathVariable Long dictId) { + return dictTypeService.removeById(dictId); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/controller/SysMenuController.java b/src/main/java/com/unissense/sip/controller/SysMenuController.java new file mode 100644 index 0000000..9216e28 --- /dev/null +++ b/src/main/java/com/unissense/sip/controller/SysMenuController.java @@ -0,0 +1,40 @@ +package com.unissense.sip.controller; + +import com.unissense.sip.entity.SysMenu; +import com.unissense.sip.service.SysMenuService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.*; + +import java.util.List; + +@RestController +@RequestMapping("/api/menus") +public class SysMenuController { + + @Autowired + private SysMenuService sysMenuService; + + @GetMapping("/{menuCode}") + public ResponseEntity getMenuByCode(@PathVariable String menuCode) { + SysMenu menu = sysMenuService.getByMenuCode(menuCode); + return menu != null ? ResponseEntity.ok(menu) : ResponseEntity.notFound().build(); + } + + @PostMapping + public ResponseEntity createMenu(@RequestBody SysMenu menu) { + boolean success = sysMenuService.createMenu(menu); + return success ? ResponseEntity.ok(true) : ResponseEntity.badRequest().build(); + } + + @GetMapping + public ResponseEntity listMenus() { + return ResponseEntity.ok(sysMenuService.list()); + } + + @GetMapping("/children/{parentId}") + public ResponseEntity> getChildrenMenus(@PathVariable Long parentId) { + List children = sysMenuService.getChildrenMenus(parentId); + return ResponseEntity.ok(children); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/controller/SysRoleController.java b/src/main/java/com/unissense/sip/controller/SysRoleController.java new file mode 100644 index 0000000..0a385f6 --- /dev/null +++ b/src/main/java/com/unissense/sip/controller/SysRoleController.java @@ -0,0 +1,26 @@ +package com.unissense.sip.controller; + +import com.unissense.sip.entity.SysRole; +import com.unissense.sip.service.SysRoleService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.*; + +@RestController +@RequestMapping("/api/roles") +public class SysRoleController { + + @Autowired + private SysRoleService sysRoleService; + + @PostMapping + public ResponseEntity createRole(@RequestBody SysRole role) { + boolean success = sysRoleService.createRole(role); + return success ? ResponseEntity.ok(true) : ResponseEntity.badRequest().build(); + } + + @GetMapping + public ResponseEntity listRoles() { + return ResponseEntity.ok(sysRoleService.list()); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/controller/SysUserController.java b/src/main/java/com/unissense/sip/controller/SysUserController.java new file mode 100644 index 0000000..81fd918 --- /dev/null +++ b/src/main/java/com/unissense/sip/controller/SysUserController.java @@ -0,0 +1,32 @@ +package com.unissense.sip.controller; + +import com.unissense.sip.entity.SysUser; +import com.unissense.sip.service.SysUserService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.*; + +@RestController +@RequestMapping("/api/users") +public class SysUserController { + + @Autowired + private SysUserService sysUserService; + + @GetMapping("/{username}") + public ResponseEntity getUserByUsername(@PathVariable String username) { + SysUser user = sysUserService.getByUsername(username); + return user != null ? ResponseEntity.ok(user) : ResponseEntity.notFound().build(); + } + + @PostMapping + public ResponseEntity createUser(@RequestBody SysUser user) { + boolean result = sysUserService.createUser(user); + return ResponseEntity.ok(result); + } + + @GetMapping("/test") + public ResponseEntity test() { + return ResponseEntity.ok("User API is working!"); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/controller/SysUserRoleController.java b/src/main/java/com/unissense/sip/controller/SysUserRoleController.java new file mode 100644 index 0000000..2c3d1f3 --- /dev/null +++ b/src/main/java/com/unissense/sip/controller/SysUserRoleController.java @@ -0,0 +1,36 @@ +package com.unissense.sip.controller; + +import com.unissense.sip.service.SysUserRoleService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.http.ResponseEntity; +import org.springframework.web.bind.annotation.*; + +import java.util.List; + +@RestController +@RequestMapping("/api/user-roles") +public class SysUserRoleController { + + @Autowired + private SysUserRoleService sysUserRoleService; + + @GetMapping("/user/{userId}/roles") + public ResponseEntity> getUserRoles(@PathVariable Long userId) { + List roleIds = sysUserRoleService.getRoleIdsByUserId(userId); + return ResponseEntity.ok(roleIds); + } + + @PostMapping("/user/{userId}/roles") + public ResponseEntity assignRoles( + @PathVariable Long userId, + @RequestBody List roleIds) { + boolean success = sysUserRoleService.assignRoles(userId, roleIds); + return success ? ResponseEntity.ok(true) : ResponseEntity.badRequest().build(); + } + + @DeleteMapping("/user/{userId}/roles") + public ResponseEntity removeUserRoles(@PathVariable Long userId) { + boolean success = sysUserRoleService.removeUserRoles(userId); + return success ? ResponseEntity.ok(true) : ResponseEntity.badRequest().build(); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/dto/LoginRequest.java b/src/main/java/com/unissense/sip/dto/LoginRequest.java new file mode 100644 index 0000000..ff11d31 --- /dev/null +++ b/src/main/java/com/unissense/sip/dto/LoginRequest.java @@ -0,0 +1,10 @@ +package com.unissense.sip.dto; + +import lombok.Data; + +@Data +public class LoginRequest { + private String username; + private String password; + private String captcha; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/dto/LoginResponse.java b/src/main/java/com/unissense/sip/dto/LoginResponse.java new file mode 100644 index 0000000..8d50dbe --- /dev/null +++ b/src/main/java/com/unissense/sip/dto/LoginResponse.java @@ -0,0 +1,15 @@ +package com.unissense.sip.dto; + +import com.unissense.sip.entity.SysMenu; +import com.unissense.sip.entity.SysUser; +import lombok.Data; + +import java.util.List; + +@Data +public class LoginResponse { + private String token; + private SysUser user; + private List roles; + private List menus; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/entity/SysDept.java b/src/main/java/com/unissense/sip/entity/SysDept.java new file mode 100644 index 0000000..480790c --- /dev/null +++ b/src/main/java/com/unissense/sip/entity/SysDept.java @@ -0,0 +1,46 @@ +package com.unissense.sip.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; + +import java.time.LocalDateTime; + +@Data +@TableName("sys_dept") +public class SysDept { + + @TableId(type = IdType.AUTO) + private Long deptId; + + private Long parentId; + + private String deptName; + + private Integer orderNum; + + private String leader; + + private String phone; + + private String email; + + private Integer status; + + private String deptCode; + + private LocalDateTime deleteAt; + + private LocalDateTime createAt; + + private String createBy; + + private LocalDateTime createTime; + + private String updateBy; + + private LocalDateTime updateTime; + + private String remark; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/entity/SysDictData.java b/src/main/java/com/unissense/sip/entity/SysDictData.java new file mode 100644 index 0000000..4c11e16 --- /dev/null +++ b/src/main/java/com/unissense/sip/entity/SysDictData.java @@ -0,0 +1,40 @@ +package com.unissense.sip.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; + +import java.time.LocalDateTime; + +@Data +@TableName("sys_dict_data") +public class SysDictData { + + @TableId(type = IdType.AUTO) + private Long dictCode; + + private Long dictSort; + + private String dictLabel; + + private String dictValue; + + private String dictType; + + private String cssClass; + + private String listClass; + + private Integer status; + + private String createBy; + + private LocalDateTime createTime; + + private String updateBy; + + private LocalDateTime updateTime; + + private String remark; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/entity/SysDictType.java b/src/main/java/com/unissense/sip/entity/SysDictType.java new file mode 100644 index 0000000..1e87dea --- /dev/null +++ b/src/main/java/com/unissense/sip/entity/SysDictType.java @@ -0,0 +1,32 @@ +package com.unissense.sip.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; + +import java.time.LocalDateTime; + +@Data +@TableName("sys_dict_type") +public class SysDictType { + + @TableId(type = IdType.AUTO) + private Long dictId; + + private String dictName; + + private String dictType; + + private Integer status; + + private String createBy; + + private LocalDateTime createTime; + + private String updateBy; + + private LocalDateTime updateTime; + + private String remark; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/entity/SysMenu.java b/src/main/java/com/unissense/sip/entity/SysMenu.java new file mode 100644 index 0000000..268f5d2 --- /dev/null +++ b/src/main/java/com/unissense/sip/entity/SysMenu.java @@ -0,0 +1,50 @@ +package com.unissense.sip.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; + +import java.time.LocalDateTime; + +@Data +@TableName("sys_menu") +public class SysMenu { + + @TableId(type = IdType.AUTO) + private Long menuId; + + private Long parentId; + + private String menuName; + + private String path; + + private String component; + + private String perms; + + private String icon; + + private Integer type; + + private Integer orderNum; + + private Integer status; + + private String menuCode; + + private LocalDateTime deleteAt; + + private LocalDateTime createAt; + + private String createBy; + + private LocalDateTime createTime; + + private String updateBy; + + private LocalDateTime updateTime; + + private String remark; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/entity/SysRole.java b/src/main/java/com/unissense/sip/entity/SysRole.java new file mode 100644 index 0000000..7644be3 --- /dev/null +++ b/src/main/java/com/unissense/sip/entity/SysRole.java @@ -0,0 +1,40 @@ +package com.unissense.sip.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; + +import java.time.LocalDateTime; + +@Data +@TableName("sys_role") +public class SysRole { + + @TableId(type = IdType.AUTO) + private Long roleId; + + private String roleName; + + private String roleKey; + + private Integer roleSort; + + private String dataScope; + + private Integer status; + + private LocalDateTime deleteAt; + + private LocalDateTime createAt; + + private String createBy; + + private LocalDateTime createTime; + + private String updateBy; + + private LocalDateTime updateTime; + + private String remark; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/entity/SysRoleMenu.java b/src/main/java/com/unissense/sip/entity/SysRoleMenu.java new file mode 100644 index 0000000..8c59453 --- /dev/null +++ b/src/main/java/com/unissense/sip/entity/SysRoleMenu.java @@ -0,0 +1,18 @@ +package com.unissense.sip.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; + +@Data +@TableName("sys_role_menu") +public class SysRoleMenu { + + @TableId(type = IdType.AUTO) + private Long id; + + private Long roleId; + + private Long menuId; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/entity/SysUser.java b/src/main/java/com/unissense/sip/entity/SysUser.java new file mode 100644 index 0000000..7a332ad --- /dev/null +++ b/src/main/java/com/unissense/sip/entity/SysUser.java @@ -0,0 +1,31 @@ +package com.unissense.sip.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; + +import java.time.LocalDateTime; + +@Data +@TableName("sys_user") +public class SysUser { + @TableId(type = IdType.AUTO) + private Long id; + + private String username; + + private String password; + + private String email; + + private String phone; + + private Integer status; + + private LocalDateTime createTime; + + private LocalDateTime updateTime; + + private LocalDateTime deleteAt; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/entity/SysUserRole.java b/src/main/java/com/unissense/sip/entity/SysUserRole.java new file mode 100644 index 0000000..3541cb8 --- /dev/null +++ b/src/main/java/com/unissense/sip/entity/SysUserRole.java @@ -0,0 +1,18 @@ +package com.unissense.sip.entity; + +import com.baomidou.mybatisplus.annotation.IdType; +import com.baomidou.mybatisplus.annotation.TableId; +import com.baomidou.mybatisplus.annotation.TableName; +import lombok.Data; + +@Data +@TableName("sys_user_role") +public class SysUserRole { + + @TableId(type = IdType.AUTO) + private Long id; + + private Long userId; + + private Long roleId; +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/mapper/SysDeptMapper.java b/src/main/java/com/unissense/sip/mapper/SysDeptMapper.java new file mode 100644 index 0000000..4d26e91 --- /dev/null +++ b/src/main/java/com/unissense/sip/mapper/SysDeptMapper.java @@ -0,0 +1,9 @@ +package com.unissense.sip.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.unissense.sip.entity.SysDept; +import org.apache.ibatis.annotations.Mapper; + +@Mapper +public interface SysDeptMapper extends BaseMapper { +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/mapper/SysDictDataMapper.java b/src/main/java/com/unissense/sip/mapper/SysDictDataMapper.java new file mode 100644 index 0000000..34b5f8e --- /dev/null +++ b/src/main/java/com/unissense/sip/mapper/SysDictDataMapper.java @@ -0,0 +1,9 @@ +package com.unissense.sip.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.unissense.sip.entity.SysDictData; +import org.apache.ibatis.annotations.Mapper; + +@Mapper +public interface SysDictDataMapper extends BaseMapper { +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/mapper/SysDictTypeMapper.java b/src/main/java/com/unissense/sip/mapper/SysDictTypeMapper.java new file mode 100644 index 0000000..ba1075b --- /dev/null +++ b/src/main/java/com/unissense/sip/mapper/SysDictTypeMapper.java @@ -0,0 +1,9 @@ +package com.unissense.sip.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.unissense.sip.entity.SysDictType; +import org.apache.ibatis.annotations.Mapper; + +@Mapper +public interface SysDictTypeMapper extends BaseMapper { +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/mapper/SysMenuMapper.java b/src/main/java/com/unissense/sip/mapper/SysMenuMapper.java new file mode 100644 index 0000000..9aa3919 --- /dev/null +++ b/src/main/java/com/unissense/sip/mapper/SysMenuMapper.java @@ -0,0 +1,9 @@ +package com.unissense.sip.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.unissense.sip.entity.SysMenu; +import org.apache.ibatis.annotations.Mapper; + +@Mapper +public interface SysMenuMapper extends BaseMapper { +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/mapper/SysRoleMapper.java b/src/main/java/com/unissense/sip/mapper/SysRoleMapper.java new file mode 100644 index 0000000..e983033 --- /dev/null +++ b/src/main/java/com/unissense/sip/mapper/SysRoleMapper.java @@ -0,0 +1,9 @@ +package com.unissense.sip.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.unissense.sip.entity.SysRole; +import org.apache.ibatis.annotations.Mapper; + +@Mapper +public interface SysRoleMapper extends BaseMapper { +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/mapper/SysRoleMenuMapper.java b/src/main/java/com/unissense/sip/mapper/SysRoleMenuMapper.java new file mode 100644 index 0000000..085d39d --- /dev/null +++ b/src/main/java/com/unissense/sip/mapper/SysRoleMenuMapper.java @@ -0,0 +1,9 @@ +package com.unissense.sip.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.unissense.sip.entity.SysRoleMenu; +import org.apache.ibatis.annotations.Mapper; + +@Mapper +public interface SysRoleMenuMapper extends BaseMapper { +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/mapper/SysUserMapper.java b/src/main/java/com/unissense/sip/mapper/SysUserMapper.java new file mode 100644 index 0000000..6f7c3f0 --- /dev/null +++ b/src/main/java/com/unissense/sip/mapper/SysUserMapper.java @@ -0,0 +1,9 @@ +package com.unissense.sip.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.unissense.sip.entity.SysUser; +import org.apache.ibatis.annotations.Mapper; + +@Mapper +public interface SysUserMapper extends BaseMapper { +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/mapper/SysUserRoleMapper.java b/src/main/java/com/unissense/sip/mapper/SysUserRoleMapper.java new file mode 100644 index 0000000..188a25e --- /dev/null +++ b/src/main/java/com/unissense/sip/mapper/SysUserRoleMapper.java @@ -0,0 +1,9 @@ +package com.unissense.sip.mapper; + +import com.baomidou.mybatisplus.core.mapper.BaseMapper; +import com.unissense.sip.entity.SysUserRole; +import org.apache.ibatis.annotations.Mapper; + +@Mapper +public interface SysUserRoleMapper extends BaseMapper { +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/SysDeptService.java b/src/main/java/com/unissense/sip/service/SysDeptService.java new file mode 100644 index 0000000..3097b38 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/SysDeptService.java @@ -0,0 +1,20 @@ +package com.unissense.sip.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import com.unissense.sip.entity.SysDept; + +public interface SysDeptService extends IService { + /** + * 根据部门编码查询部门 + * @param deptCode 部门编码 + * @return 部门信息 + */ + SysDept getByDeptCode(String deptCode); + + /** + * 创建新部门 + * @param dept 部门信息 + * @return 是否创建成功 + */ + boolean createDept(SysDept dept); +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/SysDictDataService.java b/src/main/java/com/unissense/sip/service/SysDictDataService.java new file mode 100644 index 0000000..8cab0f5 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/SysDictDataService.java @@ -0,0 +1,29 @@ +package com.unissense.sip.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import com.unissense.sip.entity.SysDictData; + +import java.util.List; + +/** + * 字典数据Service接口 + */ +public interface SysDictDataService extends IService { + + /** + * 根据字典类型查询字典数据列表 + * + * @param dictType 字典类型 + * @return 字典数据列表 + */ + List selectDictDataByType(String dictType); + + /** + * 根据字典类型和字典键值查询字典数据信息 + * + * @param dictType 字典类型 + * @param dictValue 字典键值 + * @return 字典标签 + */ + String selectDictLabel(String dictType, String dictValue); +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/SysDictTypeService.java b/src/main/java/com/unissense/sip/service/SysDictTypeService.java new file mode 100644 index 0000000..dd02eda --- /dev/null +++ b/src/main/java/com/unissense/sip/service/SysDictTypeService.java @@ -0,0 +1,18 @@ +package com.unissense.sip.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import com.unissense.sip.entity.SysDictType; + +/** + * 字典类型Service接口 + */ +public interface SysDictTypeService extends IService { + + /** + * 根据字典类型查询字典数据 + * + * @param dictType 字典类型 + * @return 字典数据 + */ + SysDictType selectDictTypeByType(String dictType); +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/SysMenuService.java b/src/main/java/com/unissense/sip/service/SysMenuService.java new file mode 100644 index 0000000..f8814b1 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/SysMenuService.java @@ -0,0 +1,29 @@ +package com.unissense.sip.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import com.unissense.sip.entity.SysMenu; + +import java.util.List; + +public interface SysMenuService extends IService { + /** + * 根据菜单编码查询菜单 + * @param menuCode 菜单编码 + * @return 菜单信息 + */ + SysMenu getByMenuCode(String menuCode); + + /** + * 创建新菜单 + * @param menu 菜单信息 + * @return 是否创建成功 + */ + boolean createMenu(SysMenu menu); + + /** + * 获取子菜单列表 + * @param parentId 父菜单ID + * @return 子菜单列表 + */ + List getChildrenMenus(Long parentId); +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/SysRoleMenuService.java b/src/main/java/com/unissense/sip/service/SysRoleMenuService.java new file mode 100644 index 0000000..3eb1bfe --- /dev/null +++ b/src/main/java/com/unissense/sip/service/SysRoleMenuService.java @@ -0,0 +1,30 @@ +package com.unissense.sip.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import com.unissense.sip.entity.SysRoleMenu; + +import java.util.List; + +public interface SysRoleMenuService extends IService { + /** + * 获取角色的菜单ID列表 + * @param roleId 角色ID + * @return 菜单ID列表 + */ + List getMenuIdsByRoleId(Long roleId); + + /** + * 为角色分配菜单 + * @param roleId 角色ID + * @param menuIds 菜单ID列表 + * @return 是否分配成功 + */ + boolean assignMenus(Long roleId, List menuIds); + + /** + * 删除角色的所有菜单 + * @param roleId 角色ID + * @return 是否删除成功 + */ + boolean removeRoleMenus(Long roleId); +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/SysRoleService.java b/src/main/java/com/unissense/sip/service/SysRoleService.java new file mode 100644 index 0000000..67a5925 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/SysRoleService.java @@ -0,0 +1,14 @@ +package com.unissense.sip.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import com.unissense.sip.entity.SysRole; + +public interface SysRoleService extends IService { + + /** + * 创建新角色 + * @param role 角色信息 + * @return 是否创建成功 + */ + boolean createRole(SysRole role); +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/SysUserRoleService.java b/src/main/java/com/unissense/sip/service/SysUserRoleService.java new file mode 100644 index 0000000..a6481f6 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/SysUserRoleService.java @@ -0,0 +1,45 @@ +package com.unissense.sip.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import com.unissense.sip.entity.SysUserRole; +import com.unissense.sip.entity.SysMenu; + +import java.util.List; + +public interface SysUserRoleService extends IService { + /** + * 获取用户的角色ID列表 + * @param userId 用户ID + * @return 角色ID列表 + */ + List getRoleIdsByUserId(Long userId); + + /** + * 为用户分配角色 + * @param userId 用户ID + * @param roleIds 角色ID列表 + * @return 是否分配成功 + */ + boolean assignRoles(Long userId, List roleIds); + + /** + * 删除用户的所有角色 + * @param userId 用户ID + * @return 是否删除成功 + */ + boolean removeUserRoles(Long userId); + + /** + * 获取用户的角色标识列表 + * @param userId 用户ID + * @return 角色标识列表 + */ + List getRoleKeysByUserId(Long userId); + + /** + * 获取用户的菜单列表 + * @param userId 用户ID + * @return 菜单列表 + */ + List getMenusByUserId(Long userId); +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/SysUserService.java b/src/main/java/com/unissense/sip/service/SysUserService.java new file mode 100644 index 0000000..f81ab90 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/SysUserService.java @@ -0,0 +1,46 @@ +package com.unissense.sip.service; + +import com.baomidou.mybatisplus.extension.service.IService; +import com.unissense.sip.dto.LoginRequest; +import com.unissense.sip.dto.LoginResponse; +import com.unissense.sip.entity.SysMenu; +import com.unissense.sip.entity.SysUser; + +import java.util.List; + +public interface SysUserService extends IService { + /** + * 根据用户名查询用户 + * @param username 用户名 + * @return 用户对象 + */ + SysUser getByUsername(String username); + + /** + * 创建新用户 + * @param user 用户信息 + * @return 是否创建成功 + */ + boolean createUser(SysUser user); + + /** + * 用户登录 + * @param loginRequest 登录请求 + * @return 登录响应 + */ + LoginResponse login(LoginRequest loginRequest); + + /** + * 获取用户角色列表 + * @param userId 用户ID + * @return 角色标识列表 + */ + List getUserRoles(Long userId); + + /** + * 获取用户菜单权限 + * @param userId 用户ID + * @return 菜单列表 + */ + List getUserMenus(Long userId); +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/impl/SysDeptServiceImpl.java b/src/main/java/com/unissense/sip/service/impl/SysDeptServiceImpl.java new file mode 100644 index 0000000..0779140 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/impl/SysDeptServiceImpl.java @@ -0,0 +1,27 @@ +package com.unissense.sip.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.unissense.sip.entity.SysDept; +import com.unissense.sip.mapper.SysDeptMapper; +import com.unissense.sip.service.SysDeptService; +import org.springframework.stereotype.Service; + +import java.time.LocalDateTime; + +@Service +public class SysDeptServiceImpl extends ServiceImpl implements SysDeptService { + + @Override + public SysDept getByDeptCode(String deptCode) { + return this.getOne(new LambdaQueryWrapper() + .eq(SysDept::getDeptCode, deptCode) + .isNull(SysDept::getDeleteAt)); + } + + @Override + public boolean createDept(SysDept dept) { + dept.setCreateAt(LocalDateTime.now()); + return this.save(dept); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/impl/SysDictDataServiceImpl.java b/src/main/java/com/unissense/sip/service/impl/SysDictDataServiceImpl.java new file mode 100644 index 0000000..69f448e --- /dev/null +++ b/src/main/java/com/unissense/sip/service/impl/SysDictDataServiceImpl.java @@ -0,0 +1,34 @@ +package com.unissense.sip.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.unissense.sip.entity.SysDictData; +import com.unissense.sip.mapper.SysDictDataMapper; +import com.unissense.sip.service.SysDictDataService; +import org.springframework.stereotype.Service; + +import java.util.List; + +/** + * 字典数据Service实现类 + */ +@Service +public class SysDictDataServiceImpl extends ServiceImpl implements SysDictDataService { + + @Override + public List selectDictDataByType(String dictType) { + LambdaQueryWrapper wrapper = new LambdaQueryWrapper<>(); + wrapper.eq(SysDictData::getDictType, dictType) + .orderByAsc(SysDictData::getDictSort); + return list(wrapper); + } + + @Override + public String selectDictLabel(String dictType, String dictValue) { + LambdaQueryWrapper wrapper = new LambdaQueryWrapper<>(); + wrapper.eq(SysDictData::getDictType, dictType) + .eq(SysDictData::getDictValue, dictValue); + SysDictData dictData = getOne(wrapper); + return dictData != null ? dictData.getDictLabel() : ""; + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/impl/SysDictTypeServiceImpl.java b/src/main/java/com/unissense/sip/service/impl/SysDictTypeServiceImpl.java new file mode 100644 index 0000000..9a3b018 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/impl/SysDictTypeServiceImpl.java @@ -0,0 +1,22 @@ +package com.unissense.sip.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.unissense.sip.entity.SysDictType; +import com.unissense.sip.mapper.SysDictTypeMapper; +import com.unissense.sip.service.SysDictTypeService; +import org.springframework.stereotype.Service; + +/** + * 字典类型Service实现类 + */ +@Service +public class SysDictTypeServiceImpl extends ServiceImpl implements SysDictTypeService { + + @Override + public SysDictType selectDictTypeByType(String dictType) { + LambdaQueryWrapper wrapper = new LambdaQueryWrapper<>(); + wrapper.eq(SysDictType::getDictType, dictType); + return getOne(wrapper); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/impl/SysMenuServiceImpl.java b/src/main/java/com/unissense/sip/service/impl/SysMenuServiceImpl.java new file mode 100644 index 0000000..9cf5909 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/impl/SysMenuServiceImpl.java @@ -0,0 +1,36 @@ +package com.unissense.sip.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.unissense.sip.entity.SysMenu; +import com.unissense.sip.mapper.SysMenuMapper; +import com.unissense.sip.service.SysMenuService; +import org.springframework.stereotype.Service; + +import java.time.LocalDateTime; +import java.util.List; + +@Service +public class SysMenuServiceImpl extends ServiceImpl implements SysMenuService { + + @Override + public SysMenu getByMenuCode(String menuCode) { + return this.getOne(new LambdaQueryWrapper() + .eq(SysMenu::getMenuCode, menuCode) + .isNull(SysMenu::getDeleteAt)); + } + + @Override + public boolean createMenu(SysMenu menu) { + menu.setCreateAt(LocalDateTime.now()); + return this.save(menu); + } + + @Override + public List getChildrenMenus(Long parentId) { + return this.list(new LambdaQueryWrapper() + .eq(SysMenu::getParentId, parentId) + .isNull(SysMenu::getDeleteAt) + .orderByAsc(SysMenu::getOrderNum)); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/impl/SysRoleMenuServiceImpl.java b/src/main/java/com/unissense/sip/service/impl/SysRoleMenuServiceImpl.java new file mode 100644 index 0000000..e9bc1f3 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/impl/SysRoleMenuServiceImpl.java @@ -0,0 +1,51 @@ +package com.unissense.sip.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.unissense.sip.entity.SysRoleMenu; +import com.unissense.sip.mapper.SysRoleMenuMapper; +import com.unissense.sip.service.SysRoleMenuService; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Transactional; + +import java.util.ArrayList; +import java.util.List; +import java.util.stream.Collectors; + +@Service +public class SysRoleMenuServiceImpl extends ServiceImpl implements SysRoleMenuService { + + @Override + public List getMenuIdsByRoleId(Long roleId) { + return this.list(new LambdaQueryWrapper() + .eq(SysRoleMenu::getRoleId, roleId)) + .stream() + .map(SysRoleMenu::getMenuId) + .collect(Collectors.toList()); + } + + @Override + @Transactional(rollbackFor = Exception.class) + public boolean assignMenus(Long roleId, List menuIds) { + // 先删除原有的角色菜单关系 + this.removeRoleMenus(roleId); + + // 构建新的角色菜单关系 + List roleMenus = new ArrayList<>(); + for (Long menuId : menuIds) { + SysRoleMenu roleMenu = new SysRoleMenu(); + roleMenu.setRoleId(roleId); + roleMenu.setMenuId(menuId); + roleMenus.add(roleMenu); + } + + // 批量保存新的角色菜单关系 + return this.saveBatch(roleMenus); + } + + @Override + public boolean removeRoleMenus(Long roleId) { + return this.remove(new LambdaQueryWrapper() + .eq(SysRoleMenu::getRoleId, roleId)); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/impl/SysRoleServiceImpl.java b/src/main/java/com/unissense/sip/service/impl/SysRoleServiceImpl.java new file mode 100644 index 0000000..51a0334 --- /dev/null +++ b/src/main/java/com/unissense/sip/service/impl/SysRoleServiceImpl.java @@ -0,0 +1,20 @@ +package com.unissense.sip.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.unissense.sip.entity.SysRole; +import com.unissense.sip.mapper.SysRoleMapper; +import com.unissense.sip.service.SysRoleService; +import org.springframework.stereotype.Service; + +import java.time.LocalDateTime; + +@Service +public class SysRoleServiceImpl extends ServiceImpl implements SysRoleService { + + @Override + public boolean createRole(SysRole role) { + role.setCreateAt(LocalDateTime.now()); + return this.save(role); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/impl/SysUserRoleServiceImpl.java b/src/main/java/com/unissense/sip/service/impl/SysUserRoleServiceImpl.java new file mode 100644 index 0000000..d70bb7b --- /dev/null +++ b/src/main/java/com/unissense/sip/service/impl/SysUserRoleServiceImpl.java @@ -0,0 +1,97 @@ +package com.unissense.sip.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.unissense.sip.entity.SysUserRole; +import com.unissense.sip.entity.SysRole; +import com.unissense.sip.entity.SysMenu; +import com.unissense.sip.mapper.SysUserRoleMapper; +import com.unissense.sip.service.SysUserRoleService; +import com.unissense.sip.service.SysRoleService; +import com.unissense.sip.service.SysMenuService; +import com.unissense.sip.service.SysRoleMenuService; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; +import org.springframework.transaction.annotation.Transactional; + +import java.time.LocalDateTime; +import java.util.List; +import java.util.Collections; +import java.util.stream.Collectors; + +@Service +public class SysUserRoleServiceImpl extends ServiceImpl implements SysUserRoleService { + + @Autowired + private SysRoleService roleService; + + @Autowired + private SysMenuService menuService; + + @Autowired + private SysRoleMenuService roleMenuService; + + @Override + public List getRoleIdsByUserId(Long userId) { + List userRoles = this.list(new LambdaQueryWrapper() + .eq(SysUserRole::getUserId, userId)); + return userRoles.stream() + .map(SysUserRole::getRoleId) + .collect(Collectors.toList()); + } + + @Override + @Transactional + public boolean assignRoles(Long userId, List roleIds) { + // 先删除用户现有的角色 + this.removeUserRoles(userId); + + // 分配新的角色 + List userRoles = roleIds.stream().map(roleId -> { + SysUserRole userRole = new SysUserRole(); + userRole.setUserId(userId); + userRole.setRoleId(roleId); + return userRole; + }).collect(Collectors.toList()); + + return this.saveBatch(userRoles); + } + + @Override + public boolean removeUserRoles(Long userId) { + return this.remove(new LambdaQueryWrapper() + .eq(SysUserRole::getUserId, userId)); + } + + @Override + public List getRoleKeysByUserId(Long userId) { + List roleIds = this.getRoleIdsByUserId(userId); + if (roleIds.isEmpty()) { + return Collections.emptyList(); + } + return roleService.listByIds(roleIds).stream() + .map(SysRole::getRoleKey) + .collect(Collectors.toList()); + } + + @Override + public List getMenusByUserId(Long userId) { + List roleIds = this.getRoleIdsByUserId(userId); + if (roleIds.isEmpty()) { + return Collections.emptyList(); + } + + // 获取所有角色对应的菜单ID + List menuIds = roleIds.stream() + .flatMap(roleId -> roleMenuService.getMenuIdsByRoleId(roleId).stream()) + .distinct() + .collect(Collectors.toList()); + + if (menuIds.isEmpty()) { + return Collections.emptyList(); + } + + // 查询菜单列表 + return menuService.listByIds(menuIds); + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/service/impl/SysUserServiceImpl.java b/src/main/java/com/unissense/sip/service/impl/SysUserServiceImpl.java new file mode 100644 index 0000000..024429c --- /dev/null +++ b/src/main/java/com/unissense/sip/service/impl/SysUserServiceImpl.java @@ -0,0 +1,94 @@ +package com.unissense.sip.service.impl; + +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; +import com.unissense.sip.dto.LoginRequest; +import com.unissense.sip.dto.LoginResponse; +import com.unissense.sip.entity.SysMenu; +import com.unissense.sip.entity.SysUser; +import com.unissense.sip.mapper.SysUserMapper; +import com.unissense.sip.service.SysUserRoleService; +import com.unissense.sip.service.SysUserService; +import com.unissense.sip.utils.JwtUtils; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.data.redis.core.StringRedisTemplate; +import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; +import org.springframework.stereotype.Service; + +import java.time.LocalDateTime; +import java.util.List; + +@Service +public class SysUserServiceImpl extends ServiceImpl implements SysUserService { + @Override + public List getUserMenus(Long userId) { + return userRoleService.getMenusByUserId(userId); + } + + @Autowired + private BCryptPasswordEncoder passwordEncoder; + + @Autowired + private JwtUtils jwtUtils; + + @Autowired + private StringRedisTemplate redisTemplate; + + @Autowired + private SysUserRoleService userRoleService; + + @Override + public SysUser getByUsername(String username) { + return this.getOne(new LambdaQueryWrapper() + .eq(SysUser::getUsername, username) + .isNull(SysUser::getDeleteAt)); + } + + @Override + public boolean createUser(SysUser user) { + user.setCreateTime(LocalDateTime.now()); + user.setUpdateTime(LocalDateTime.now()); + user.setStatus(1); // 默认启用状态 + user.setPassword(passwordEncoder.encode(user.getPassword())); + return this.save(user); + } + + @Override + public LoginResponse login(LoginRequest loginRequest) { + // 验证验证码 + String captchaKey = "captcha:" + loginRequest.getUsername(); + String captcha = redisTemplate.opsForValue().get(captchaKey); + if (captcha == null || !captcha.equalsIgnoreCase(loginRequest.getCaptcha())) { + throw new RuntimeException("验证码错误或已过期"); + } + redisTemplate.delete(captchaKey); + + // 验证用户名和密码 + SysUser user = getByUsername(loginRequest.getUsername()); + if (user == null || !passwordEncoder.matches(loginRequest.getPassword(), user.getPassword())) { + throw new RuntimeException("用户名或密码错误"); + } + + // 生成token + String token = jwtUtils.generateToken(user.getUsername()); + + // 获取用户角色和菜单权限 + List roles = getUserRoles(user.getId()); + List menus = userRoleService.getMenusByUserId(user.getId()); + + // 构建响应 + LoginResponse response = new LoginResponse(); + response.setToken(token); + response.setUser(user); + response.setRoles(roles); + response.setMenus(menus); + + return response; + } + + @Override + public List getUserRoles(Long userId) { + return userRoleService.getRoleKeysByUserId(userId); + } + +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/utils/CaptchaUtils.java b/src/main/java/com/unissense/sip/utils/CaptchaUtils.java new file mode 100644 index 0000000..fda629e --- /dev/null +++ b/src/main/java/com/unissense/sip/utils/CaptchaUtils.java @@ -0,0 +1,43 @@ +package com.unissense.sip.utils; + +import java.awt.*; +import java.awt.image.BufferedImage; +import java.util.Random; + +public class CaptchaUtils { + private static final String CHARACTERS = "2345678abcdefhijkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVWXYZ"; + private static final int WIDTH = 90; + private static final int HEIGHT = 40; + private static final int LENGTH = 4; + private static final int LINES = 5; + + public static BufferedImage generateCaptchaImage(StringBuilder captcha) { + BufferedImage image = new BufferedImage(WIDTH, HEIGHT, BufferedImage.TYPE_INT_RGB); + Graphics2D g2d = image.createGraphics(); + + // 设置背景色 + g2d.setColor(Color.WHITE); + g2d.fillRect(0, 0, WIDTH, HEIGHT); + + // 生成随机字符 + Random random = new Random(); + g2d.setFont(new Font("Arial", Font.BOLD, 28)); + + for (int i = 0; i < LENGTH; i++) { + String ch = String.valueOf(CHARACTERS.charAt(random.nextInt(CHARACTERS.length()))); + captcha.append(ch); + g2d.setColor(new Color(random.nextInt(88), random.nextInt(188), random.nextInt(255))); + g2d.drawString(ch, (i * 20) + 10, 30); + } + + // 添加干扰线 + for (int i = 0; i < LINES; i++) { + g2d.setColor(new Color(random.nextInt(255), random.nextInt(255), random.nextInt(255))); + g2d.drawLine(random.nextInt(WIDTH), random.nextInt(HEIGHT), + random.nextInt(WIDTH), random.nextInt(HEIGHT)); + } + + g2d.dispose(); + return image; + } +} \ No newline at end of file diff --git a/src/main/java/com/unissense/sip/utils/JwtUtils.java b/src/main/java/com/unissense/sip/utils/JwtUtils.java new file mode 100644 index 0000000..509570e --- /dev/null +++ b/src/main/java/com/unissense/sip/utils/JwtUtils.java @@ -0,0 +1,49 @@ +package com.unissense.sip.utils; + +import io.jsonwebtoken.Claims; +import io.jsonwebtoken.Jwts; +import io.jsonwebtoken.SignatureAlgorithm; +import org.springframework.beans.factory.annotation.Value; +import org.springframework.stereotype.Component; + +import java.util.Date; + +@Component +public class JwtUtils { + + @Value("${jwt.secret}") + private String secret; + + @Value("${jwt.expiretime}") + private long expireTime; + + public String generateToken(String username) { + Date now = new Date(); + Date expiration = new Date(now.getTime() + expireTime * 1000); + + return Jwts.builder() + .setSubject(username) + .setIssuedAt(now) + .setExpiration(expiration) + .signWith(SignatureAlgorithm.HS256, secret) + .compact(); + } + + public String getUsernameFromToken(String token) { + Claims claims = Jwts.parser() + .setSigningKey(secret) + .parseClaimsJws(token) + .getBody(); + + return claims.getSubject(); + } + + public boolean validateToken(String token) { + try { + Jwts.parser().setSigningKey(secret).parseClaimsJws(token); + return true; + } catch (Exception e) { + return false; + } + } +} \ No newline at end of file diff --git a/src/main/resources/application.yml b/src/main/resources/application.yml new file mode 100644 index 0000000..cafc828 --- /dev/null +++ b/src/main/resources/application.yml @@ -0,0 +1,26 @@ +spring: + datasource: + url: jdbc:mysql://unis-sip-mysql.ns-dv9ov434.svc:3306/unis_sip?useSSL=false&serverTimezone=UTC + username: root + password: 5tzz94jd + driver-class-name: com.mysql.cj.jdbc.Driver + +# MyBatis Plus配置 +mybatis-plus: + mapper-locations: classpath*:/mapper/**/*.xml + type-aliases-package: com.unis.sip.entity + configuration: + map-underscore-to-camel-case: true + log-impl: org.apache.ibatis.logging.stdout.StdOutImpl + global-config: + db-config: + logic-delete-field: deleteAt + logic-delete-value: now() + logic-not-delete-value: null + +server: + port: 8080 + +jwt: + secret: unis-sip-secret-key + expiretime: 86400000 # 24 hours in milliseconds \ No newline at end of file diff --git a/target/classes/application.yml b/target/classes/application.yml new file mode 100644 index 0000000..cafc828 --- /dev/null +++ b/target/classes/application.yml @@ -0,0 +1,26 @@ +spring: + datasource: + url: jdbc:mysql://unis-sip-mysql.ns-dv9ov434.svc:3306/unis_sip?useSSL=false&serverTimezone=UTC + username: root + password: 5tzz94jd + driver-class-name: com.mysql.cj.jdbc.Driver + +# MyBatis Plus配置 +mybatis-plus: + mapper-locations: classpath*:/mapper/**/*.xml + type-aliases-package: com.unis.sip.entity + configuration: + map-underscore-to-camel-case: true + log-impl: org.apache.ibatis.logging.stdout.StdOutImpl + global-config: + db-config: + logic-delete-field: deleteAt + logic-delete-value: now() + logic-not-delete-value: null + +server: + port: 8080 + +jwt: + secret: unis-sip-secret-key + expiretime: 86400000 # 24 hours in milliseconds \ No newline at end of file diff --git a/target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst b/target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst new file mode 100644 index 0000000..dc378ac --- /dev/null +++ b/target/maven-status/maven-compiler-plugin/compile/default-compile/inputFiles.lst @@ -0,0 +1,45 @@ +/home/devbox/project/src/main/java/com/unissense/sip/service/SysDictDataService.java +/home/devbox/project/src/main/java/com/unissense/sip/service/impl/SysRoleServiceImpl.java +/home/devbox/project/src/main/java/com/unissense/sip/service/SysRoleService.java +/home/devbox/project/src/main/java/com/unissense/sip/controller/SysRoleController.java +/home/devbox/project/src/main/java/com/unissense/sip/controller/SysUserController.java +/home/devbox/project/src/main/java/com/unissense/sip/entity/SysRole.java +/home/devbox/project/src/main/java/com/unissense/sip/service/impl/SysDeptServiceImpl.java +/home/devbox/project/src/main/java/com/unissense/sip/UnisSipApplication.java +/home/devbox/project/src/main/java/com/unissense/sip/entity/SysUser.java +/home/devbox/project/src/main/java/com/unissense/sip/controller/SysUserRoleController.java +/home/devbox/project/src/main/java/com/unissense/sip/controller/AuthController.java +/home/devbox/project/src/main/java/com/unissense/sip/mapper/SysDeptMapper.java +/home/devbox/project/src/main/java/com/unissense/sip/dto/LoginRequest.java +/home/devbox/project/src/main/java/com/unissense/sip/controller/SysDictDataController.java +/home/devbox/project/src/main/java/com/unissense/sip/entity/SysUserRole.java +/home/devbox/project/src/main/java/com/unissense/sip/service/SysUserRoleService.java +/home/devbox/project/src/main/java/com/unissense/sip/service/impl/SysRoleMenuServiceImpl.java +/home/devbox/project/src/main/java/com/unissense/sip/utils/CaptchaUtils.java +/home/devbox/project/src/main/java/com/unissense/sip/service/impl/SysMenuServiceImpl.java +/home/devbox/project/src/main/java/com/unissense/sip/entity/SysDictType.java +/home/devbox/project/src/main/java/com/unissense/sip/mapper/SysRoleMenuMapper.java +/home/devbox/project/src/main/java/com/unissense/sip/mapper/SysMenuMapper.java +/home/devbox/project/src/main/java/com/unissense/sip/service/SysUserService.java +/home/devbox/project/src/main/java/com/unissense/sip/entity/SysDept.java +/home/devbox/project/src/main/java/com/unissense/sip/entity/SysDictData.java +/home/devbox/project/src/main/java/com/unissense/sip/controller/SysDeptController.java +/home/devbox/project/src/main/java/com/unissense/sip/mapper/SysDictTypeMapper.java +/home/devbox/project/src/main/java/com/unissense/sip/utils/JwtUtils.java +/home/devbox/project/src/main/java/com/unissense/sip/mapper/SysDictDataMapper.java +/home/devbox/project/src/main/java/com/unissense/sip/mapper/SysUserRoleMapper.java +/home/devbox/project/src/main/java/com/unissense/sip/service/impl/SysUserServiceImpl.java +/home/devbox/project/src/main/java/com/unissense/sip/entity/SysRoleMenu.java +/home/devbox/project/src/main/java/com/unissense/sip/controller/SysMenuController.java +/home/devbox/project/src/main/java/com/unissense/sip/service/impl/SysDictDataServiceImpl.java +/home/devbox/project/src/main/java/com/unissense/sip/mapper/SysRoleMapper.java +/home/devbox/project/src/main/java/com/unissense/sip/entity/SysMenu.java +/home/devbox/project/src/main/java/com/unissense/sip/controller/SysDictTypeController.java +/home/devbox/project/src/main/java/com/unissense/sip/dto/LoginResponse.java +/home/devbox/project/src/main/java/com/unissense/sip/service/SysDictTypeService.java +/home/devbox/project/src/main/java/com/unissense/sip/service/SysDeptService.java +/home/devbox/project/src/main/java/com/unissense/sip/service/SysRoleMenuService.java +/home/devbox/project/src/main/java/com/unissense/sip/service/impl/SysDictTypeServiceImpl.java +/home/devbox/project/src/main/java/com/unissense/sip/service/impl/SysUserRoleServiceImpl.java +/home/devbox/project/src/main/java/com/unissense/sip/service/SysMenuService.java +/home/devbox/project/src/main/java/com/unissense/sip/mapper/SysUserMapper.java diff --git a/template/index.html b/template/index.html new file mode 100644 index 0000000..fa65b71 --- /dev/null +++ b/template/index.html @@ -0,0 +1,228 @@ + + + + + + 售后服务平台 + + + + +
+
+
+ + +
+
+ +
+ +
+
+
+
+ + + + + + + \ No newline at end of file diff --git a/template/js/auth.js b/template/js/auth.js new file mode 100644 index 0000000..2f7f636 --- /dev/null +++ b/template/js/auth.js @@ -0,0 +1,94 @@ +// 登录和权限管理相关的JavaScript代码 +const auth = { + // 存储登录信息 + setLoginInfo(loginResponse) { + localStorage.setItem('token', loginResponse.token); + localStorage.setItem('user', JSON.stringify(loginResponse.user)); + localStorage.setItem('roles', JSON.stringify(loginResponse.roles)); + localStorage.setItem('menus', JSON.stringify(loginResponse.menus)); + }, + + // 清除登录信息 + clearLoginInfo() { + localStorage.removeItem('token'); + localStorage.removeItem('user'); + localStorage.removeItem('roles'); + localStorage.removeItem('menus'); + }, + + // 获取用户信息 + getUser() { + const userStr = localStorage.getItem('user'); + return userStr ? JSON.parse(userStr) : null; + }, + + // 获取用户角色 + getRoles() { + const rolesStr = localStorage.getItem('roles'); + return rolesStr ? JSON.parse(rolesStr) : []; + }, + + // 获取用户菜单 + getMenus() { + const menusStr = localStorage.getItem('menus'); + return menusStr ? JSON.parse(menusStr) : []; + }, + + // 生成菜单树 + generateMenuTree(menus) { + const menuMap = {}; + const menuTree = []; + + // 创建菜单映射 + menus.forEach(menu => { + menuMap[menu.menuId] = { + ...menu, + children: [] + }; + }); + + // 构建菜单树 + menus.forEach(menu => { + const menuItem = menuMap[menu.menuId]; + if (menu.parentId === 0) { + menuTree.push(menuItem); + } else { + const parentMenu = menuMap[menu.parentId]; + if (parentMenu) { + parentMenu.children.push(menuItem); + } + } + }); + + return menuTree; + }, + + // 渲染菜单 + renderMenu(menuTree) { + const menuHtml = menuTree.map(menu => { + if (menu.children && menu.children.length > 0) { + return ` + + + ${this.renderMenu(menu.children)} + + `; + } else { + return ` + + + ${menu.menuName} + + `; + } + }).join(''); + + return menuHtml; + } +}; + +// 导出auth对象 +export default auth; \ No newline at end of file diff --git a/template/login.html b/template/login.html new file mode 100644 index 0000000..d5f21be --- /dev/null +++ b/template/login.html @@ -0,0 +1,136 @@ + + + + + + 登录 - 售后服务平台 + + + + +
+ +
+ + + + + + + \ No newline at end of file