Files
nanguangszwlback/sql/20260817_expense_account_two_level.sql
T
rcx 77420e9617 feat(sys):合同附件增加原始文件名存储字段,配合上传v2回显原名称
需求背景:合同管理-上传的文件需显示原始文件名(原显示 LOCAL:D:\upload\{uuid}.pdf 之类存储键)。
附件此前仅存 fileKey,原始文件名在上传落盘时已被 UUID 重命名丢失,回显无原名可用。
改动内容:
1. contract_manage 表新增 4 个附件原始文件名字段(见 sql/20260818_contract_attachment_original_name.sql):
   contract_original_name    合同正本附件原始文件名
   integrity_agreement_name  廉政协议附件原始文件名
   security_protocol_name    安全协议附件原始文件名
   other_attachments_name    其他附件原始文件名(多文件与 other_attachments_url 同分隔符、同顺序)
2. ContractManage / ContractManagePO / ContractManageDO / ContractManageDTO
   四个对象同步新增对应 4 个 name 字段,保存、详情、列表全链路透传。
   Assembler 与 ContractManageImpl 为 BeanUtils 同名拷贝、Mapper XML 为 SELECT a.*,均无需改动。"
 "配套依赖:
- mhd-product 新增 /menu/upload/v2 返回 { fileKey, originalName }(另一提交)
- 前端上传后成对保存 fileKey 与 originalName,回显显示 name 字段
兼容说明:
- 存量合同 name 字段为空,前端回退显示 fileKey 末段(uuid 名),属预期兼容行为
- 纯新增字段,旧代码不读写,不影响既有接口
2026-08-19 18:08:59 +08:00

252 lines
15 KiB
SQL
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
-- ============================================================================
-- 费用科目两级化改造脚本(费用统计分析报表前置主数据改造)
-- 日期 : 2026-08-17
-- 数据库 : 达梦 DM8Oracle 兼容语法)
-- 目标库 : 测试库 192.168.0.49:5236NGWL_TEST_SYSTEM / NGWL_TEST_BMS,生产执行前替换 schema
-- 背景 :
-- 现有费用科目全部为平级一级科目(恒温仓仓租/水费/运费...),费用统计分析报表
-- 需要"一级科目(费用类别) - 二级科目(具体费用项)"两级结构(模板:仓储收入/散租...)。
-- 运行时解析逻辑(BusinessDocumentApplicationService.getSubInfoByCode2 分支)完全由
-- EXPENSE_ACCOUNT 的 first_subject_flag + upper_subject_code 驱动,
-- 因此只需重挂主数据树 + 刷历史冗余字段,业务代码零改动。
--
-- ⚠️ 执行顺序严格按步骤,每步执行后核对验证输出再继续。
-- ⚠️ 生产执行前必须:1)已完成测试库验证 2)停业务推送或低峰期执行 3)先执行步骤0备份
-- ============================================================================
-- ============================================================================
-- 步骤 0.1 盘点现状(只读,执行后人工核对科目清单与 TOP_ORGANIZATION_ID
-- ============================================================================
SELECT SUBJECT_CODE, SUBJECT_NAME, FIRST_SUBJECT_FLAG, UPPER_SUBJECT_CODE,
UPPER_SUBJECT, STATUS, ACCOUNT_EXPENSE_TYPE, TOP_ORGANIZATION_ID, SHOW_SEQ
FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT
ORDER BY FIRST_SUBJECT_FLAG, SUBJECT_CODE;
-- 记下 TOP_ORGANIZATION_ID(下文新增一级科目要用同一个值,记为 :ORG_ID,示例按 2827
-- 记下现有科目里最大的 SHOW_SEQ(新一级科目排序用)
-- ============================================================================
-- 步骤 0.2 受影响行数盘点(只读;6 张表统一四列模式)
-- 条件 = FIRST_SUBJECT_CODE 命中映射表旧编码 且 SECOND_SUBJECT_CODE 为空
-- ============================================================================
SELECT 'BILLING_STATEMENT' AS TBL, COUNT(*) AS CNT FROM NGWL_TEST_BMS.BILLING_STATEMENT BS WHERE BS.SECOND_SUBJECT_CODE IS NULL AND BS.FIRST_SUBJECT_CODE IN ('2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006')
UNION ALL
SELECT 'BUSINESS_DOCUMENT', COUNT(*) FROM NGWL_TEST_BMS.BUSINESS_DOCUMENT BD WHERE BD.SECOND_SUBJECT_CODE IS NULL AND BD.FIRST_SUBJECT_CODE IN ('2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006')
UNION ALL
SELECT 'BILL_DETAIL', COUNT(*) FROM NGWL_TEST_BMS.BILL_DETAIL BD WHERE BD.SECOND_SUBJECT_CODE IS NULL AND BD.FIRST_SUBJECT_CODE IN ('2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006')
UNION ALL
SELECT 'BILLING_RULES', COUNT(*) FROM NGWL_TEST_BMS.BILLING_RULES BR WHERE BR.SECOND_SUBJECT_CODE IS NULL AND BR.FIRST_SUBJECT_CODE IN ('2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006')
UNION ALL
SELECT 'TASK_FLOW_RECORDS', COUNT(*) FROM NGWL_TEST_BMS.TASK_FLOW_RECORDS TF WHERE TF.SECOND_SUBJECT_CODE IS NULL AND TF.FIRST_SUBJECT_CODE IN ('2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006')
UNION ALL
SELECT 'CONTRACT_MANAGE_DETAIL', COUNT(*) FROM NGWL_TEST_SYSTEM.CONTRACT_MANAGE_DETAIL CD WHERE CD.SECOND_SUBJECT_CODE IS NULL AND CD.FIRST_SUBJECT_CODE IN ('2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006');
-- ============================================================================
-- 步骤 0.3 重复科目 TYLSCCSNCZ 引用检查(只读;决定后续是"仅重挂"还是"迁移引用后停用"
-- ============================================================================
SELECT 'LEASE' AS SRC, COUNT(*) AS CNT FROM NGWL_TEST_SYSTEM.LEASE L WHERE L.SECOND_SUBJECT_CODE = 'TYLSCCSNCZ'
UNION ALL
SELECT 'CONTRACT_MANAGE_DETAIL', COUNT(*) FROM NGWL_TEST_SYSTEM.CONTRACT_MANAGE_DETAIL CD WHERE CD.SECOND_SUBJECT_CODE = 'TYLSCCSNCZ'
UNION ALL
SELECT 'BILLING_RULES', COUNT(*) FROM NGWL_TEST_BMS.BILLING_RULES BR WHERE BR.SECOND_SUBJECT_CODE = 'TYLSCCSNCZ'
UNION ALL
SELECT 'BILLING_STATEMENT', COUNT(*) FROM NGWL_TEST_BMS.BILLING_STATEMENT BS WHERE BS.SECOND_SUBJECT_CODE = 'TYLSCCSNCZ';
-- ============================================================================
-- 步骤 0.5 备份(必须执行;回滚的唯一依靠)
-- ============================================================================
CREATE TABLE NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT_BAK_20260817 AS
SELECT * FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT;
-- 大表只备份科目四列 + 主键,避免整表复制
CREATE TABLE NGWL_TEST_BMS.SUBJ_BAK_20260817 AS
SELECT BILLING_STATEMENT_ID, FIRST_SUBJECT_CODE, FIRST_SUBJECT_NAME, SECOND_SUBJECT_CODE, SECOND_SUBJECT_NAME
FROM NGWL_TEST_BMS.BILLING_STATEMENT
WHERE SECOND_SUBJECT_CODE IS NULL
AND FIRST_SUBJECT_CODE IN ('2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006');
-- ============================================================================
-- 步骤 1 迁移映射表(本次改造的"事实清单",新旧对照唯一来源)
-- NEW_FIRST 编码为建议值【需业务确认,尤其与 NC 科目对照】,确认后如改动需同步改步骤2/3
-- ============================================================================
CREATE TABLE NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 (
OLD_CODE VARCHAR(100), -- 现平级科目编码(将成为二级科目编码,不变)
NEW_FIRST_CODE VARCHAR(100), -- 归属一级科目编码
NEW_FIRST_NAME VARCHAR(200)
);
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('2001', 'CCSR', '仓储收入'); -- 恒温仓仓租
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('2002', 'CCSR', '仓储收入'); -- 普通仓室内仓租
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('2003', 'CCSR', '仓储收入'); -- 临时仓储室内仓租
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('2004', 'CCSR', '仓储收入'); -- 室外空地仓租
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('TYLSCCSNCZ', 'CCSR', '仓储收入'); -- 临时仓储室内仓租(重复编码,本期仅重挂不停用)
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('1001', 'PSSR', '配送收入'); -- 运费
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('1007', 'ZZSR', '增值服务收入'); -- 装卸费
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('2005', 'WYSR', '物业收入'); -- 电费
INSERT INTO NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 VALUES ('2006', 'WYSR', '物业收入'); -- 水费
COMMIT;
-- ============================================================================
-- 步骤 2 新增 5 个一级科目(费用类别)
-- TOP_ORGANIZATION_ID 用步骤0.1盘出的 :ORG_ID(示例 2827);
-- SHOW_SEQ 排在现有科目之前(一级优先展示);ACCOUNT_EXPENSE_TYPE=1 收入侧
-- ============================================================================
INSERT INTO NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT
(TOP_ORGANIZATION_ID, SUBJECT_CODE, SUBJECT_NAME, SHOW_SEQ, FIRST_SUBJECT_FLAG,
UPPER_SUBJECT_CODE, UPPER_SUBJECT, STATUS, ACCOUNT_EXPENSE_TYPE, DEL_FLAG)
VALUES
(2827, 'CCSR', '仓储收入', 1, 1, NULL, NULL, 1, 1, 1),
(2827, 'PSSR', '配送收入', 2, 1, NULL, NULL, 1, 1, 1),
(2827, 'ZZSR', '增值服务收入', 3, 1, NULL, NULL, 1, 1, 1),
(2827, 'WYSR', '物业收入', 4, 1, NULL, NULL, 1, 1, 1),
(2827, 'QT', '其他', 9, 1, NULL, NULL, 1, 1, 1);
COMMIT;
-- ============================================================================
-- 步骤 3 现有平级科目降为二级并挂到一级下(编码/名称不变,只改树关系)
-- ============================================================================
UPDATE NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT EA
SET (EA.FIRST_SUBJECT_FLAG, EA.UPPER_SUBJECT_CODE, EA.UPPER_SUBJECT) =
(SELECT 2, M.NEW_FIRST_CODE, M.NEW_FIRST_NAME
FROM NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 M
WHERE M.OLD_CODE = EA.SUBJECT_CODE)
WHERE EXISTS (SELECT 1 FROM NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 M
WHERE M.OLD_CODE = EA.SUBJECT_CODE);
COMMIT;
-- 验证:SELECT * FROM ... WHERE FIRST_SUBJECT_FLAG=2 AND UPPER_SUBJECT_CODE IS NULL; -- 应为 0 行
-- ============================================================================
-- 步骤 4 刷历史冗余字段(6 张表,模式一致:旧一级 → 新二级,挂新一级)
-- 只动 FIRST_SUBJECT_CODE 命中映射且 SECOND_SUBJECT_CODE 为空的行(平级时期的存量)
-- ============================================================================
-- 4.1 计费流水(报表取数表,最重要)
MERGE INTO NGWL_TEST_BMS.BILLING_STATEMENT BS
USING NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 M
ON (BS.FIRST_SUBJECT_CODE = M.OLD_CODE AND BS.SECOND_SUBJECT_CODE IS NULL)
WHEN MATCHED THEN UPDATE SET
BS.SECOND_SUBJECT_CODE = M.OLD_CODE,
BS.SECOND_SUBJECT_NAME = (SELECT EA.SUBJECT_NAME FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT EA WHERE EA.SUBJECT_CODE = M.OLD_CODE),
BS.FIRST_SUBJECT_CODE = M.NEW_FIRST_CODE,
BS.FIRST_SUBJECT_NAME = M.NEW_FIRST_NAME;
COMMIT;
-- 4.2 业务单据
MERGE INTO NGWL_TEST_BMS.BUSINESS_DOCUMENT BD
USING NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 M
ON (BD.FIRST_SUBJECT_CODE = M.OLD_CODE AND BD.SECOND_SUBJECT_CODE IS NULL)
WHEN MATCHED THEN UPDATE SET
BD.SECOND_SUBJECT_CODE = M.OLD_CODE,
BD.SECOND_SUBJECT_NAME = (SELECT EA.SUBJECT_NAME FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT EA WHERE EA.SUBJECT_CODE = M.OLD_CODE),
BD.FIRST_SUBJECT_CODE = M.NEW_FIRST_CODE,
BD.FIRST_SUBJECT_NAME = M.NEW_FIRST_NAME;
COMMIT;
-- 4.3 账单明细
MERGE INTO NGWL_TEST_BMS.BILL_DETAIL BDL
USING NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 M
ON (BDL.FIRST_SUBJECT_CODE = M.OLD_CODE AND BDL.SECOND_SUBJECT_CODE IS NULL)
WHEN MATCHED THEN UPDATE SET
BDL.SECOND_SUBJECT_CODE = M.OLD_CODE,
BDL.SECOND_SUBJECT_NAME = (SELECT EA.SUBJECT_NAME FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT EA WHERE EA.SUBJECT_CODE = M.OLD_CODE),
BDL.FIRST_SUBJECT_CODE = M.NEW_FIRST_CODE,
BDL.FIRST_SUBJECT_NAME = M.NEW_FIRST_NAME;
COMMIT;
-- 4.4 计费规则
MERGE INTO NGWL_TEST_BMS.BILLING_RULES BR
USING NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 M
ON (BR.FIRST_SUBJECT_CODE = M.OLD_CODE AND BR.SECOND_SUBJECT_CODE IS NULL)
WHEN MATCHED THEN UPDATE SET
BR.SECOND_SUBJECT_CODE = M.OLD_CODE,
BR.SECOND_SUBJECT_NAME = (SELECT EA.SUBJECT_NAME FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT EA WHERE EA.SUBJECT_CODE = M.OLD_CODE),
BR.FIRST_SUBJECT_CODE = M.NEW_FIRST_CODE,
BR.FIRST_SUBJECT_NAME = M.NEW_FIRST_NAME;
COMMIT;
-- 4.5 任务流转记录
MERGE INTO NGWL_TEST_BMS.TASK_FLOW_RECORDS TF
USING NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 M
ON (TF.FIRST_SUBJECT_CODE = M.OLD_CODE AND TF.SECOND_SUBJECT_CODE IS NULL)
WHEN MATCHED THEN UPDATE SET
TF.SECOND_SUBJECT_CODE = M.OLD_CODE,
TF.SECOND_SUBJECT_NAME = (SELECT EA.SUBJECT_NAME FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT EA WHERE EA.SUBJECT_CODE = M.OLD_CODE),
TF.FIRST_SUBJECT_CODE = M.NEW_FIRST_CODE,
TF.FIRST_SUBJECT_NAME = M.NEW_FIRST_NAME;
COMMIT;
-- 4.6 合同明细(在 system 库;影响进行中的合同计费展示,不影响金额计算)
MERGE INTO NGWL_TEST_SYSTEM.CONTRACT_MANAGE_DETAIL CD
USING NGWL_TEST_SYSTEM.SUBJECT_MIG_MAP_20260817 M
ON (CD.FIRST_SUBJECT_CODE = M.OLD_CODE AND CD.SECOND_SUBJECT_CODE IS NULL)
WHEN MATCHED THEN UPDATE SET
CD.SECOND_SUBJECT_CODE = M.OLD_CODE,
CD.SECOND_SUBJECT_NAME = (SELECT EA.SUBJECT_NAME FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT EA WHERE EA.SUBJECT_CODE = M.OLD_CODE),
CD.FIRST_SUBJECT_CODE = M.NEW_FIRST_CODE,
CD.FIRST_SUBJECT_NAME = M.NEW_FIRST_NAME;
COMMIT;
-- ============================================================================
-- 步骤 5 验证(全部只读)
-- ============================================================================
-- 5.1 科目树:5 个一级 + 9 个二级,二级全部有上级
SELECT FIRST_SUBJECT_FLAG, SUBJECT_CODE, SUBJECT_NAME, UPPER_SUBJECT_CODE, STATUS
FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT
WHERE SUBJECT_CODE IN ('CCSR','PSSR','ZZSR','WYSR','QT','2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006')
ORDER BY FIRST_SUBJECT_FLAG, UPPER_SUBJECT_CODE, SUBJECT_CODE;
-- 5.2 报表口径守恒:刷数前后按月总金额必须一致(金额只挪科目不增减)
SELECT SUBSTR(TO_CHAR(BUSINESS_DATE,'YYYY-MM'),1,7) AS YM,
FIRST_SUBJECT_NAME, SECOND_SUBJECT_NAME, SUM(BILLING_AMOUNT) AS AMT
FROM NGWL_TEST_BMS.BILLING_STATEMENT
WHERE BILLING_STATE IN (2,3) AND RED_FLUSH_STATE = 1 AND DEL_FLAG = 1 AND ACCOUNT_EXPENSE_TYPE = 1
GROUP BY SUBSTR(TO_CHAR(BUSINESS_DATE,'YYYY-MM'),1,7), FIRST_SUBJECT_NAME, SECOND_SUBJECT_NAME
ORDER BY 1, 2, 3;
-- 与执行前同查询结果比对:合计列逐月相等;差异只应出现在科目归属列
-- 5.3 无漏网:仍以旧编码当一级、二级为空的行应为 0
SELECT COUNT(*) FROM NGWL_TEST_BMS.BILLING_STATEMENT
WHERE SECOND_SUBJECT_CODE IS NULL AND FIRST_SUBJECT_CODE IN ('2001','2002','2003','2004','TYLSCCSNCZ','1001','1007','2005','2006');
-- 5.4 新推送回归:迁移后触发一次租赁出账/装卸费推送,检查 billing_statement 新行
-- FIRST_SUBJECT_NAME='仓储收入'、SECOND_SUBJECT_NAME='临时仓储室内仓租' 即为解析正确
-- ============================================================================
-- 回滚(仅在验证失败时)
-- ============================================================================
-- 1) 恢复科目树:
-- MERGE INTO NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT EA
-- USING NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT_BAK_20260817 B
-- ON (EA.EXPENSE_ACCOUNT_ID = B.EXPENSE_ACCOUNT_ID)
-- WHEN MATCHED THEN UPDATE SET
-- EA.FIRST_SUBJECT_FLAG = B.FIRST_SUBJECT_FLAG,
-- EA.UPPER_SUBJECT_CODE = B.UPPER_SUBJECT_CODE,
-- EA.UPPER_SUBJECT = B.UPPER_SUBJECT;
-- 删除新增一级:DELETE FROM NGWL_TEST_SYSTEM.EXPENSE_ACCOUNT WHERE SUBJECT_CODE IN ('CCSR','PSSR','ZZSR','WYSR','QT');
-- 2) 恢复流水科目:
-- MERGE INTO NGWL_TEST_BMS.BILLING_STATEMENT BS
-- USING NGWL_TEST_BMS.SUBJ_BAK_20260817 B
-- ON (BS.BILLING_STATEMENT_ID = B.BILLING_STATEMENT_ID)
-- WHEN MATCHED THEN UPDATE SET
-- BS.FIRST_SUBJECT_CODE = B.FIRST_SUBJECT_CODE, BS.FIRST_SUBJECT_NAME = B.FIRST_SUBJECT_NAME,
-- BS.SECOND_SUBJECT_CODE = B.SECOND_SUBJECT_CODE, BS.SECOND_SUBJECT_NAME = B.SECOND_SUBJECT_NAME;
-- COMMIT;
-- ============================================================================
-- 备注
-- 1. TYLSCCSNCZ 与 2003 同名重复科目:本期仅同样重挂为"仓储收入"二级(报表按名称归组已合并成一行)。
-- 彻底去重(改 LEASE/合同引用 → 停用 TYLSCCSNCZ)作为后续主数据治理,引用量见步骤 0.3。
-- 2. 模板中"散租/固定出租"二级口径:现有科目按仓库类型命名(恒温仓/普通仓/室外空地/临时仓储),
-- 仅凭编码无法区分计费模式,本期保持原名挂二级;若业务要求改成散租/固定出租口径,
-- 需结合 LEASE.LEASE_TYPE(整租/散租) 对仓租流水逐一判定后改映射表重跑,属二期。
-- 3. 新一级编码 CCSR/PSSR/ZZSR/WYSR/QT 为建议值,上线前与业务/NC 对账确认,改动需同步步骤1/2。
-- ============================================================================