From 1c0304091d5a7dd05859167f5e417cf932c67028 Mon Sep 17 00:00:00 2001
From: 刘光辉 <347230014@qq.com>
Date: 星期四, 17 九月 2026 11:19:17 +0800
Subject: [PATCH] 字段信息基础班
---
docs/tms/tms_schema_pg.sql | 2171 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 2,171 insertions(+), 0 deletions(-)
diff --git a/docs/tms/tms_schema_pg.sql b/docs/tms/tms_schema_pg.sql
new file mode 100644
index 0000000..d122c8a
--- /dev/null
+++ b/docs/tms/tms_schema_pg.sql
@@ -0,0 +1,2171 @@
+-- =============================================================================
+-- 鐜绘�濋煬 TMS 鍩硅绠$悊绯荤粺 路 PostgreSQL 18 寤鸿〃鑴氭湰
+-- 閫傜敤锛欽NPF 6.x锛堝瓧娈甸鏍煎榻愮幇鏈� lims_/dms_ 琛級
+-- 鏉ユ簮锛氱幓鎬濋煬TMS鍔熻兘璁捐涔� V1 + 鑰侀浼佺晫闈㈠瓧娈�
+--
+-- 浣跨敤
+-- 1) 鎺ㄨ崘锛欽NPF銆屾暟鎹缓妯°�嶆寜琛ㄦ竻鍗曞缓琛紝鍐嶇粦琛ㄥ崟锛堢郴缁熷瓧娈典細鑷姩甯︼級
+-- 2) 鎴栧厛鎵ц鏈剼鏈紝鍐嶅埌鏁版嵁寤烘ā銆屽悓姝ユ暟鎹〃銆�
+--
+-- 绾﹀畾
+-- f_id 涓婚敭 varchar(50)锛涘瓙琛� f_foreign_id = 涓昏〃 f_id
+-- 娴佺▼琛ㄥ崟鍚� f_flow_id / f_flow_task_id / f_flow_state
+-- 鐢ㄦ埛/缁勭粐/宀椾綅瀛� JNPF ID锛涘閫� text锛涢檮浠� text(JSON)
+-- 涓氬姟鐘舵�佸瓨缂栫爜锛岄�夐」鐢� JNPF 瀛楀吀
+-- =============================================================================
+
+BEGIN;
+
+-- ---------------------------------------------------------------------------
+-- 1. 鍩虹璁剧疆
+-- ---------------------------------------------------------------------------
+-- 鍩硅鍦扮偣銆傚湪绾垮涔犱换鍔″湴鐐瑰彲绌猴紱鍗犵敤鎸夊皬鏃朵笌鏈彇娑堜换鍔℃椂闂翠氦鍙夋牎楠屻��
+CREATE TABLE IF NOT EXISTS tms_place (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ place_no varchar(50) NOT NULL,
+ place_name varchar(200) NOT NULL,
+ place_group varchar(50),
+ enabled varchar(20) NOT NULL DEFAULT '1',
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_place PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_place IS '鍩硅鍦扮偣銆傚湪绾垮涔犱换鍔″湴鐐瑰彲绌猴紱鍗犵敤鎸夊皬鏃朵笌鏈彇娑堜换鍔℃椂闂翠氦鍙夋牎楠屻��';
+COMMENT ON COLUMN tms_place.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_place.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_place.place_no IS '鍦扮偣缂栧彿锛屽崟鎹鍒� A+YYYYMM+4锛屽 A2026090001';
+COMMENT ON COLUMN tms_place.place_name IS '鍦扮偣鍚嶇О';
+COMMENT ON COLUMN tms_place.place_group IS '缁勫埆/鍒嗗尯锛屽瓧鍏革細鍔炲叕鍖�/鐢熶骇鍖�/A鍖�/B鍖�';
+COMMENT ON COLUMN tms_place.enabled IS '1鍚敤 0鍋滅敤';
+COMMENT ON COLUMN tms_place.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_place.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_place.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_place.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_place.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_place.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_place.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_place.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_place_no ON tms_place (place_no) WHERE f_delete_mark = 0;
+CREATE INDEX IF NOT EXISTS idx_tms_place_group ON tms_place (place_group, enabled);
+
+-- 鍩硅甯堟。妗堬紝鍏宠仈绯荤粺鐢ㄦ埛锛涢噸澶嶅綍鍏ユ寜user_id璇嗗埆锛涜处鍙锋敞閿�鍚庤嚜鍔ㄥ簾寮冦��
+CREATE TABLE IF NOT EXISTS tms_trainer (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ archive_no varchar(50),
+ user_id varchar(50) NOT NULL,
+ trainer_name varchar(100),
+ dept_id varchar(50),
+ post_id varchar(50),
+ school varchar(200),
+ education varchar(50),
+ major varchar(100),
+ tech_title varchar(100),
+ hire_date date,
+ license varchar(200),
+ work_years varchar(50),
+ trainer_level varchar(50),
+ biz_status varchar(20) NOT NULL DEFAULT 'valid',
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_trainer PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_trainer IS '鍩硅甯堟。妗堬紝鍏宠仈绯荤粺鐢ㄦ埛锛涢噸澶嶅綍鍏ユ寜user_id璇嗗埆锛涜处鍙锋敞閿�鍚庤嚜鍔ㄥ簾寮冦��';
+COMMENT ON COLUMN tms_trainer.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_trainer.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_trainer.archive_no IS '妗f缂栧彿 AR+YYYY+4锛屽彲涓庝釜浜哄煿璁。妗堝叡鐢�';
+COMMENT ON COLUMN tms_trainer.user_id IS '绯荤粺鐢ㄦ埛ID';
+COMMENT ON COLUMN tms_trainer.trainer_name IS '濮撳悕锛堝啑浣欙紝渚夸簬鍒楄〃锛�';
+COMMENT ON COLUMN tms_trainer.dept_id IS '閮ㄩ棬';
+COMMENT ON COLUMN tms_trainer.post_id IS '宀椾綅';
+COMMENT ON COLUMN tms_trainer.school IS '姣曚笟闄㈡牎';
+COMMENT ON COLUMN tms_trainer.education IS '瀛﹀巻';
+COMMENT ON COLUMN tms_trainer.major IS '涓撲笟';
+COMMENT ON COLUMN tms_trainer.tech_title IS '鎶�鏈亴绉�';
+COMMENT ON COLUMN tms_trainer.hire_date IS '鍏ヨ亴鏃堕棿';
+COMMENT ON COLUMN tms_trainer.license IS '鎵т笟璇佷功';
+COMMENT ON COLUMN tms_trainer.work_years IS '宸ヤ綔骞撮檺';
+COMMENT ON COLUMN tms_trainer.trainer_level IS '鍩硅甯堢骇鍒�';
+COMMENT ON COLUMN tms_trainer.biz_status IS 'valid鏈夋晥鏈熷唴 / revoked宸叉挙閿�';
+COMMENT ON COLUMN tms_trainer.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_trainer.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_trainer.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_trainer.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_trainer.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_trainer.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_trainer.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_trainer.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_trainer_user ON tms_trainer (user_id) WHERE f_delete_mark = 0;
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_trainer_no ON tms_trainer (archive_no) WHERE f_delete_mark = 0;
+CREATE INDEX IF NOT EXISTS idx_tms_trainer_status ON tms_trainer (biz_status);
+
+-- 鍩硅甯堜釜浜哄伐浣滅粡鍘嗗瓙琛�
+CREATE TABLE IF NOT EXISTS tms_trainer_work (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ sort_no int,
+ hire_date date,
+ leave_date date,
+ company_name varchar(200),
+ post_name varchar(100),
+ leave_reason varchar(200),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_trainer_work PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_trainer_work IS '鍩硅甯堜釜浜哄伐浣滅粡鍘嗗瓙琛�';
+COMMENT ON COLUMN tms_trainer_work.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_trainer_work.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_trainer_work.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_trainer_work.sort_no IS '搴忓彿';
+COMMENT ON COLUMN tms_trainer_work.hire_date IS '鍏ヨ亴鏃堕棿';
+COMMENT ON COLUMN tms_trainer_work.leave_date IS '绂昏亴鏃堕棿';
+COMMENT ON COLUMN tms_trainer_work.company_name IS '鍏徃鍚嶇О';
+COMMENT ON COLUMN tms_trainer_work.post_name IS '浠昏亴宀椾綅';
+COMMENT ON COLUMN tms_trainer_work.leave_reason IS '绂昏亴鍘熷洜';
+COMMENT ON COLUMN tms_trainer_work.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_trainer_work.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_trainer_work.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_trainer_work.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_trainer_work.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_trainer_work_fid ON tms_trainer_work (f_foreign_id);
+
+-- 鍩硅甯堜釜浜哄煿璁粡鍘嗗瓙琛�
+CREATE TABLE IF NOT EXISTS tms_trainer_exp (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ sort_no int,
+ train_date date,
+ org_name varchar(200),
+ cert_name varchar(200),
+ cert_file text,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_trainer_exp PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_trainer_exp IS '鍩硅甯堜釜浜哄煿璁粡鍘嗗瓙琛�';
+COMMENT ON COLUMN tms_trainer_exp.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_trainer_exp.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_trainer_exp.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_trainer_exp.sort_no IS '搴忓彿';
+COMMENT ON COLUMN tms_trainer_exp.train_date IS '鍩硅鏃堕棿';
+COMMENT ON COLUMN tms_trainer_exp.org_name IS '鍩硅鏈烘瀯';
+COMMENT ON COLUMN tms_trainer_exp.cert_name IS '鍩硅璇佷功';
+COMMENT ON COLUMN tms_trainer_exp.cert_file IS '璇佷功闄勪欢';
+COMMENT ON COLUMN tms_trainer_exp.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_trainer_exp.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_trainer_exp.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_trainer_exp.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_trainer_exp.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_trainer_exp_fid ON tms_trainer_exp (f_foreign_id);
+
+-- 鍩硅绠$悊鍛樿法閮ㄩ棬鎺堟潈銆傚埌鏈熷墠涓�涓湀鎻愰啋绠$悊鍛�/鍩硅甯堛��
+CREATE TABLE IF NOT EXISTS tms_admin_auth (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ admin_user_id varchar(50) NOT NULL,
+ scope_dept_id text NOT NULL,
+ include_child varchar(10) NOT NULL DEFAULT '1',
+ registrar_id varchar(50),
+ register_date date,
+ expire_date date,
+ biz_status varchar(20) NOT NULL DEFAULT 'valid',
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_admin_auth PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_admin_auth IS '鍩硅绠$悊鍛樿法閮ㄩ棬鎺堟潈銆傚埌鏈熷墠涓�涓湀鎻愰啋绠$悊鍛�/鍩硅甯堛��';
+COMMENT ON COLUMN tms_admin_auth.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_admin_auth.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_admin_auth.admin_user_id IS '鍩硅绠$悊鍛�';
+COMMENT ON COLUMN tms_admin_auth.scope_dept_id IS '绠$悊鑼冨洿锛岀粍缁囧閫�';
+COMMENT ON COLUMN tms_admin_auth.include_child IS '鏄惁鍖呭惈涓嬬骇閮ㄩ棬 1鏄� 0鍚�';
+COMMENT ON COLUMN tms_admin_auth.registrar_id IS '鐧昏浜�';
+COMMENT ON COLUMN tms_admin_auth.register_date IS '鐧昏鏃ユ湡';
+COMMENT ON COLUMN tms_admin_auth.expire_date IS '鎺堟潈鍒版湡鏃ワ紝鍙┖琛ㄧず闀挎湡';
+COMMENT ON COLUMN tms_admin_auth.biz_status IS 'valid鏈夋晥 / revoked搴熷純';
+COMMENT ON COLUMN tms_admin_auth.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_admin_auth.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_admin_auth.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_admin_auth.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_admin_auth.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_admin_auth.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_admin_auth.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_admin_auth.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_admin_auth_user ON tms_admin_auth (admin_user_id, biz_status);
+
+-- 鍩硅鏂瑰紡閰嶇疆锛堝惈绛惧埌瑙勫垯锛屼笉浠呮槸瀛楀吀锛�
+CREATE TABLE IF NOT EXISTS tms_train_mode (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ mode_code varchar(50) NOT NULL,
+ mode_name varchar(100) NOT NULL,
+ sign_rule varchar(20) NOT NULL DEFAULT 'both',
+ allow_guest_sign varchar(10) NOT NULL DEFAULT '0',
+ same_day_required varchar(10) NOT NULL DEFAULT '0',
+ place_required varchar(10) NOT NULL DEFAULT '1',
+ sort_no int,
+ enabled varchar(10) NOT NULL DEFAULT '1',
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_train_mode PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_train_mode IS '鍩硅鏂瑰紡閰嶇疆锛堝惈绛惧埌瑙勫垯锛屼笉浠呮槸瀛楀吀锛�';
+COMMENT ON COLUMN tms_train_mode.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_train_mode.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_train_mode.mode_code IS '缂栫爜锛歰nsite/practice/online';
+COMMENT ON COLUMN tms_train_mode.mode_name IS '鍚嶇О锛氶泦涓巿璇�/鎿嶄綔鎺堣/鍦ㄧ嚎瀛︿範';
+COMMENT ON COLUMN tms_train_mode.sign_rule IS 'scan浠呮壂鐮� / both鎵爜+鍦ㄧ嚎';
+COMMENT ON COLUMN tms_train_mode.allow_guest_sign IS '鍏佽鍚嶅崟澶栫鍒帮紝闆嗕腑鎺堣=1';
+COMMENT ON COLUMN tms_train_mode.same_day_required IS '寮�濮嬬粨鏉熷繀椤诲悓涓�澶╋紝闆嗕腑/鎿嶄綔=1';
+COMMENT ON COLUMN tms_train_mode.place_required IS '鍦扮偣蹇呭~锛屽湪绾垮涔�=0';
+COMMENT ON COLUMN tms_train_mode.sort_no IS '鎺掑簭';
+COMMENT ON COLUMN tms_train_mode.enabled IS '鍚敤';
+COMMENT ON COLUMN tms_train_mode.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_train_mode.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_train_mode.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_train_mode.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_train_mode.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_train_mode.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_train_mode.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_train_mode.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_train_mode_code ON tms_train_mode (mode_code) WHERE f_delete_mark = 0;
+
+-- 绛惧埌鏂瑰紡锛欰PP鎵爜 / 寰俊鎵爜 / 鍦ㄧ嚎绛惧埌
+CREATE TABLE IF NOT EXISTS tms_sign_mode (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ mode_code varchar(50) NOT NULL,
+ mode_name varchar(100) NOT NULL,
+ tip_seconds int NOT NULL DEFAULT 30,
+ match_roster varchar(10) NOT NULL DEFAULT '1',
+ enabled varchar(10) NOT NULL DEFAULT '1',
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_sign_mode PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_sign_mode IS '绛惧埌鏂瑰紡锛欰PP鎵爜 / 寰俊鎵爜 / 鍦ㄧ嚎绛惧埌';
+COMMENT ON COLUMN tms_sign_mode.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_sign_mode.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_sign_mode.mode_code IS '缂栫爜锛歛pp_scan/wx_scan/online';
+COMMENT ON COLUMN tms_sign_mode.mode_name IS '鍚嶇О';
+COMMENT ON COLUMN tms_sign_mode.tip_seconds IS '鏈夊煿璁鐐规椂寮哄埗闃呰绉掓暟锛孖T鍙皟';
+COMMENT ON COLUMN tms_sign_mode.match_roster IS '鏄惁蹇呴』鍖归厤鍩硅瀵硅薄鍚嶅崟';
+COMMENT ON COLUMN tms_sign_mode.enabled IS '鍚敤';
+COMMENT ON COLUMN tms_sign_mode.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_sign_mode.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_sign_mode.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_sign_mode.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_sign_mode.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_sign_mode.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_sign_mode.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_sign_mode.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_sign_mode_code ON tms_sign_mode (mode_code) WHERE f_delete_mark = 0;
+
+-- 鍩硅鏁堟灉璇勪及鏂瑰紡锛氭彁闂� / 鐜板満鎿嶄綔 / 鍦ㄧ嚎鑰冭瘯 / 鏃犻渶鑰冩牳
+CREATE TABLE IF NOT EXISTS tms_eval_mode (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ mode_code varchar(50) NOT NULL,
+ mode_name varchar(100) NOT NULL,
+ need_paper varchar(10) NOT NULL DEFAULT '0',
+ need_quiz varchar(10) NOT NULL DEFAULT '0',
+ need_practice varchar(10) NOT NULL DEFAULT '0',
+ enabled varchar(10) NOT NULL DEFAULT '1',
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_eval_mode PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_eval_mode IS '鍩硅鏁堟灉璇勪及鏂瑰紡锛氭彁闂� / 鐜板満鎿嶄綔 / 鍦ㄧ嚎鑰冭瘯 / 鏃犻渶鑰冩牳';
+COMMENT ON COLUMN tms_eval_mode.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_eval_mode.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_eval_mode.mode_code IS '缂栫爜锛歲uiz/practice/exam/none';
+COMMENT ON COLUMN tms_eval_mode.mode_name IS '鍚嶇О';
+COMMENT ON COLUMN tms_eval_mode.need_paper IS '鏄惁闇�瑕佽瘯鍗�';
+COMMENT ON COLUMN tms_eval_mode.need_quiz IS '鏄惁闇�瑕佹彁闂璁�';
+COMMENT ON COLUMN tms_eval_mode.need_practice IS '鏄惁闇�瑕佸疄鎿嶈瘎鍒�';
+COMMENT ON COLUMN tms_eval_mode.enabled IS '鍚敤';
+COMMENT ON COLUMN tms_eval_mode.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_eval_mode.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_eval_mode.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_eval_mode.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_eval_mode.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_eval_mode.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_eval_mode.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_eval_mode.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_eval_mode_code ON tms_eval_mode (mode_code) WHERE f_delete_mark = 0;
+
+-- 鍩硅璇剧▼涓绘暟鎹紝璁″垝/浠诲姟鍙紩鐢�
+CREATE TABLE IF NOT EXISTS tms_course (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ course_no varchar(50),
+ course_name varchar(200) NOT NULL,
+ category varchar(50),
+ train_mode varchar(50),
+ eval_mode varchar(50),
+ paper_id varchar(50),
+ hours numeric(8,1),
+ enabled varchar(10) NOT NULL DEFAULT '1',
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_course PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_course IS '鍩硅璇剧▼涓绘暟鎹紝璁″垝/浠诲姟鍙紩鐢�';
+COMMENT ON COLUMN tms_course.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_course.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_course.course_no IS '璇剧▼缂栧彿';
+COMMENT ON COLUMN tms_course.course_name IS '璇剧▼鍚嶇О';
+COMMENT ON COLUMN tms_course.category IS '璇剧▼鍒嗙被';
+COMMENT ON COLUMN tms_course.train_mode IS '鍩硅鏂瑰紡缂栫爜';
+COMMENT ON COLUMN tms_course.eval_mode IS '鑰冩牳鏂瑰紡缂栫爜';
+COMMENT ON COLUMN tms_course.paper_id IS '鍏宠仈璇曞嵎';
+COMMENT ON COLUMN tms_course.hours IS '瀛︽椂';
+COMMENT ON COLUMN tms_course.enabled IS '鍚敤';
+COMMENT ON COLUMN tms_course.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_course.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_course.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_course.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_course.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_course.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_course.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_course.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_course_no ON tms_course (course_no) WHERE f_delete_mark = 0;
+
+-- 鍩硅鏁欐潗/浼佷笟鐭ヨ瘑搴撱�傚彲涓婁紶鏈湴鎴栧紩鐢―MS锛堥渶閴存潈锛夈�傛挙閿�鍚庝笉鍙啀寮曠敤銆�
+CREATE TABLE IF NOT EXISTS tms_material (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ material_no varchar(50) NOT NULL,
+ material_name varchar(500) NOT NULL,
+ file_type varchar(50),
+ apply_time date,
+ applicant_id varchar(50),
+ apply_dept_id varchar(50),
+ file_json text,
+ dms_file_id varchar(50),
+ quote_count int NOT NULL DEFAULT 0,
+ biz_status varchar(20) NOT NULL DEFAULT 'valid',
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_material PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_material IS '鍩硅鏁欐潗/浼佷笟鐭ヨ瘑搴撱�傚彲涓婁紶鏈湴鎴栧紩鐢―MS锛堥渶閴存潈锛夈�傛挙閿�鍚庝笉鍙啀寮曠敤銆�';
+COMMENT ON COLUMN tms_material.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_material.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_material.material_no IS '鏁欐潗缂栧彿 TM+YYYYMM+4';
+COMMENT ON COLUMN tms_material.material_name IS '鏁欐潗鍚嶇О';
+COMMENT ON COLUMN tms_material.file_type IS 'Word/PPT/Excel/PDF/瑙嗛/闊抽';
+COMMENT ON COLUMN tms_material.apply_time IS '鐢宠鏃堕棿';
+COMMENT ON COLUMN tms_material.applicant_id IS '涓婁紶鐢宠浜�';
+COMMENT ON COLUMN tms_material.apply_dept_id IS '鐢宠浜洪儴闂�';
+COMMENT ON COLUMN tms_material.file_json IS '鏁欐潗闄勪欢锛圝NPF闄勪欢JSON锛�';
+COMMENT ON COLUMN tms_material.dms_file_id IS '寮曠敤鐨凞MS鏂囦欢ID';
+COMMENT ON COLUMN tms_material.quote_count IS '琚换鍔″紩鐢ㄦ鏁�';
+COMMENT ON COLUMN tms_material.biz_status IS 'valid鏈夋晥 / revoked宸叉挙閿�';
+COMMENT ON COLUMN tms_material.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_material.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_material.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_material.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_material.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_material.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_material.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_material.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_material_no ON tms_material (material_no) WHERE f_delete_mark = 0;
+CREATE INDEX IF NOT EXISTS idx_tms_material_type ON tms_material (file_type, biz_status);
+
+-- ---------------------------------------------------------------------------
+-- 2. 棰樺簱璇曞嵎
+-- ---------------------------------------------------------------------------
+-- 棰樺簱
+CREATE TABLE IF NOT EXISTS tms_question_bank (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ bank_name varchar(200) NOT NULL,
+ question_count int NOT NULL DEFAULT 0,
+ biz_status varchar(20) NOT NULL DEFAULT 'normal',
+ remark text,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_question_bank PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_question_bank IS '棰樺簱';
+COMMENT ON COLUMN tms_question_bank.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_question_bank.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_question_bank.bank_name IS '棰樺簱鍚嶇О';
+COMMENT ON COLUMN tms_question_bank.question_count IS '璇曢鏁伴噺锛堢淮鎶ゆ椂鍥炲啓锛�';
+COMMENT ON COLUMN tms_question_bank.biz_status IS 'normal姝e父 / invalid澶辨晥';
+COMMENT ON COLUMN tms_question_bank.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_question_bank.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_question_bank.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_question_bank.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_question_bank.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_question_bank.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_question_bank.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_question_bank.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_qbank_status ON tms_question_bank (biz_status);
+
+-- 璇曢銆備慨鏀逛笉褰卞搷宸插畬鎴愯�冭瘯蹇収銆�
+CREATE TABLE IF NOT EXISTS tms_question (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ question_no varchar(50),
+ bank_id varchar(50) NOT NULL,
+ question_type varchar(20) NOT NULL,
+ difficulty varchar(20),
+ source_type varchar(50),
+ stem text NOT NULL,
+ analysis text,
+ admin_user_id varchar(50),
+ biz_status varchar(20) NOT NULL DEFAULT 'open',
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_question PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_question IS '璇曢銆備慨鏀逛笉褰卞搷宸插畬鎴愯�冭瘯蹇収銆�';
+COMMENT ON COLUMN tms_question.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_question.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_question.question_no IS '璇曢缂栧彿锛屽彲娴佹按';
+COMMENT ON COLUMN tms_question.bank_id IS '鎵�灞為搴� tms_question_bank.f_id';
+COMMENT ON COLUMN tms_question.question_type IS 'single鍗曢�� / multi澶氶�� / judge鍒ゆ柇 / blank濉┖ / essay闂瓟';
+COMMENT ON COLUMN tms_question.difficulty IS 'easy/normal/hard锛岀晫闈㈤粯璁や竴鑸�';
+COMMENT ON COLUMN tms_question.source_type IS '璇曢鏉ユ簮锛岄粯璁よ嚜鍛介';
+COMMENT ON COLUMN tms_question.stem IS '棰樺共锛屽瘜鏂囨湰';
+COMMENT ON COLUMN tms_question.analysis IS '绛旀瑙f瀽/澶囨敞锛岄敊棰樺彲鏄剧ず';
+COMMENT ON COLUMN tms_question.admin_user_id IS '绠$悊鍛�';
+COMMENT ON COLUMN tms_question.biz_status IS 'open寮�鏀� / closed涓嶅紑鏀� / invalid搴熷純';
+COMMENT ON COLUMN tms_question.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_question.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_question.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_question.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_question.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_question.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_question.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_question_bank ON tms_question (bank_id, question_type, biz_status);
+
+-- 璇曢閫夐」銆傚崟閫夊崟閫変腑锛屽閫夊彲澶氶�変腑锛屽垽鏂彲鍋氭垚A瀵笲閿欍��
+CREATE TABLE IF NOT EXISTS tms_question_option (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ sort_no int,
+ option_label varchar(10),
+ option_content text,
+ is_correct varchar(10) NOT NULL DEFAULT '0',
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_question_option PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_question_option IS '璇曢閫夐」銆傚崟閫夊崟閫変腑锛屽閫夊彲澶氶�変腑锛屽垽鏂彲鍋氭垚A瀵笲閿欍��';
+COMMENT ON COLUMN tms_question_option.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_question_option.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_question_option.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_question_option.sort_no IS '搴忓彿';
+COMMENT ON COLUMN tms_question_option.option_label IS 'A/B/C/D...';
+COMMENT ON COLUMN tms_question_option.option_content IS '閫夐」鍐呭';
+COMMENT ON COLUMN tms_question_option.is_correct IS '鏄惁姝g‘绛旀 1鏄� 0鍚�';
+COMMENT ON COLUMN tms_question_option.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_question_option.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_question_option.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_question_option.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_question_option.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_qopt_fid ON tms_question_option (f_foreign_id);
+
+-- 璇曞嵎銆傚け鏁堣瘯鍗蜂笉寰楀啀鐢ㄤ簬鏂颁换鍔★紱鏀瑰嵎涓嶅奖鍝嶅凡鑰冭褰曘��
+CREATE TABLE IF NOT EXISTS tms_paper (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ paper_name varchar(300) NOT NULL,
+ biz_status varchar(20) NOT NULL DEFAULT 'open',
+ duration_min int NOT NULL DEFAULT 60,
+ exam_start timestamp,
+ exam_end timestamp,
+ score_publish_time timestamp,
+ pass_score numeric(8,1),
+ total_score numeric(8,1),
+ sort_mode varchar(20) NOT NULL DEFAULT 'paper',
+ has_subjective varchar(10) NOT NULL DEFAULT '0',
+ remark text,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_paper PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_paper IS '璇曞嵎銆傚け鏁堣瘯鍗蜂笉寰楀啀鐢ㄤ簬鏂颁换鍔★紱鏀瑰嵎涓嶅奖鍝嶅凡鑰冭褰曘��';
+COMMENT ON COLUMN tms_paper.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_paper.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_paper.paper_name IS '璇曞嵎鍚嶇О';
+COMMENT ON COLUMN tms_paper.biz_status IS 'open寮�鏀� / closed涓嶅紑鏀� / invalid澶辨晥';
+COMMENT ON COLUMN tms_paper.duration_min IS '鑰冭瘯鏃堕暱锛堝垎閽燂級';
+COMMENT ON COLUMN tms_paper.exam_start IS '璇曞嵎绾у紑鑰冩椂闂达紝鍙┖锛屼换鍔′笂鍐嶈';
+COMMENT ON COLUMN tms_paper.exam_end IS '璇曞嵎绾х粨鑰冩椂闂达紝鍙┖';
+COMMENT ON COLUMN tms_paper.score_publish_time IS '鎴愮哗鍏竷鏃堕棿锛岀┖=绔嬪嵆鍏竷';
+COMMENT ON COLUMN tms_paper.pass_score IS '鍚堟牸鍒嗘暟';
+COMMENT ON COLUMN tms_paper.total_score IS '璇曞嵎鎬诲垎';
+COMMENT ON COLUMN tms_paper.sort_mode IS 'paper璇曞嵎鑷韩椤哄簭 / random闅忔満';
+COMMENT ON COLUMN tms_paper.has_subjective IS '鏄惁鍚富瑙傞锛岀粍鍗锋椂鍥炲啓';
+COMMENT ON COLUMN tms_paper.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_paper.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_paper.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_paper.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_paper.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_paper.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_paper.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_paper.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_paper_status ON tms_paper (biz_status);
+
+-- 璇曞嵎绔犺妭锛屽彲鎸夐鍨嬪綊绫�
+CREATE TABLE IF NOT EXISTS tms_paper_section (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ section_name varchar(100),
+ question_type varchar(20),
+ sort_no int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_paper_section PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_paper_section IS '璇曞嵎绔犺妭锛屽彲鎸夐鍨嬪綊绫�';
+COMMENT ON COLUMN tms_paper_section.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_paper_section.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_paper_section.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_paper_section.section_name IS '绔犺妭鍚嶏紝濡� 涓�銆佸崟閫夐';
+COMMENT ON COLUMN tms_paper_section.question_type IS '榛樿棰樺瀷';
+COMMENT ON COLUMN tms_paper_section.sort_no IS '鎺掑簭';
+COMMENT ON COLUMN tms_paper_section.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_paper_section.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_paper_section.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_paper_section.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_paper_section.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_psec_fid ON tms_paper_section (f_foreign_id);
+
+-- 璇曞嵎缁勬垚璇曢锛堝綋鍓嶇増鏈級銆傚凡鑰冭瘯鍗疯蛋 tms_exam_item 蹇収銆�
+CREATE TABLE IF NOT EXISTS tms_paper_question (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ section_id varchar(50),
+ question_id varchar(50) NOT NULL,
+ score numeric(8,1),
+ sort_no int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_paper_question PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_paper_question IS '璇曞嵎缁勬垚璇曢锛堝綋鍓嶇増鏈級銆傚凡鑰冭瘯鍗疯蛋 tms_exam_item 蹇収銆�';
+COMMENT ON COLUMN tms_paper_question.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_paper_question.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_paper_question.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_paper_question.section_id IS '绔犺妭ID';
+COMMENT ON COLUMN tms_paper_question.question_id IS '璇曢ID';
+COMMENT ON COLUMN tms_paper_question.score IS '鏈鍒嗗��';
+COMMENT ON COLUMN tms_paper_question.sort_no IS '鑷畾涔夋帓搴�';
+COMMENT ON COLUMN tms_paper_question.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_paper_question.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_paper_question.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_paper_question.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_paper_question.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_pq_fid ON tms_paper_question (f_foreign_id);
+CREATE INDEX IF NOT EXISTS idx_tms_pq_qid ON tms_paper_question (question_id);
+
+-- ---------------------------------------------------------------------------
+-- 3. 宀椾綅/骞村害璁″垝
+-- ---------------------------------------------------------------------------
+-- 宀椾綅鍩硅鐩綍銆傛敮鎸佸崌鐗堛�佸簾寮冦�傚鎵归�氳繃鍚庡彲鏁村崟澶嶅埗銆�
+CREATE TABLE IF NOT EXISTS tms_post_catalog (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ catalog_no varchar(50),
+ post_id varchar(50) NOT NULL,
+ post_name varchar(100),
+ dept_id varchar(50),
+ version_no int NOT NULL DEFAULT 1,
+ biz_status varchar(20) NOT NULL DEFAULT 'valid',
+ remark varchar(500),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_post_catalog PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_post_catalog IS '宀椾綅鍩硅鐩綍銆傛敮鎸佸崌鐗堛�佸簾寮冦�傚鎵归�氳繃鍚庡彲鏁村崟澶嶅埗銆�';
+COMMENT ON COLUMN tms_post_catalog.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_post_catalog.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_post_catalog.catalog_no IS '鐩綍缂栧彿';
+COMMENT ON COLUMN tms_post_catalog.post_id IS '宀椾綅';
+COMMENT ON COLUMN tms_post_catalog.post_name IS '宀椾綅鍚嶇О鍐椾綑';
+COMMENT ON COLUMN tms_post_catalog.dept_id IS '鎵�灞為儴闂�';
+COMMENT ON COLUMN tms_post_catalog.version_no IS '鐗堟湰鍙凤紝鍗囩増+1';
+COMMENT ON COLUMN tms_post_catalog.biz_status IS 'valid鏈夋晥 / revoked搴熷純';
+COMMENT ON COLUMN tms_post_catalog.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_post_catalog.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_post_catalog.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_post_catalog.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_post_catalog.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_post_catalog.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_post_catalog.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_post_catalog.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_post_catalog.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_post_catalog.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_post_catalog.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_pcat_post ON tms_post_catalog (post_id, biz_status);
+
+-- 宀椾綅鍩硅鐩綍鍐呭琛岋紝鏀寔鍥炶溅澶氳銆佹墜鍔ㄦ帓搴�
+CREATE TABLE IF NOT EXISTS tms_post_catalog_item (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ sort_no int,
+ subject varchar(500),
+ train_mode varchar(50),
+ hours numeric(8,1),
+ eval_mode varchar(50),
+ material_id varchar(50),
+ course_id varchar(50),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_post_catalog_item PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_post_catalog_item IS '宀椾綅鍩硅鐩綍鍐呭琛岋紝鏀寔鍥炶溅澶氳銆佹墜鍔ㄦ帓搴�';
+COMMENT ON COLUMN tms_post_catalog_item.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_post_catalog_item.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_post_catalog_item.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_post_catalog_item.sort_no IS '椤哄簭';
+COMMENT ON COLUMN tms_post_catalog_item.subject IS '鍩硅鍐呭';
+COMMENT ON COLUMN tms_post_catalog_item.train_mode IS '鍩硅鏂瑰紡';
+COMMENT ON COLUMN tms_post_catalog_item.hours IS '璇炬椂';
+COMMENT ON COLUMN tms_post_catalog_item.eval_mode IS '鑰冩牳鏂瑰紡';
+COMMENT ON COLUMN tms_post_catalog_item.material_id IS '鏁欐潗';
+COMMENT ON COLUMN tms_post_catalog_item.course_id IS '璇剧▼';
+COMMENT ON COLUMN tms_post_catalog_item.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_post_catalog_item.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_post_catalog_item.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_post_catalog_item.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_post_catalog_item.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_pcati_fid ON tms_post_catalog_item (f_foreign_id);
+
+-- 宀椾綅鍩硅璁″垝銆傜敱鐩綍鎺ㄩ�侊紝鍙敓鎴愪釜浜哄矖浣嶅煿璁拰鍩硅浠诲姟銆�
+CREATE TABLE IF NOT EXISTS tms_post_plan (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ plan_no varchar(50) NOT NULL,
+ post_id varchar(50),
+ post_name varchar(100),
+ dept_id varchar(50),
+ plan_end_time date,
+ post_desc text,
+ trainees text,
+ catalog_id varchar(50),
+ publish_status varchar(20) NOT NULL DEFAULT 'draft',
+ remark varchar(500),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_post_plan PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_post_plan IS '宀椾綅鍩硅璁″垝銆傜敱鐩綍鎺ㄩ�侊紝鍙敓鎴愪釜浜哄矖浣嶅煿璁拰鍩硅浠诲姟銆�';
+COMMENT ON COLUMN tms_post_plan.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_post_plan.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_post_plan.plan_no IS '璁″垝缂栧彿 JP+YYYYMM+4锛屽 JP2026090012';
+COMMENT ON COLUMN tms_post_plan.post_id IS '宀椾綅缂栫爜/ID';
+COMMENT ON COLUMN tms_post_plan.post_name IS '宀椾綅鍚嶇О';
+COMMENT ON COLUMN tms_post_plan.dept_id IS '鎵�灞為儴闂�';
+COMMENT ON COLUMN tms_post_plan.plan_end_time IS '璁″垝缁撴潫鏃堕棿锛屽甫鍏ヤ釜浜哄矖浣嶅煿璁�';
+COMMENT ON COLUMN tms_post_plan.post_desc IS '宀椾綅鎻忚堪';
+COMMENT ON COLUMN tms_post_plan.trainees IS '鍩硅瀵硅薄锛岀敤鎴峰閫�';
+COMMENT ON COLUMN tms_post_plan.catalog_id IS '鏉ユ簮鐩綍';
+COMMENT ON COLUMN tms_post_plan.publish_status IS 'draft鏈彂甯� / published宸插彂甯�';
+COMMENT ON COLUMN tms_post_plan.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_post_plan.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_post_plan.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_post_plan.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_post_plan.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_post_plan.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_post_plan.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_post_plan.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_post_plan.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_post_plan.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_post_plan.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_pplan_no ON tms_post_plan (plan_no) WHERE f_delete_mark = 0;
+CREATE INDEX IF NOT EXISTS idx_tms_pplan_post ON tms_post_plan (post_id, publish_status);
+
+-- 宀椾綅鍩硅璁″垝鏄庣粏
+CREATE TABLE IF NOT EXISTS tms_post_plan_item (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ plan_time date,
+ teacher_id varchar(50),
+ subject varchar(500),
+ train_mode varchar(50),
+ hours numeric(8,1),
+ eval_mode varchar(50),
+ material_id varchar(50),
+ task_id varchar(50),
+ line_status varchar(20),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_post_plan_item PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_post_plan_item IS '宀椾綅鍩硅璁″垝鏄庣粏';
+COMMENT ON COLUMN tms_post_plan_item.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_post_plan_item.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_post_plan_item.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_post_plan_item.plan_time IS '鍩硅璁″垝鏃堕棿';
+COMMENT ON COLUMN tms_post_plan_item.teacher_id IS '鍩硅甯�';
+COMMENT ON COLUMN tms_post_plan_item.subject IS '鍩硅鍐呭';
+COMMENT ON COLUMN tms_post_plan_item.train_mode IS '鍩硅鏂瑰紡';
+COMMENT ON COLUMN tms_post_plan_item.hours IS '鍩硅璇炬椂';
+COMMENT ON COLUMN tms_post_plan_item.eval_mode IS '鑰冩牳鏂瑰紡';
+COMMENT ON COLUMN tms_post_plan_item.material_id IS '鏁欐潗';
+COMMENT ON COLUMN tms_post_plan_item.task_id IS '鐢熸垚鐨勫煿璁换鍔D';
+COMMENT ON COLUMN tms_post_plan_item.line_status IS 'pending寰呭彂甯� / published宸插彂甯� / done宸插畬鎴�';
+COMMENT ON COLUMN tms_post_plan_item.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_post_plan_item.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_post_plan_item.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_post_plan_item.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_post_plan_item.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_pplani_fid ON tms_post_plan_item (f_foreign_id);
+
+-- 涓汉宀椾綅鍩硅娓呭崟銆傝浆宀楁椂瀛愯〃鏍囪宸插煿璁繃鍒欎笉鐢熸垚浠诲姟銆�
+CREATE TABLE IF NOT EXISTS tms_person_post (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ plan_id varchar(50),
+ catalog_id varchar(50),
+ user_id varchar(50) NOT NULL,
+ post_id varchar(50),
+ plan_end_time date,
+ biz_status varchar(20) NOT NULL DEFAULT 'doing',
+ person_remark varchar(500),
+ audit_remark varchar(500),
+ approve_remark varchar(500),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_person_post PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_person_post IS '涓汉宀椾綅鍩硅娓呭崟銆傝浆宀楁椂瀛愯〃鏍囪宸插煿璁繃鍒欎笉鐢熸垚浠诲姟銆�';
+COMMENT ON COLUMN tms_person_post.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_person_post.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_person_post.plan_id IS '宀椾綅鍩硅璁″垝ID';
+COMMENT ON COLUMN tms_person_post.catalog_id IS '鐩綍ID';
+COMMENT ON COLUMN tms_person_post.user_id IS '鍩硅瀵硅薄';
+COMMENT ON COLUMN tms_person_post.post_id IS '宀椾綅';
+COMMENT ON COLUMN tms_person_post.plan_end_time IS '璁″垝缁撴潫鏃堕棿锛堢敱璁″垝甯﹀嚭锛�';
+COMMENT ON COLUMN tms_person_post.biz_status IS 'doing鎵ц涓� / done瀹屾垚 / returned閫�鍥�';
+COMMENT ON COLUMN tms_person_post.person_remark IS '涓汉澶囨敞';
+COMMENT ON COLUMN tms_person_post.audit_remark IS '瀹℃牳澶囨敞';
+COMMENT ON COLUMN tms_person_post.approve_remark IS '瀹℃壒澶囨敞';
+COMMENT ON COLUMN tms_person_post.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_person_post.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_person_post.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_person_post.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_person_post.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_person_post.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_person_post.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_person_post.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_person_post.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_person_post.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_ppost_user ON tms_person_post (user_id, biz_status);
+CREATE INDEX IF NOT EXISTS idx_tms_ppost_plan ON tms_person_post (plan_id);
+
+-- 涓汉宀椾綅鍩硅鏄庣粏
+CREATE TABLE IF NOT EXISTS tms_person_post_item (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ subject varchar(500),
+ train_mode varchar(50),
+ hours numeric(8,1),
+ eval_mode varchar(50),
+ already_trained varchar(10) NOT NULL DEFAULT '0',
+ task_id varchar(50),
+ line_status varchar(20),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_person_post_item PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_person_post_item IS '涓汉宀椾綅鍩硅鏄庣粏';
+COMMENT ON COLUMN tms_person_post_item.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_person_post_item.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_person_post_item.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_person_post_item.subject IS '鍩硅鍐呭';
+COMMENT ON COLUMN tms_person_post_item.train_mode IS '鍩硅鏂瑰紡';
+COMMENT ON COLUMN tms_person_post_item.hours IS '璇炬椂';
+COMMENT ON COLUMN tms_person_post_item.eval_mode IS '鑰冩牳鏂瑰紡';
+COMMENT ON COLUMN tms_person_post_item.already_trained IS '杞矖锛氭槸鍚﹀凡鍩硅杩囷紝鏄垯涓嶇敓鎴愪换鍔�';
+COMMENT ON COLUMN tms_person_post_item.task_id IS '鐢熸垚鐨勫煿璁换鍔�';
+COMMENT ON COLUMN tms_person_post_item.line_status IS '鐘舵��';
+COMMENT ON COLUMN tms_person_post_item.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_person_post_item.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_person_post_item.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_person_post_item.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_person_post_item.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_pposti_fid ON tms_person_post_item (f_foreign_id);
+
+-- 骞村害鍩硅璁″垝锛堝叕鍙�/閮ㄩ棬锛夈�傚姙缁撳悗鐢熸垚鍩硅浠诲姟銆傛祦绋嬶細閮ㄩ棬璐熻矗浜衡啋QA璐熻矗浜恒��
+CREATE TABLE IF NOT EXISTS tms_annual_plan (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ plan_year int NOT NULL,
+ plan_no varchar(50) NOT NULL,
+ plan_type varchar(20),
+ author_id varchar(50),
+ author_dept_id varchar(50),
+ author_date date,
+ version_no int NOT NULL DEFAULT 1,
+ dept_leader_id varchar(50),
+ qa_leader_id varchar(50),
+ biz_status varchar(20) NOT NULL DEFAULT 'draft',
+ remark text,
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_annual_plan PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_annual_plan IS '骞村害鍩硅璁″垝锛堝叕鍙�/閮ㄩ棬锛夈�傚姙缁撳悗鐢熸垚鍩硅浠诲姟銆傛祦绋嬶細閮ㄩ棬璐熻矗浜衡啋QA璐熻矗浜恒��';
+COMMENT ON COLUMN tms_annual_plan.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_annual_plan.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_annual_plan.plan_year IS '骞翠唤锛屽埗瀹氭椂榛樿褰撳墠骞�+1';
+COMMENT ON COLUMN tms_annual_plan.plan_no IS '璁″垝缂栧彿锛屽 20260001';
+COMMENT ON COLUMN tms_annual_plan.plan_type IS 'company鍏徃绾� / dept閮ㄩ棬绾�';
+COMMENT ON COLUMN tms_annual_plan.author_id IS '鍒跺畾浜�';
+COMMENT ON COLUMN tms_annual_plan.author_dept_id IS '鍒跺畾閮ㄩ棬';
+COMMENT ON COLUMN tms_annual_plan.author_date IS '鍒跺畾鏃ユ湡';
+COMMENT ON COLUMN tms_annual_plan.version_no IS '鐗堟湰';
+COMMENT ON COLUMN tms_annual_plan.dept_leader_id IS '閮ㄩ棬璐熻矗浜猴紙绛炬牳灞曠ず锛�';
+COMMENT ON COLUMN tms_annual_plan.qa_leader_id IS 'QA閮ㄨ礋璐d汉';
+COMMENT ON COLUMN tms_annual_plan.biz_status IS 'draft鑽夌 / approving瀹℃壒涓� / approved宸叉壒鍑�';
+COMMENT ON COLUMN tms_annual_plan.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_annual_plan.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_annual_plan.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_annual_plan.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_annual_plan.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_annual_plan.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_annual_plan.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_annual_plan.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_annual_plan.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_annual_plan.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_annual_plan.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_aplan_no ON tms_annual_plan (plan_no) WHERE f_delete_mark = 0;
+CREATE INDEX IF NOT EXISTS idx_tms_aplan_year ON tms_annual_plan (plan_year, plan_type, author_dept_id);
+
+-- 骞村害鍩硅璁″垝鏄庣粏
+CREATE TABLE IF NOT EXISTS tms_annual_plan_item (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ train_month varchar(6),
+ subject varchar(500),
+ train_mode varchar(50),
+ trainees text,
+ hours numeric(8,1),
+ teacher_id varchar(50),
+ eval_mode varchar(50),
+ course_id varchar(50),
+ line_status varchar(20) NOT NULL DEFAULT 'pending',
+ task_id varchar(50),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_annual_plan_item PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_annual_plan_item IS '骞村害鍩硅璁″垝鏄庣粏';
+COMMENT ON COLUMN tms_annual_plan_item.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_annual_plan_item.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_annual_plan_item.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_annual_plan_item.train_month IS '鍩硅鏈堜唤 YYYYMM锛屽 202609';
+COMMENT ON COLUMN tms_annual_plan_item.subject IS '鍩硅鍐呭';
+COMMENT ON COLUMN tms_annual_plan_item.train_mode IS '鍩硅鏂瑰紡';
+COMMENT ON COLUMN tms_annual_plan_item.trainees IS '鍩硅瀵硅薄';
+COMMENT ON COLUMN tms_annual_plan_item.hours IS '鍩硅璇炬椂';
+COMMENT ON COLUMN tms_annual_plan_item.teacher_id IS '鍩硅甯�';
+COMMENT ON COLUMN tms_annual_plan_item.eval_mode IS '鑰冩牳鏂瑰紡';
+COMMENT ON COLUMN tms_annual_plan_item.course_id IS '鍩硅璇剧▼';
+COMMENT ON COLUMN tms_annual_plan_item.line_status IS 'pending寰呮墽琛� / tasked宸茬敓鎴愪换鍔� / done宸插畬鎴� / delayed宸插欢鏈�';
+COMMENT ON COLUMN tms_annual_plan_item.task_id IS '鐢熸垚鐨勫煿璁换鍔�';
+COMMENT ON COLUMN tms_annual_plan_item.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_annual_plan_item.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_annual_plan_item.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_annual_plan_item.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_annual_plan_item.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_aplani_fid ON tms_annual_plan_item (f_foreign_id);
+CREATE INDEX IF NOT EXISTS idx_tms_aplani_month ON tms_annual_plan_item (train_month);
+
+-- 骞村害鍩硅璁″垝寤舵湡鐢宠
+CREATE TABLE IF NOT EXISTS tms_annual_delay (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ plan_id varchar(50) NOT NULL,
+ item_id varchar(50),
+ old_month varchar(6),
+ new_month varchar(6),
+ reason text,
+ biz_status varchar(20),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_annual_delay PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_annual_delay IS '骞村害鍩硅璁″垝寤舵湡鐢宠';
+COMMENT ON COLUMN tms_annual_delay.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_annual_delay.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_annual_delay.plan_id IS '骞村害璁″垝ID';
+COMMENT ON COLUMN tms_annual_delay.item_id IS '璁″垝鏄庣粏ID';
+COMMENT ON COLUMN tms_annual_delay.old_month IS '鍘熸湀浠�';
+COMMENT ON COLUMN tms_annual_delay.new_month IS '寤舵湡鑷虫湀浠�';
+COMMENT ON COLUMN tms_annual_delay.reason IS '寤舵湡鍘熷洜';
+COMMENT ON COLUMN tms_annual_delay.biz_status IS '瀹℃壒鐘舵��';
+COMMENT ON COLUMN tms_annual_delay.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_annual_delay.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_annual_delay.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_annual_delay.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_annual_delay.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_annual_delay.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_annual_delay.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_annual_delay.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_annual_delay.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_annual_delay.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_adelay_plan ON tms_annual_delay (plan_id);
+
+-- ---------------------------------------------------------------------------
+-- 4. 鍩硅浠诲姟涓庤褰�
+-- ---------------------------------------------------------------------------
+-- 鍩硅浠诲姟锛堟牳蹇冿級銆傛潵婧愶細宀椾綅璁″垝/骞村害璁″垝/鏂囦欢鐢熸晥/涓存椂/澶栧嚭/鍐嶇淮鎶ゃ��
+CREATE TABLE IF NOT EXISTS tms_task (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ task_no varchar(50) NOT NULL,
+ category varchar(50),
+ train_type varchar(50),
+ source_type varchar(50),
+ source_plan_no varchar(50),
+ source_id varchar(50),
+ source_item_id varchar(50),
+ subject text,
+ key_points text,
+ material_id varchar(50),
+ material_no varchar(50),
+ place_id varchar(50),
+ place_no varchar(50),
+ place_name varchar(200),
+ start_time timestamp,
+ end_time timestamp,
+ close_time timestamp,
+ paper_id varchar(50),
+ paper_name varchar(300),
+ exam_start timestamp,
+ exam_end timestamp,
+ teacher_id text,
+ train_mode varchar(50),
+ eval_mode varchar(50),
+ trainees text,
+ task_kind varchar(20),
+ prev_task_no varchar(50),
+ publish_status varchar(20) NOT NULL DEFAULT 'draft',
+ publish_time timestamp,
+ retake_limit int NOT NULL DEFAULT 1,
+ pass_score numeric(8,1),
+ quiz_ratio int,
+ sign_rate int,
+ pass_rate int,
+ unfinished_rate int,
+ overdue_remind varchar(10) NOT NULL DEFAULT '0',
+ invite_flag varchar(10) NOT NULL DEFAULT '0',
+ dms_file_id varchar(50),
+ remark varchar(500),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_task PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_task IS '鍩硅浠诲姟锛堟牳蹇冿級銆傛潵婧愶細宀椾綅璁″垝/骞村害璁″垝/鏂囦欢鐢熸晥/涓存椂/澶栧嚭/鍐嶇淮鎶ゃ��';
+COMMENT ON COLUMN tms_task.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_task.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_task.task_no IS '浠诲姟缂栧彿 TT+YYYYMM+4锛屽 TT2026090618';
+COMMENT ON COLUMN tms_task.category IS '鍩硅鍒嗙被锛氫复鏃跺煿璁�/宀椾綅鍩硅璁″垝/骞村害鍩硅璁″垝/鏂囦欢鐢熸晥鍩硅/澶栧嚭鍩硅/鍐嶇淮鎶�';
+COMMENT ON COLUMN tms_task.train_type IS '鍩硅绫诲瀷锛堝垪琛ㄥ瓧娈碉紝鍙笌鍒嗙被骞跺瓨锛�';
+COMMENT ON COLUMN tms_task.source_type IS '鏉ユ簮绫诲瀷缂栫爜';
+COMMENT ON COLUMN tms_task.source_plan_no IS '鏉ユ簮璁″垝缂栧彿';
+COMMENT ON COLUMN tms_task.source_id IS '鏉ユ簮涓昏〃ID';
+COMMENT ON COLUMN tms_task.source_item_id IS '鏉ユ簮鏄庣粏ID锛屽綊妗e洖鍐�';
+COMMENT ON COLUMN tms_task.subject IS '鍩硅涓婚';
+COMMENT ON COLUMN tms_task.key_points IS '鍩硅瑕佺偣锛岀鍒板墠寮哄埗闃呰';
+COMMENT ON COLUMN tms_task.material_id IS '鍩硅鏁欐潗';
+COMMENT ON COLUMN tms_task.material_no IS '鏁欐潗缂栧彿鍐椾綑';
+COMMENT ON COLUMN tms_task.place_id IS '鍩硅鍦扮偣';
+COMMENT ON COLUMN tms_task.place_no IS '鍦扮偣缂栧彿鍐椾綑';
+COMMENT ON COLUMN tms_task.place_name IS '鍦扮偣鍚嶇О鍐椾綑';
+COMMENT ON COLUMN tms_task.start_time IS '鍩硅寮�濮嬫椂闂�';
+COMMENT ON COLUMN tms_task.end_time IS '鍩硅缁撴潫鏃堕棿';
+COMMENT ON COLUMN tms_task.close_time IS '浠诲姟鍏抽棴鏃堕棿锛屽埌杈惧悗璁板綍杩涘緟褰掓。';
+COMMENT ON COLUMN tms_task.paper_id IS '璇曞嵎';
+COMMENT ON COLUMN tms_task.paper_name IS '璇曞嵎鍚嶇О鍐椾綑';
+COMMENT ON COLUMN tms_task.exam_start IS '鑰冭瘯寮�濮嬫椂闂�';
+COMMENT ON COLUMN tms_task.exam_end IS '鑰冭瘯缁撴潫鏃堕棿';
+COMMENT ON COLUMN tms_task.teacher_id IS '鍩硅甯堬紝鍙閫�';
+COMMENT ON COLUMN tms_task.train_mode IS '鍩硅鏂瑰紡';
+COMMENT ON COLUMN tms_task.eval_mode IS '鍩硅鏁堟灉璇勪及鏂瑰紡/鑰冩牳鏂瑰紡';
+COMMENT ON COLUMN tms_task.trainees IS '鍩硅瀵硅薄锛岀敤鎴峰閫夛紱鍙戝竷鏃舵媶涓汉浠诲姟';
+COMMENT ON COLUMN tms_task.task_kind IS '浠诲姟绫诲瀷锛歯ew鏂板 / continue缁х画(鍐嶇淮鎶�)';
+COMMENT ON COLUMN tms_task.prev_task_no IS '涓婁竴娆″煿璁换鍔$紪鍙�';
+COMMENT ON COLUMN tms_task.publish_status IS 'draft鏈彂甯� / published宸插彂甯� / cancelled宸插彇娑� / done宸插畬鎴�';
+COMMENT ON COLUMN tms_task.publish_time IS '鍙戝竷鏃堕棿';
+COMMENT ON COLUMN tms_task.retake_limit IS '涓嶅悎鏍煎彲閲嶈�冩鏁�';
+COMMENT ON COLUMN tms_task.pass_score IS '閫氳繃鍒嗘暟锛岀┖鍒欑敤璇曞嵎';
+COMMENT ON COLUMN tms_task.quiz_ratio IS '鎻愰棶姣斾緥0-100锛岃嚜鍔ㄧ畻搴旀彁闂汉鏁�';
+COMMENT ON COLUMN tms_task.sign_rate IS '绛惧埌鐜�%锛屽彇鏁磋垗灏忔暟';
+COMMENT ON COLUMN tms_task.pass_rate IS '鍚堟牸鐜�%锛屽彇鏁磋垗灏忔暟';
+COMMENT ON COLUMN tms_task.unfinished_rate IS '鏈畬鎴愮巼%';
+COMMENT ON COLUMN tms_task.overdue_remind IS '鏄惁閫炬湡鎻愰啋閮ㄩ棬棰嗗';
+COMMENT ON COLUMN tms_task.invite_flag IS '鏄惁鍙戦�佸煿璁個璇�';
+COMMENT ON COLUMN tms_task.dms_file_id IS '鏂囦欢鐢熸晥鑷姩寮曞叆鐨勯檮浠�';
+COMMENT ON COLUMN tms_task.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_task.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_task.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_task.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_task.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_task.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_task.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_task.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_task.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_task.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_task.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_task_no ON tms_task (task_no) WHERE f_delete_mark = 0;
+CREATE INDEX IF NOT EXISTS idx_tms_task_status ON tms_task (publish_status, start_time);
+CREATE INDEX IF NOT EXISTS idx_tms_task_place ON tms_task (place_id, start_time, end_time);
+CREATE INDEX IF NOT EXISTS idx_tms_task_source ON tms_task (source_type, source_id);
+CREATE INDEX IF NOT EXISTS idx_tms_task_teacher ON tms_task (teacher_id);
+
+-- 鍩硅浠诲姟鏁欐潗/闄勪欢娓呭崟锛屽彂甯冨悗鍚屾鍒板煿璁褰�
+CREATE TABLE IF NOT EXISTS tms_task_file (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ file_no varchar(50),
+ file_name varchar(300),
+ material_id varchar(50),
+ file_json text,
+ can_download varchar(10) NOT NULL DEFAULT '0',
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_task_file PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_task_file IS '鍩硅浠诲姟鏁欐潗/闄勪欢娓呭崟锛屽彂甯冨悗鍚屾鍒板煿璁褰�';
+COMMENT ON COLUMN tms_task_file.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_task_file.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_task_file.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_task_file.file_no IS '缂栧彿';
+COMMENT ON COLUMN tms_task_file.file_name IS '鏂囦欢鍚嶇О';
+COMMENT ON COLUMN tms_task_file.material_id IS '鏉ユ簮鏁欐潗';
+COMMENT ON COLUMN tms_task_file.file_json IS '闄勪欢';
+COMMENT ON COLUMN tms_task_file.can_download IS '寮曠敤鏁欐潗榛樿涓嶅彲涓嬭浇鎵撳嵃';
+COMMENT ON COLUMN tms_task_file.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_task_file.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_task_file.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_task_file.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_task_file.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_tfile_fid ON tms_task_file (f_foreign_id);
+
+-- 鍩硅浠诲姟鎻愰棶棰勮闂鍜岀瓟妗堬紝绛惧埌鍚庡脊鍑�
+CREATE TABLE IF NOT EXISTS tms_task_quiz (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ sort_no int,
+ question text,
+ answer text,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_task_quiz PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_task_quiz IS '鍩硅浠诲姟鎻愰棶棰勮闂鍜岀瓟妗堬紝绛惧埌鍚庡脊鍑�';
+COMMENT ON COLUMN tms_task_quiz.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_task_quiz.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_task_quiz.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_task_quiz.sort_no IS '搴忓彿';
+COMMENT ON COLUMN tms_task_quiz.question IS '闂';
+COMMENT ON COLUMN tms_task_quiz.answer IS '鍙傝�冪瓟妗�';
+COMMENT ON COLUMN tms_task_quiz.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_task_quiz.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_task_quiz.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_task_quiz.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_task_quiz.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_tquiz_fid ON tms_task_quiz (f_foreign_id);
+
+-- 涓汉鍩硅浠诲姟銆傚彂甯冩椂鎸変汉鎷嗚锛涘鍛樼鑷/绛惧埌/鑰冭瘯鍏ュ彛銆�
+CREATE TABLE IF NOT EXISTS tms_person_task (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ task_id varchar(50) NOT NULL,
+ task_no varchar(50),
+ user_id varchar(50) NOT NULL,
+ dept_id varchar(50),
+ hours numeric(8,1),
+ biz_status varchar(20) NOT NULL DEFAULT 'todo',
+ sign_time timestamp,
+ sign_mode varchar(20),
+ learn_seconds int,
+ exam_score numeric(8,1),
+ pass_flag varchar(20),
+ guest_flag varchar(10) NOT NULL DEFAULT '0',
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_person_task PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_person_task IS '涓汉鍩硅浠诲姟銆傚彂甯冩椂鎸変汉鎷嗚锛涘鍛樼鑷/绛惧埌/鑰冭瘯鍏ュ彛銆�';
+COMMENT ON COLUMN tms_person_task.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_person_task.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_person_task.task_id IS '鍩硅浠诲姟ID';
+COMMENT ON COLUMN tms_person_task.task_no IS '浠诲姟缂栧彿鍐椾綑';
+COMMENT ON COLUMN tms_person_task.user_id IS '鍩硅瀵硅薄';
+COMMENT ON COLUMN tms_person_task.dept_id IS '褰撴椂閮ㄩ棬蹇収';
+COMMENT ON COLUMN tms_person_task.hours IS '瀛︽椂';
+COMMENT ON COLUMN tms_person_task.biz_status IS 'todo鏈畬鎴� / signed宸茬鍒� / done宸插畬鎴� / expired宸茶繃鏈� / cancelled宸插彇娑�';
+COMMENT ON COLUMN tms_person_task.sign_time IS '绛惧埌鏃堕棿';
+COMMENT ON COLUMN tms_person_task.sign_mode IS '绛惧埌鏂瑰紡';
+COMMENT ON COLUMN tms_person_task.learn_seconds IS '鍦ㄧ嚎瀛︿範鏃堕暱绉�';
+COMMENT ON COLUMN tms_person_task.exam_score IS '鑰冭瘯鎴愮哗';
+COMMENT ON COLUMN tms_person_task.pass_flag IS 'pass鍚堟牸 / fail涓嶅悎鏍� / na鏃犻渶鑰冩牳';
+COMMENT ON COLUMN tms_person_task.guest_flag IS '鏄惁鍚嶅崟澶栫鍒�';
+COMMENT ON COLUMN tms_person_task.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_person_task.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_person_task.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_person_task.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_person_task.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_person_task.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_person_task.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_ptask_user ON tms_person_task (user_id, biz_status);
+CREATE INDEX IF NOT EXISTS idx_tms_ptask_task ON tms_person_task (task_id);
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_ptask_task_user ON tms_person_task (task_id, user_id) WHERE f_delete_mark = 0;
+
+-- 鍩硅璁板綍銆備换鍔″彂甯冨悗鐢熸垚锛涘叧闂椂闂村埌杈捐繘寰呭綊妗c��
+CREATE TABLE IF NOT EXISTS tms_record (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ record_no varchar(50),
+ task_id varchar(50) NOT NULL,
+ task_no varchar(50),
+ category varchar(50),
+ subject text,
+ teacher_id text,
+ train_type varchar(50),
+ train_mode varchar(50),
+ eval_mode varchar(50),
+ start_time timestamp,
+ end_time timestamp,
+ close_time timestamp,
+ archive_status varchar(20) NOT NULL DEFAULT 'pending',
+ archive_time timestamp,
+ archiver_id varchar(50),
+ sign_rate int,
+ pass_rate int,
+ lecture_file text,
+ paper_sign_file text,
+ print_tpl_id varchar(50),
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_record PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_record IS '鍩硅璁板綍銆備换鍔″彂甯冨悗鐢熸垚锛涘叧闂椂闂村埌杈捐繘寰呭綊妗c��';
+COMMENT ON COLUMN tms_record.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_record.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_record.record_no IS '璁板綍缂栧彿锛岄粯璁ゅ悓浠诲姟缂栧彿';
+COMMENT ON COLUMN tms_record.task_id IS '鍩硅浠诲姟ID';
+COMMENT ON COLUMN tms_record.task_no IS '浠诲姟缂栧彿';
+COMMENT ON COLUMN tms_record.category IS '鍩硅鍒嗙被';
+COMMENT ON COLUMN tms_record.subject IS '鍩硅涓婚';
+COMMENT ON COLUMN tms_record.teacher_id IS '鍩硅甯�';
+COMMENT ON COLUMN tms_record.train_type IS '鍩硅绫诲瀷';
+COMMENT ON COLUMN tms_record.train_mode IS '鍩硅鏂瑰紡';
+COMMENT ON COLUMN tms_record.eval_mode IS '鑰冩牳鏂瑰紡';
+COMMENT ON COLUMN tms_record.start_time IS '鍩硅寮�濮嬫椂闂达紝濂楁墦妯℃澘鎸夋绱㈠紩鐗堟湰';
+COMMENT ON COLUMN tms_record.end_time IS '鍩硅缁撴潫鏃堕棿';
+COMMENT ON COLUMN tms_record.close_time IS '鍏抽棴鏃堕棿';
+COMMENT ON COLUMN tms_record.archive_status IS 'pending寰呭綊妗� / ready鍙綊妗� / archived宸插綊妗� / invalid鏃犳晥';
+COMMENT ON COLUMN tms_record.archive_time IS '褰掓。鏃堕棿';
+COMMENT ON COLUMN tms_record.archiver_id IS '褰掓。浜�';
+COMMENT ON COLUMN tms_record.sign_rate IS '鍙備笌/绛惧埌鐜�% 鍙栨暣鑸嶅皬鏁�';
+COMMENT ON COLUMN tms_record.pass_rate IS '鍚堟牸鐜�%';
+COMMENT ON COLUMN tms_record.lecture_file IS '鍩硅璁蹭箟闄勪欢';
+COMMENT ON COLUMN tms_record.paper_sign_file IS '绾歌川绛惧埌琛ㄩ檮浠�';
+COMMENT ON COLUMN tms_record.print_tpl_id IS '鎵撳嵃妯℃澘鐗堟湰';
+COMMENT ON COLUMN tms_record.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_record.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_record.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_record.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_record.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_record.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_record.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_record.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_record_task ON tms_record (task_id) WHERE f_delete_mark = 0;
+CREATE INDEX IF NOT EXISTS idx_tms_record_arch ON tms_record (archive_status, start_time);
+
+-- 鍩硅璁板綍绛惧埌/缁撴灉鏄庣粏锛堜竴浜轰竴琛岋級
+CREATE TABLE IF NOT EXISTS tms_record_sign (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ user_id varchar(50) NOT NULL,
+ user_name varchar(100),
+ dept_id varchar(50),
+ sign_time timestamp,
+ sign_mode varchar(20),
+ guest_flag varchar(10) NOT NULL DEFAULT '0',
+ result_flag varchar(20),
+ exam_score numeric(8,1),
+ practice_score numeric(8,1),
+ quiz_score numeric(8,1),
+ exam_id varchar(50),
+ judge_user_id varchar(50),
+ judge_time timestamp,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_record_sign PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_record_sign IS '鍩硅璁板綍绛惧埌/缁撴灉鏄庣粏锛堜竴浜轰竴琛岋級';
+COMMENT ON COLUMN tms_record_sign.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_record_sign.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_record_sign.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_record_sign.user_id IS '鍩硅瀵硅薄';
+COMMENT ON COLUMN tms_record_sign.user_name IS '濮撳悕蹇収';
+COMMENT ON COLUMN tms_record_sign.dept_id IS '閮ㄩ棬蹇収';
+COMMENT ON COLUMN tms_record_sign.sign_time IS '绛惧埌鏃堕棿';
+COMMENT ON COLUMN tms_record_sign.sign_mode IS '绛惧埌鏂瑰紡';
+COMMENT ON COLUMN tms_record_sign.guest_flag IS '鍚嶅崟澶栫鍒�';
+COMMENT ON COLUMN tms_record_sign.result_flag IS 'pass鍚堟牸 / fail涓嶅悎鏍� / absent鏈弬鍔� / na鏃犻渶鑰冩牳';
+COMMENT ON COLUMN tms_record_sign.exam_score IS '鑰冭瘯鎴愮哗';
+COMMENT ON COLUMN tms_record_sign.practice_score IS '瀹炴搷鎴愮哗';
+COMMENT ON COLUMN tms_record_sign.quiz_score IS '鎻愰棶鎴愮哗';
+COMMENT ON COLUMN tms_record_sign.exam_id IS '绛斿嵎ID';
+COMMENT ON COLUMN tms_record_sign.judge_user_id IS '缁撴灉鍒ゅ畾浜猴紙鍩硅甯堬級';
+COMMENT ON COLUMN tms_record_sign.judge_time IS '鍒ゅ畾鏃堕棿';
+COMMENT ON COLUMN tms_record_sign.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_record_sign.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_record_sign.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_record_sign.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_record_sign.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_rsign_fid ON tms_record_sign (f_foreign_id);
+CREATE INDEX IF NOT EXISTS idx_tms_rsign_user ON tms_record_sign (user_id);
+
+-- 鍩硅璁板綍鍙樻洿锛氭敼缁撴潫鏃堕棿銆佸鍔犲煿璁汉鍛樸�傚煿璁笀鍙戣捣鈫掗儴闂ㄩ瀵硷紙棰嗗鍗冲煿璁笀鍒欒烦杩囷級銆�
+CREATE TABLE IF NOT EXISTS tms_record_change (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ record_id varchar(50) NOT NULL,
+ task_id varchar(50),
+ change_type varchar(20),
+ old_end_time timestamp,
+ new_end_time timestamp,
+ add_users text,
+ reason text,
+ biz_status varchar(20),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_record_change PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_record_change IS '鍩硅璁板綍鍙樻洿锛氭敼缁撴潫鏃堕棿銆佸鍔犲煿璁汉鍛樸�傚煿璁笀鍙戣捣鈫掗儴闂ㄩ瀵硷紙棰嗗鍗冲煿璁笀鍒欒烦杩囷級銆�';
+COMMENT ON COLUMN tms_record_change.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_record_change.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_record_change.record_id IS '鍩硅璁板綍ID';
+COMMENT ON COLUMN tms_record_change.task_id IS '浠诲姟ID';
+COMMENT ON COLUMN tms_record_change.change_type IS 'end_time鏀圭粨鏉熸椂闂� / add_user澧炲姞浜哄憳';
+COMMENT ON COLUMN tms_record_change.old_end_time IS '鍘熺粨鏉熸椂闂�';
+COMMENT ON COLUMN tms_record_change.new_end_time IS '鏂扮粨鏉熸椂闂�';
+COMMENT ON COLUMN tms_record_change.add_users IS '鏂板浜哄憳';
+COMMENT ON COLUMN tms_record_change.reason IS '鍙樻洿鍘熷洜';
+COMMENT ON COLUMN tms_record_change.biz_status IS '瀹℃壒鐘舵��';
+COMMENT ON COLUMN tms_record_change.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_record_change.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_record_change.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_record_change.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_record_change.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_record_change.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_record_change.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_record_change.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_record_change.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_record_change.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_rchg_rec ON tms_record_change (record_id);
+
+-- 鍩硅璧勬枡褰掓。锛堢數瀛�/绾歌川/瀹炴搷璁板綍鍙岀粨鍚堬級
+CREATE TABLE IF NOT EXISTS tms_archive_file (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ record_id varchar(50) NOT NULL,
+ task_id varchar(50),
+ archive_type varchar(20),
+ file_json text,
+ archive_time timestamp,
+ archiver_id varchar(50),
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_archive_file PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_archive_file IS '鍩硅璧勬枡褰掓。锛堢數瀛�/绾歌川/瀹炴搷璁板綍鍙岀粨鍚堬級';
+COMMENT ON COLUMN tms_archive_file.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_archive_file.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_archive_file.record_id IS '鍩硅璁板綍ID';
+COMMENT ON COLUMN tms_archive_file.task_id IS '浠诲姟ID';
+COMMENT ON COLUMN tms_archive_file.archive_type IS 'electronic鐢靛瓙 / paper绾歌川 / practice瀹炴搷妗f';
+COMMENT ON COLUMN tms_archive_file.file_json IS '褰掓。璧勬枡';
+COMMENT ON COLUMN tms_archive_file.archive_time IS '褰掓。鏃堕棿';
+COMMENT ON COLUMN tms_archive_file.archiver_id IS '褰掓。浜�';
+COMMENT ON COLUMN tms_archive_file.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_archive_file.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_archive_file.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_archive_file.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_archive_file.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_archive_file.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_archive_file.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_archive_file.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_afile_rec ON tms_archive_file (record_id);
+
+-- ---------------------------------------------------------------------------
+-- 5. 鑰冭瘯涓庤�冩牳
+-- ---------------------------------------------------------------------------
+-- 鍦ㄧ嚎鑰冭瘯绛斿嵎銆備腑閫旈��鍑哄彲缁�冿紱鎻愪氦鍚庡瑙傞鑷姩璇勫垎锛屾湁涓昏棰樿繘闃呭嵎銆�
+CREATE TABLE IF NOT EXISTS tms_exam (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ task_id varchar(50) NOT NULL,
+ person_task_id varchar(50),
+ record_id varchar(50),
+ paper_id varchar(50),
+ paper_name varchar(300),
+ user_id varchar(50) NOT NULL,
+ attempt_no int NOT NULL DEFAULT 1,
+ start_time timestamp,
+ submit_time timestamp,
+ duration_min int,
+ objective_score numeric(8,1),
+ subjective_score numeric(8,1),
+ total_score numeric(8,1),
+ pass_score numeric(8,1),
+ pass_flag varchar(20),
+ grade_status varchar(20) NOT NULL DEFAULT 'auto',
+ grader_id varchar(50),
+ grade_time timestamp,
+ exam_status varchar(20) NOT NULL DEFAULT 'doing',
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_exam PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_exam IS '鍦ㄧ嚎鑰冭瘯绛斿嵎銆備腑閫旈��鍑哄彲缁�冿紱鎻愪氦鍚庡瑙傞鑷姩璇勫垎锛屾湁涓昏棰樿繘闃呭嵎銆�';
+COMMENT ON COLUMN tms_exam.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_exam.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_exam.task_id IS '鍩硅浠诲姟';
+COMMENT ON COLUMN tms_exam.person_task_id IS '涓汉浠诲姟';
+COMMENT ON COLUMN tms_exam.record_id IS '鍩硅璁板綍';
+COMMENT ON COLUMN tms_exam.paper_id IS '褰撴椂璇曞嵎ID';
+COMMENT ON COLUMN tms_exam.paper_name IS '璇曞嵎鍚嶇О蹇収';
+COMMENT ON COLUMN tms_exam.user_id IS '鑰冪敓';
+COMMENT ON COLUMN tms_exam.attempt_no IS '绗嚑娆¤�冭瘯';
+COMMENT ON COLUMN tms_exam.start_time IS '寮�濮嬩綔绛�';
+COMMENT ON COLUMN tms_exam.submit_time IS '浜ゅ嵎鏃堕棿';
+COMMENT ON COLUMN tms_exam.duration_min IS '褰撴椂鏃堕暱蹇収';
+COMMENT ON COLUMN tms_exam.objective_score IS '瀹㈣棰樺緱鍒�';
+COMMENT ON COLUMN tms_exam.subjective_score IS '涓昏棰樺緱鍒�';
+COMMENT ON COLUMN tms_exam.total_score IS '鎬诲垎';
+COMMENT ON COLUMN tms_exam.pass_score IS '褰撴椂鍚堟牸鍒嗗揩鐓�';
+COMMENT ON COLUMN tms_exam.pass_flag IS 'pass/fail';
+COMMENT ON COLUMN tms_exam.grade_status IS 'auto鏃犻渶闃呭嵎 / pending寰呮壒鏀� / graded宸叉壒鏀�';
+COMMENT ON COLUMN tms_exam.grader_id IS '闃呭嵎鑰佸笀';
+COMMENT ON COLUMN tms_exam.grade_time IS '闃呭嵎鏃堕棿';
+COMMENT ON COLUMN tms_exam.exam_status IS 'doing鑰冭瘯涓� / submitted宸蹭氦鍗� / cancelled宸插彇娑�';
+COMMENT ON COLUMN tms_exam.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_exam.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_exam.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_exam.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_exam.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_exam.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_exam.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_exam_task_user ON tms_exam (task_id, user_id, attempt_no);
+CREATE INDEX IF NOT EXISTS idx_tms_exam_grade ON tms_exam (grade_status);
+CREATE INDEX IF NOT EXISTS idx_tms_exam_user ON tms_exam (user_id);
+
+-- 绛斿嵎璇曢蹇収锛氶鐩�/閫夐」/绛旀/鍒嗘暟淇濈暀鑰冭瘯褰撴椂鐘舵�侊紝鍚庣画鏀归鏀瑰嵎涓嶅奖鍝嶃��
+CREATE TABLE IF NOT EXISTS tms_exam_item (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ question_id varchar(50),
+ question_type varchar(20),
+ stem text,
+ options_json text,
+ correct_answer text,
+ user_answer text,
+ score numeric(8,1),
+ got_score numeric(8,1),
+ is_subjective varchar(10) NOT NULL DEFAULT '0',
+ analysis text,
+ sort_no int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_exam_item PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_exam_item IS '绛斿嵎璇曢蹇収锛氶鐩�/閫夐」/绛旀/鍒嗘暟淇濈暀鑰冭瘯褰撴椂鐘舵�侊紝鍚庣画鏀归鏀瑰嵎涓嶅奖鍝嶃��';
+COMMENT ON COLUMN tms_exam_item.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_exam_item.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_exam_item.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_exam_item.question_id IS '鍘熻瘯棰業D';
+COMMENT ON COLUMN tms_exam_item.question_type IS '棰樺瀷蹇収';
+COMMENT ON COLUMN tms_exam_item.stem IS '棰樺共蹇収';
+COMMENT ON COLUMN tms_exam_item.options_json IS '閫夐」蹇収 JSON';
+COMMENT ON COLUMN tms_exam_item.correct_answer IS '褰撴椂姝g‘绛旀';
+COMMENT ON COLUMN tms_exam_item.user_answer IS '鑰冪敓浣滅瓟';
+COMMENT ON COLUMN tms_exam_item.score IS '鏈婊″垎';
+COMMENT ON COLUMN tms_exam_item.got_score IS '寰楀垎';
+COMMENT ON COLUMN tms_exam_item.is_subjective IS '鏄惁涓昏棰�';
+COMMENT ON COLUMN tms_exam_item.analysis IS '瑙f瀽蹇収';
+COMMENT ON COLUMN tms_exam_item.sort_no IS '璇曞嵎鍐呴『搴�';
+COMMENT ON COLUMN tms_exam_item.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_exam_item.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_exam_item.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_exam_item.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_exam_item.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_eitem_fid ON tms_exam_item (f_foreign_id);
+
+-- 瀹炴搷鑰冩牳涓昏〃锛屼繚瀛樺悗鍥炲啓鍩硅璁板綍
+CREATE TABLE IF NOT EXISTS tms_practice (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ task_id varchar(50) NOT NULL,
+ record_id varchar(50),
+ teacher_id varchar(50),
+ practice_time timestamp,
+ remark varchar(500),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_practice PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_practice IS '瀹炴搷鑰冩牳涓昏〃锛屼繚瀛樺悗鍥炲啓鍩硅璁板綍';
+COMMENT ON COLUMN tms_practice.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_practice.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_practice.task_id IS '鍩硅浠诲姟';
+COMMENT ON COLUMN tms_practice.record_id IS '鍩硅璁板綍';
+COMMENT ON COLUMN tms_practice.teacher_id IS '鑰冩牳浜�';
+COMMENT ON COLUMN tms_practice.practice_time IS '鑰冩牳鏃堕棿';
+COMMENT ON COLUMN tms_practice.remark IS '澶囨敞';
+COMMENT ON COLUMN tms_practice.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_practice.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_practice.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_practice.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_practice.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_practice.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_practice.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_prac_task ON tms_practice (task_id);
+
+-- 瀹炴搷鑰冩牳鏄庣粏
+CREATE TABLE IF NOT EXISTS tms_practice_item (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ user_id varchar(50) NOT NULL,
+ content text,
+ score numeric(8,1),
+ result_flag varchar(20),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_practice_item PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_practice_item IS '瀹炴搷鑰冩牳鏄庣粏';
+COMMENT ON COLUMN tms_practice_item.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_practice_item.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_practice_item.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_practice_item.user_id IS '鍩硅瀵硅薄';
+COMMENT ON COLUMN tms_practice_item.content IS '鑰冩牳鍐呭';
+COMMENT ON COLUMN tms_practice_item.score IS '鍒嗘暟';
+COMMENT ON COLUMN tms_practice_item.result_flag IS '鍚堟牸/涓嶅悎鏍�';
+COMMENT ON COLUMN tms_practice_item.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_practice_item.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_practice_item.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_practice_item.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_practice_item.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_praci_fid ON tms_practice_item (f_foreign_id);
+
+-- 鐜板満鎻愰棶鑰冩牳鎵撳垎锛屼繚瀛樺悗鍥炲啓鍩硅璁板綍
+CREATE TABLE IF NOT EXISTS tms_quiz_score (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ task_id varchar(50) NOT NULL,
+ record_id varchar(50),
+ user_id varchar(50) NOT NULL,
+ question text,
+ answer text,
+ score numeric(8,1),
+ teacher_id varchar(50),
+ quiz_time timestamp,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_quiz_score PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_quiz_score IS '鐜板満鎻愰棶鑰冩牳鎵撳垎锛屼繚瀛樺悗鍥炲啓鍩硅璁板綍';
+COMMENT ON COLUMN tms_quiz_score.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_quiz_score.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_quiz_score.task_id IS '鍩硅浠诲姟';
+COMMENT ON COLUMN tms_quiz_score.record_id IS '鍩硅璁板綍';
+COMMENT ON COLUMN tms_quiz_score.user_id IS '鍩硅瀵硅薄';
+COMMENT ON COLUMN tms_quiz_score.question IS '鎻愰棶鍐呭';
+COMMENT ON COLUMN tms_quiz_score.answer IS '鍥炵瓟';
+COMMENT ON COLUMN tms_quiz_score.score IS '鍒嗘暟';
+COMMENT ON COLUMN tms_quiz_score.teacher_id IS '鎻愰棶浜�';
+COMMENT ON COLUMN tms_quiz_score.quiz_time IS '鏃堕棿';
+COMMENT ON COLUMN tms_quiz_score.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_quiz_score.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_quiz_score.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_quiz_score.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_quiz_score.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_quiz_score.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_quiz_score.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_qscore_task ON tms_quiz_score (task_id);
+CREATE INDEX IF NOT EXISTS idx_tms_qscore_user ON tms_quiz_score (user_id);
+
+-- ---------------------------------------------------------------------------
+-- 6. 涓汉妗f
+-- ---------------------------------------------------------------------------
+-- 涓汉鍩硅妗f銆傚叆鑱岃嚜鍔ㄥ缓妗o紱涓�浜轰竴妗c��
+CREATE TABLE IF NOT EXISTS tms_person_file (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ archive_no varchar(50) NOT NULL,
+ archive_date date,
+ user_id varchar(50) NOT NULL,
+ user_name varchar(100),
+ dept_id varchar(50),
+ hire_date date,
+ leave_date date,
+ main_post_id varchar(50),
+ part_post_id varchar(50),
+ biz_status varchar(20) NOT NULL DEFAULT 'valid',
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_person_file PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_person_file IS '涓汉鍩硅妗f銆傚叆鑱岃嚜鍔ㄥ缓妗o紱涓�浜轰竴妗c��';
+COMMENT ON COLUMN tms_person_file.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_person_file.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_person_file.archive_no IS '妗f缂栧彿 AR+YYYY+4';
+COMMENT ON COLUMN tms_person_file.archive_date IS '寤烘。鏃堕棿';
+COMMENT ON COLUMN tms_person_file.user_id IS '鍛樺伐';
+COMMENT ON COLUMN tms_person_file.user_name IS '濮撳悕鍐椾綑';
+COMMENT ON COLUMN tms_person_file.dept_id IS '鎵�灞為儴闂�';
+COMMENT ON COLUMN tms_person_file.hire_date IS '鍏ヨ亴鏃堕棿';
+COMMENT ON COLUMN tms_person_file.leave_date IS '绂昏亴鏃堕棿';
+COMMENT ON COLUMN tms_person_file.main_post_id IS '涓昏宀椾綅';
+COMMENT ON COLUMN tms_person_file.part_post_id IS '鍏艰亴宀椾綅';
+COMMENT ON COLUMN tms_person_file.biz_status IS 'valid鍦ㄨ亴 / left绂昏亴';
+COMMENT ON COLUMN tms_person_file.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_person_file.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_person_file.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_person_file.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_person_file.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_person_file.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_person_file.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_pfile_user ON tms_person_file (user_id) WHERE f_delete_mark = 0;
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_pfile_no ON tms_person_file (archive_no) WHERE f_delete_mark = 0;
+
+-- 涓汉鍩硅妗f-宸ヤ綔灞ュ巻
+CREATE TABLE IF NOT EXISTS tms_person_work (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ company_name varchar(200),
+ post_name varchar(100),
+ hire_date date,
+ leave_date date,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ CONSTRAINT pk_tms_person_work PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_person_work IS '涓汉鍩硅妗f-宸ヤ綔灞ュ巻';
+COMMENT ON COLUMN tms_person_work.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_person_work.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_person_work.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_person_work.company_name IS '鍏徃鍚嶇О';
+COMMENT ON COLUMN tms_person_work.post_name IS '浠昏亴宀椾綅';
+COMMENT ON COLUMN tms_person_work.hire_date IS '鍏ヨ亴鏃堕棿';
+COMMENT ON COLUMN tms_person_work.leave_date IS '绂昏亴鏃堕棿';
+COMMENT ON COLUMN tms_person_work.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_person_work.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_person_work.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_person_work.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_person_work.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+CREATE INDEX IF NOT EXISTS idx_tms_pwork_fid ON tms_person_work (f_foreign_id);
+
+-- 璧勮川鏂囦欢/鑾峰緱璇佷功銆傝祫璐ㄦ枃浠剁鐞嗕笌妗f瀛愯〃鍏辩敤姝よ〃銆�
+CREATE TABLE IF NOT EXISTS tms_person_cert (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ f_foreign_id varchar(50) NOT NULL,
+ archive_id varchar(50),
+ user_id varchar(50),
+ cert_no varchar(100),
+ cert_name varchar(200),
+ gain_date date,
+ expire_date date,
+ cert_file text,
+ cert_status varchar(20),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_person_cert PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_person_cert IS '璧勮川鏂囦欢/鑾峰緱璇佷功銆傝祫璐ㄦ枃浠剁鐞嗕笌妗f瀛愯〃鍏辩敤姝よ〃銆�';
+COMMENT ON COLUMN tms_person_cert.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_person_cert.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_person_cert.f_foreign_id IS '涓昏〃f_id';
+COMMENT ON COLUMN tms_person_cert.archive_id IS '涓汉妗fID锛屾棤澶栭敭瀛楁鏃剁敱涓讳粠鍐欏叆f_foreign_id';
+COMMENT ON COLUMN tms_person_cert.user_id IS '鍛樺伐锛屽垪琛ㄦā鍧楃敤';
+COMMENT ON COLUMN tms_person_cert.cert_no IS '璇佷功缂栧彿';
+COMMENT ON COLUMN tms_person_cert.cert_name IS '璇佷功鍚嶇О';
+COMMENT ON COLUMN tms_person_cert.gain_date IS '鑾峰緱鏃堕棿';
+COMMENT ON COLUMN tms_person_cert.expire_date IS '鏈夋晥鏈熻嚦';
+COMMENT ON COLUMN tms_person_cert.cert_file IS '璇佷功闄勪欢';
+COMMENT ON COLUMN tms_person_cert.cert_status IS 'valid鏈夋晥 / near杩戞晥鏈� / invalid鏃犳晥';
+COMMENT ON COLUMN tms_person_cert.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_person_cert.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_person_cert.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_person_cert.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_person_cert.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_person_cert.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_person_cert.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_pcert_fid ON tms_person_cert (f_foreign_id);
+CREATE INDEX IF NOT EXISTS idx_tms_pcert_user ON tms_person_cert (user_id);
+
+-- 涓汉鍩硅鐩綍锛堝綊妗e揩鐓э級銆傝褰曞綊妗e悗鍐欏叆锛屾弧瓒冲璁°��
+CREATE TABLE IF NOT EXISTS tms_person_train (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ archive_id varchar(50) NOT NULL,
+ user_id varchar(50) NOT NULL,
+ record_id varchar(50),
+ record_no varchar(50),
+ category varchar(50),
+ subject text,
+ train_mode varchar(50),
+ teacher_id text,
+ eval_mode varchar(50),
+ pass_flag varchar(20),
+ start_time timestamp,
+ end_time timestamp,
+ hours numeric(8,1),
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_person_train PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_person_train IS '涓汉鍩硅鐩綍锛堝綊妗e揩鐓э級銆傝褰曞綊妗e悗鍐欏叆锛屾弧瓒冲璁°��';
+COMMENT ON COLUMN tms_person_train.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_person_train.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_person_train.archive_id IS '涓汉妗fID';
+COMMENT ON COLUMN tms_person_train.user_id IS '鍛樺伐';
+COMMENT ON COLUMN tms_person_train.record_id IS '鍩硅璁板綍ID';
+COMMENT ON COLUMN tms_person_train.record_no IS '鍩硅璁板綍缂栧彿';
+COMMENT ON COLUMN tms_person_train.category IS '鍩硅绫诲瀷/鍒嗙被';
+COMMENT ON COLUMN tms_person_train.subject IS '鍩硅鍐呭';
+COMMENT ON COLUMN tms_person_train.train_mode IS '鍩硅鏂瑰紡';
+COMMENT ON COLUMN tms_person_train.teacher_id IS '鍩硅甯�';
+COMMENT ON COLUMN tms_person_train.eval_mode IS '鑰冩牳鏂瑰紡';
+COMMENT ON COLUMN tms_person_train.pass_flag IS '鏄惁鍚堟牸';
+COMMENT ON COLUMN tms_person_train.start_time IS '鍩硅寮�濮嬫椂闂�';
+COMMENT ON COLUMN tms_person_train.end_time IS '鍩硅缁撴潫鏃堕棿';
+COMMENT ON COLUMN tms_person_train.hours IS '瀛︽椂';
+COMMENT ON COLUMN tms_person_train.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_person_train.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_person_train.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_person_train.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_person_train.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_person_train.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_person_train.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_ptrain_user ON tms_person_train (user_id);
+CREATE INDEX IF NOT EXISTS idx_tms_ptrain_arch ON tms_person_train (archive_id);
+CREATE INDEX IF NOT EXISTS idx_tms_ptrain_rec ON tms_person_train (record_id);
+
+-- ---------------------------------------------------------------------------
+-- 7. 鍏朵粬娴佺▼涓庨厤缃�
+-- ---------------------------------------------------------------------------
+-- 澶栧嚭鍩硅
+CREATE TABLE IF NOT EXISTS tms_out_train (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ apply_no varchar(50),
+ applicant_id varchar(50),
+ apply_dept_id varchar(50),
+ org_name varchar(200),
+ subject varchar(500),
+ start_time timestamp,
+ end_time timestamp,
+ hours numeric(8,1),
+ file_json text,
+ biz_status varchar(20),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_out_train PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_out_train IS '澶栧嚭鍩硅';
+COMMENT ON COLUMN tms_out_train.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_out_train.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_out_train.apply_no IS '鐢宠鍗曞彿';
+COMMENT ON COLUMN tms_out_train.applicant_id IS '鐢宠浜�';
+COMMENT ON COLUMN tms_out_train.apply_dept_id IS '鐢宠閮ㄩ棬';
+COMMENT ON COLUMN tms_out_train.org_name IS '澶栭儴鏈烘瀯';
+COMMENT ON COLUMN tms_out_train.subject IS '鍩硅涓婚';
+COMMENT ON COLUMN tms_out_train.start_time IS '寮�濮�';
+COMMENT ON COLUMN tms_out_train.end_time IS '缁撴潫';
+COMMENT ON COLUMN tms_out_train.hours IS '瀛︽椂';
+COMMENT ON COLUMN tms_out_train.file_json IS '璧勬枡闄勪欢';
+COMMENT ON COLUMN tms_out_train.biz_status IS '瀹℃壒鐘舵��';
+COMMENT ON COLUMN tms_out_train.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_out_train.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_out_train.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_out_train.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_out_train.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_out_train.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_out_train.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_out_train.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_out_train.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_out_train.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_out_no ON tms_out_train (apply_no) WHERE f_delete_mark = 0;
+
+-- 杞矖浜哄憳鑰冩牳閴村畾
+CREATE TABLE IF NOT EXISTS tms_transfer_eval (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ user_id varchar(50) NOT NULL,
+ from_post_id varchar(50),
+ to_post_id varchar(50),
+ eval_result varchar(50),
+ remark text,
+ biz_status varchar(20),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_transfer_eval PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_transfer_eval IS '杞矖浜哄憳鑰冩牳閴村畾';
+COMMENT ON COLUMN tms_transfer_eval.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_transfer_eval.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_transfer_eval.user_id IS '杞矖浜哄憳';
+COMMENT ON COLUMN tms_transfer_eval.from_post_id IS '鍘熷矖浣�';
+COMMENT ON COLUMN tms_transfer_eval.to_post_id IS '鏂板矖浣�';
+COMMENT ON COLUMN tms_transfer_eval.eval_result IS '閴村畾缁撹';
+COMMENT ON COLUMN tms_transfer_eval.remark IS '璇存槑';
+COMMENT ON COLUMN tms_transfer_eval.biz_status IS '瀹℃壒鐘舵��';
+COMMENT ON COLUMN tms_transfer_eval.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_transfer_eval.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_transfer_eval.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_transfer_eval.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_transfer_eval.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_transfer_eval.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_transfer_eval.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_transfer_eval.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_transfer_eval.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_transfer_eval.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_teval_user ON tms_transfer_eval (user_id);
+
+-- 鏂板憳宸ュ煿璁晥鏋滆�冭瘎
+CREATE TABLE IF NOT EXISTS tms_newcomer_eval (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ user_id varchar(50) NOT NULL,
+ eval_result varchar(50),
+ remark text,
+ biz_status varchar(20),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_newcomer_eval PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_newcomer_eval IS '鏂板憳宸ュ煿璁晥鏋滆�冭瘎';
+COMMENT ON COLUMN tms_newcomer_eval.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_newcomer_eval.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_newcomer_eval.user_id IS '鏂板憳宸�';
+COMMENT ON COLUMN tms_newcomer_eval.eval_result IS '鑰冭瘎缁撹';
+COMMENT ON COLUMN tms_newcomer_eval.remark IS '璇存槑';
+COMMENT ON COLUMN tms_newcomer_eval.biz_status IS '瀹℃壒鐘舵��';
+COMMENT ON COLUMN tms_newcomer_eval.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_newcomer_eval.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_newcomer_eval.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_newcomer_eval.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_newcomer_eval.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_newcomer_eval.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_newcomer_eval.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_newcomer_eval.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_newcomer_eval.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_newcomer_eval.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_neval_user ON tms_newcomer_eval (user_id);
+
+-- 澶嶅矖鍛樺伐鍩硅鏁堟灉鑰冭瘎
+CREATE TABLE IF NOT EXISTS tms_return_eval (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ user_id varchar(50) NOT NULL,
+ eval_result varchar(50),
+ remark text,
+ biz_status varchar(20),
+ f_flow_id varchar(50),
+ f_flow_task_id varchar(50),
+ f_flow_state int,
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_return_eval PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_return_eval IS '澶嶅矖鍛樺伐鍩硅鏁堟灉鑰冭瘎';
+COMMENT ON COLUMN tms_return_eval.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_return_eval.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_return_eval.user_id IS '澶嶅矖鍛樺伐';
+COMMENT ON COLUMN tms_return_eval.eval_result IS '鑰冭瘎缁撹';
+COMMENT ON COLUMN tms_return_eval.remark IS '璇存槑';
+COMMENT ON COLUMN tms_return_eval.biz_status IS '瀹℃壒鐘舵��';
+COMMENT ON COLUMN tms_return_eval.f_flow_id IS '娴佺▼妯℃澘ID';
+COMMENT ON COLUMN tms_return_eval.f_flow_task_id IS '娴佺▼浠诲姟ID';
+COMMENT ON COLUMN tms_return_eval.f_flow_state IS '娴佺▼鐘舵��';
+COMMENT ON COLUMN tms_return_eval.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_return_eval.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_return_eval.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_return_eval.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_return_eval.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_return_eval.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_return_eval.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_reval_user ON tms_return_eval (user_id);
+
+-- 鍩硅璁板綍濂楁墦妯℃澘鐗堟湰銆傛寜鍩硅寮�濮嬫椂闂村尮閰嶇敓鏁堢増鏈��
+CREATE TABLE IF NOT EXISTS tms_print_template (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ tpl_code varchar(50) NOT NULL,
+ version_no int NOT NULL,
+ effective_from date NOT NULL,
+ effective_to date,
+ file_json text,
+ enabled varchar(10) NOT NULL DEFAULT '1',
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_print_template PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_print_template IS '鍩硅璁板綍濂楁墦妯℃澘鐗堟湰銆傛寜鍩硅寮�濮嬫椂闂村尮閰嶇敓鏁堢増鏈��';
+COMMENT ON COLUMN tms_print_template.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_print_template.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_print_template.tpl_code IS '妯℃澘缂栫爜锛屽 TRAIN_RECORD';
+COMMENT ON COLUMN tms_print_template.version_no IS '鐗堟湰鍙�';
+COMMENT ON COLUMN tms_print_template.effective_from IS '鐢熸晥璧峰锛堟寜鍩硅寮�濮嬫椂闂寸储寮曪級';
+COMMENT ON COLUMN tms_print_template.effective_to IS '鐢熸晥鎴锛岀┖=褰撳墠';
+COMMENT ON COLUMN tms_print_template.file_json IS '妯℃澘鏂囦欢';
+COMMENT ON COLUMN tms_print_template.enabled IS '鍚敤';
+COMMENT ON COLUMN tms_print_template.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_print_template.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_print_template.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_print_template.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_print_template.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_print_template.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_print_template.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE INDEX IF NOT EXISTS idx_tms_ptpl_code ON tms_print_template (tpl_code, effective_from);
+
+-- 鎻愰啋瑙勫垯锛氳鍒掑埌鏈熷墠涓�涓湀銆佹巿鏉冨埌鏈熴�佷釜浜哄矖浣嶅煿璁椂闄愮瓑
+CREATE TABLE IF NOT EXISTS tms_remind_rule (
+ f_id varchar(50) NOT NULL,
+ f_tenant_id varchar(50),
+ rule_code varchar(50) NOT NULL,
+ rule_name varchar(100),
+ biz_type varchar(50),
+ days_before int NOT NULL DEFAULT 30,
+ notify_roles varchar(200),
+ enabled varchar(10) NOT NULL DEFAULT '1',
+ f_creator_user_id varchar(50),
+ f_creator_time timestamp,
+ f_last_modify_user_id varchar(50),
+ f_last_modify_time timestamp,
+ f_delete_mark int NOT NULL DEFAULT 0,
+ f_delete_user_id varchar(50),
+ f_delete_time timestamp,
+ CONSTRAINT pk_tms_remind_rule PRIMARY KEY (f_id)
+);
+COMMENT ON TABLE tms_remind_rule IS '鎻愰啋瑙勫垯锛氳鍒掑埌鏈熷墠涓�涓湀銆佹巿鏉冨埌鏈熴�佷釜浜哄矖浣嶅煿璁椂闄愮瓑';
+COMMENT ON COLUMN tms_remind_rule.f_id IS '涓婚敭';
+COMMENT ON COLUMN tms_remind_rule.f_tenant_id IS '绉熸埛';
+COMMENT ON COLUMN tms_remind_rule.rule_code IS '瑙勫垯缂栫爜';
+COMMENT ON COLUMN tms_remind_rule.rule_name IS '鍚嶇О';
+COMMENT ON COLUMN tms_remind_rule.biz_type IS 'annual_plan/admin_auth/person_post/task_overdue';
+COMMENT ON COLUMN tms_remind_rule.days_before IS '鎻愬墠澶╂暟';
+COMMENT ON COLUMN tms_remind_rule.notify_roles IS '閫氱煡瑙掕壊锛氶儴闂ㄥ煿璁鐞嗗憳,鍩硅甯�,閮ㄩ棬棰嗗';
+COMMENT ON COLUMN tms_remind_rule.enabled IS '鍚敤';
+COMMENT ON COLUMN tms_remind_rule.f_creator_user_id IS '鍒涘缓浜�';
+COMMENT ON COLUMN tms_remind_rule.f_creator_time IS '鍒涘缓鏃堕棿';
+COMMENT ON COLUMN tms_remind_rule.f_last_modify_user_id IS '淇敼浜�';
+COMMENT ON COLUMN tms_remind_rule.f_last_modify_time IS '淇敼鏃堕棿';
+COMMENT ON COLUMN tms_remind_rule.f_delete_mark IS '鍒犻櫎鏍囪 0姝e父 1鍒犻櫎';
+COMMENT ON COLUMN tms_remind_rule.f_delete_user_id IS '鍒犻櫎浜�';
+COMMENT ON COLUMN tms_remind_rule.f_delete_time IS '鍒犻櫎鏃堕棿';
+CREATE UNIQUE INDEX IF NOT EXISTS uk_tms_remind_code ON tms_remind_rule (rule_code) WHERE f_delete_mark = 0;
+
+
+-- =============================================================================
+-- 棰勭疆鏁版嵁锛堝煿璁柟寮� / 绛惧埌鏂瑰紡 / 璇勪及鏂瑰紡 / 鎻愰啋瑙勫垯锛�
+-- =============================================================================
+INSERT INTO tms_train_mode (f_id, mode_code, mode_name, sign_rule, allow_guest_sign, same_day_required, place_required, sort_no, enabled, f_delete_mark)
+VALUES
+ ('tms_mode_onsite', 'onsite', '闆嗕腑鎺堣', 'scan', '1', '1', '1', 1, '1', 0),
+ ('tms_mode_practice', 'practice', '鎿嶄綔鎺堣', 'scan', '0', '1', '1', 2, '1', 0),
+ ('tms_mode_online', 'online', '鍦ㄧ嚎瀛︿範', 'both', '0', '0', '0', 3, '1', 0)
+ON CONFLICT (f_id) DO NOTHING;
+
+INSERT INTO tms_sign_mode (f_id, mode_code, mode_name, tip_seconds, match_roster, enabled, f_delete_mark)
+VALUES
+ ('tms_sign_app', 'app_scan', 'APP鎵爜', 30, '1', '1', 0),
+ ('tms_sign_wx', 'wx_scan', '寰俊鎵爜', 30, '1', '1', 0),
+ ('tms_sign_online', 'online', '鍦ㄧ嚎绛惧埌', 30, '1', '1', 0)
+ON CONFLICT (f_id) DO NOTHING;
+
+INSERT INTO tms_eval_mode (f_id, mode_code, mode_name, need_paper, need_quiz, need_practice, enabled, f_delete_mark)
+VALUES
+ ('tms_eval_quiz', 'quiz', '鎻愰棶', '0', '1', '0', '1', 0),
+ ('tms_eval_practice', 'practice', '鐜板満鎿嶄綔', '0', '0', '1', '1', 0),
+ ('tms_eval_exam', 'exam', '鍦ㄧ嚎鑰冭瘯', '1', '0', '0', '1', 0),
+ ('tms_eval_none', 'none', '鏃犻渶鑰冩牳', '0', '0', '0', '1', 0)
+ON CONFLICT (f_id) DO NOTHING;
+
+INSERT INTO tms_remind_rule (f_id, rule_code, rule_name, biz_type, days_before, notify_roles, enabled, f_delete_mark)
+VALUES
+ ('tms_rm_annual', 'annual_due', '骞村害璁″垝鍒版湡鍓嶄竴涓湀', 'annual_plan', 30, '閮ㄩ棬鍩硅绠$悊鍛�,鍩硅甯�', '1', 0),
+ ('tms_rm_auth', 'auth_due', '绠$悊鍛樻巿鏉冨埌鏈熷墠涓�涓湀', 'admin_auth', 30, '鍩硅绠$悊鍛�,鍩硅甯�', '1', 0),
+ ('tms_rm_overdue','task_overdue','鍩硅閫炬湡鎻愰啋閮ㄩ棬棰嗗', 'task_overdue', 0, '閮ㄩ棬棰嗗', '1', 0)
+ON CONFLICT (f_id) DO NOTHING;
+
+COMMIT;
--
Gitblit v1.8.0