Files
UserbaseService/sql/20261021_create_ub_custom_department_tables.sql
chenx b1b769a1b8
build / build-push (push) Successful in 59s
feat(dept): CUSTOM 自定义部门与统一部门目录契约(双来源部门二期)
- 三表 ub_custom_dept_category/ub_custom_department/ub_custom_department_member(DDL 入 service/sql,160 待人工执行)
- 实体/仓库/服务:学校隔离(AccessScopeService 新增 requireSchoolInScope/resolveWritableSchoolId)、
  del_marker=id 软删让位 uk、成员=本校教职工黑名单口径(排除学生组 type=8 与禁用账号)
- 管理端 /api/deptcategory、/api/customdept 共 17 端点(含 CandidateUsers 候选口)
- 开放端 /oapi/departments 四口:目录/分类/resolve-batch/成员(scope 缺省=select 严档),
  应用×学校授权走 sys_group_app_rel(仅验签不放行跨校)
- SysGroupService.changeIncludeChildren 补学校组类型校验
- 新增单测 83 例全绿(部门26/分类12/目录25/schoolguard12/includeChildren8)
2026-10-22 09:35:37 +08:00

103 lines
7.9 KiB
SQL
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
-- =====================================================================
-- UserBase 双来源部门 · CUSTOM 侧建表(任务书 USERBASE_DEPARTMENT_QODER_TASK.md T1 / 规格书 UB-1)
-- 三张新表:ub_custom_dept_category(自定义分类)/ ub_custom_department(自定义部门)
-- / ub_custom_department_member(部门成员关系)
-- 交付文件,不在本机执行;由人工在 160 执行
-- 执行前请备份;JPA 实体与列同名映射,执行后重启后端即可生效
-- ⚠ application.yml 是 ddl-auto=update,后端先发也会自动建表,但**不带** NOT NULL/DEFAULT/COMMENT/唯一键,
-- 且 del_marker 之类参与唯一约束的列必须由本脚本定义,故务必先执行本脚本
-- 口径:school_id = sys_group 中 type=2(学校组)节点的 id,与 AccessScopeService.scopeGroupIds() 同域
-- =====================================================================
-- ---------------------------------------------------------------------------
-- 1. 自定义分类(学校的容器层,本身无启停、无成员)
-- 名称唯一:del_marker 技巧——MySQL 的 uk 对 NULL 不去重,deleted_at 进 uk 挡不住「软删后再激活同名」,
-- 故软删时把 del_marker 置为该行 id,未删行恒为 0,同校同名只能有一条**有效**行;
-- name 列永不改写(软删保留原名,保证历史解析拿到原名、旧引用不指向新对象)
-- ---------------------------------------------------------------------------
CREATE TABLE IF NOT EXISTS ub_custom_dept_category (
id INT NOT NULL AUTO_INCREMENT COMMENT '主键(不可变稳定 ID)',
school_id INT NOT NULL COMMENT '学校组 id(sys_group.type=2 的节点 id)',
name VARCHAR(64) NOT NULL COMMENT '分类名称,学校自定;永不改写',
sort_no INT NOT NULL DEFAULT 0 COMMENT '展示顺序,越小越靠前',
is_deleted TINYINT(1) NOT NULL DEFAULT 0 COMMENT '软删标记:0=有效 / 1=已软删(不是业务状态)',
del_marker BIGINT NOT NULL DEFAULT 0 COMMENT '软删时置为该行 id;参与唯一键,保证同名只挡有效行',
deleted_at DATETIME NULL COMMENT '软删时间',
deleted_by INT NULL COMMENT '软删操作人 sys_user.id',
create_user INT NOT NULL COMMENT '创建人 sys_user.id(BaseEntity)',
create_time DATETIME NOT NULL COMMENT '创建时间(BaseEntity)',
update_user INT NULL COMMENT '修改人 sys_user.id(BaseEntity)',
update_time DATETIME NULL COMMENT '修改时间(BaseEntity)',
PRIMARY KEY (id),
UNIQUE KEY uk_school_name_marker (school_id, name, del_marker),
KEY idx_school_sort (school_id, is_deleted, sort_no)
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 COMMENT = '自定义部门分类(学校级容器,非可选部门)';
-- ---------------------------------------------------------------------------
-- 2. 自定义部门(可配成员、可启停的实际可选对象)
-- 唯一键=同校同分类下未软删的部门名不重复;跨分类、SYSTEM 与 CUSTOM 之间允许重名(A06)
-- enabled 语义直读 1=启用/0=停用,**与 sys_group.status(0=启用/1=停用)方向相反,严禁混用**
-- 软删不级联删成员:成员关系保留在库,由查询侧按部门 is_deleted 过滤(A12)
-- ---------------------------------------------------------------------------
CREATE TABLE IF NOT EXISTS ub_custom_department (
id INT NOT NULL AUTO_INCREMENT COMMENT '主键(CUSTOM 侧独立 ID,与 SYSTEM 组 id 不同域,引用须带 departmentType)',
school_id INT NOT NULL COMMENT '学校组 id(冗余自分类,写口服务端复核)',
category_id INT NOT NULL COMMENT '所属分类 ub_custom_dept_category.id,必须同校',
name VARCHAR(64) NOT NULL COMMENT '部门名称,学校自定;永不改写',
sort_no INT NOT NULL DEFAULT 0 COMMENT '同分类内展示顺序,越小越靠前',
enabled TINYINT(1) NOT NULL DEFAULT 1 COMMENT '启停:1=启用 / 0=停用(新建默认启用)',
is_deleted TINYINT(1) NOT NULL DEFAULT 0 COMMENT '软删标记:0=有效 / 1=已软删(删除不是第三种业务状态)',
del_marker BIGINT NOT NULL DEFAULT 0 COMMENT '软删时置为该行 id;参与唯一键',
deleted_at DATETIME NULL COMMENT '软删时间',
deleted_by INT NULL COMMENT '软删操作人 sys_user.id',
create_user INT NOT NULL COMMENT '创建人 sys_user.id(BaseEntity)',
create_time DATETIME NOT NULL COMMENT '创建时间(BaseEntity)',
update_user INT NULL COMMENT '修改人 sys_user.id(BaseEntity)',
update_time DATETIME NULL COMMENT '修改时间(BaseEntity)',
PRIMARY KEY (id),
UNIQUE KEY uk_school_category_name_marker (school_id, category_id, name, del_marker),
KEY idx_category_list (category_id, is_deleted, sort_no),
KEY idx_school_list (school_id, is_deleted, enabled)
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 COMMENT = '学校自定义部门(与 SYSTEM 组织树完全分离)';
-- ---------------------------------------------------------------------------
-- 3. 自定义部门成员关系(引用 sys_user.id,不复制账号)
-- 移除成员=物理删该关系行(本仓无软删惯例,增删审计靠 @OperationLog),不得残留有效成员
-- uk 挡不住并发重复插入之外的场景(如软删部门后重新激活)由服务端逐个复核兜底
-- ---------------------------------------------------------------------------
CREATE TABLE IF NOT EXISTS ub_custom_department_member (
id INT NOT NULL AUTO_INCREMENT COMMENT '主键',
school_id INT NOT NULL COMMENT '学校组 id(与部门同校,写口服务端复核)',
department_id INT NOT NULL COMMENT 'ub_custom_department.id',
user_id INT NOT NULL COMMENT 'sys_user.id(本校教职工,排除学生组成员)',
create_user INT NOT NULL COMMENT '添加人 sys_user.id(BaseEntity)',
create_time DATETIME NOT NULL COMMENT '添加时间(BaseEntity)',
update_user INT NULL COMMENT '修改人 sys_user.id(BaseEntity)',
update_time DATETIME NULL COMMENT '修改时间(BaseEntity)',
PRIMARY KEY (id),
UNIQUE KEY uk_department_user (department_id, user_id),
KEY idx_department (department_id),
KEY idx_school (school_id),
KEY idx_user (user_id)
) ENGINE = InnoDB DEFAULT CHARSET = utf8mb4 COMMENT = '自定义部门成员关系(一个用户可属同校多个部门)';
-- ---------------------------------------------------------------------------
-- 4. 核验(可选,执行后逐条确认)
-- ---------------------------------------------------------------------------
-- SHOW CREATE TABLE ub_custom_dept_category;
-- SHOW CREATE TABLE ub_custom_department;
-- SHOW CREATE TABLE ub_custom_department_member;
-- SELECT TABLE_NAME, TABLE_COMMENT FROM information_schema.TABLES
-- WHERE TABLE_SCHEMA = DATABASE() AND TABLE_NAME LIKE 'ub_custom%';
-- 唯一键生效自检(手工插入应报 1062):
-- INSERT INTO ub_custom_dept_category (school_id, name, create_user, create_time) VALUES (1, '自检分类', 0, NOW());
-- INSERT INTO ub_custom_dept_category (school_id, name, create_user, create_time) VALUES (1, '自检分类', 0, NOW()); -- 期望失败
-- DELETE FROM ub_custom_dept_category WHERE school_id = 1 AND name = '自检分类';
-- ---------------------------------------------------------------------------
-- 回滚(本期未上线,回滚即删表;CUSTOM 数据不与 sys_group 有任何写耦合)
-- ---------------------------------------------------------------------------
-- DROP TABLE IF EXISTS ub_custom_department_member;
-- DROP TABLE IF EXISTS ub_custom_department;
-- DROP TABLE IF EXISTS ub_custom_dept_category;