package jnpf.limsService.support; import java.io.IOException; import java.nio.charset.StandardCharsets; import java.nio.file.Files; import java.nio.file.Path; import java.nio.file.Paths; /** * 取样终止申请流程状态同步的静态回归检查。 */ public class LimsSxtQuyangZhongzhiShenqingFlowStatusChecks { private static final Path REPOSITORY_ROOT = Paths.get("").toAbsolutePath().normalize(); public static void main(String[] args) throws IOException { String service = read("jnpf-lims/jnpf-lims-biz/src/main/java/jnpf/limsService/impl/LimsSxtJihuaServiceImpl.java"); String entity = read("jnpf-lims/jnpf-lims-entity/src/main/java/jnpf/limsEntity/LimsSxtQuyangZhongzhiShenqingEntity.java"); String mapper = read("jnpf-lims/jnpf-lims-biz/src/main/java/jnpf/limsMapper/LimsSxtQuyangZhongzhiShenqingMapper.java"); String childEntity = read("jnpf-lims/jnpf-lims-entity/src/main/java/jnpf/limsEntity/LimsSxtQuyangZhongzhiShenqingZixiangEntity.java"); String childMapper = read("jnpf-lims/jnpf-lims-biz/src/main/java/jnpf/limsMapper/LimsSxtQuyangZhongzhiShenqingZixiangMapper.java"); String bizStatus = read("jnpf-lims/jnpf-lims-entity/src/main/java/jnpf/limsEntity/BizStatus.java"); String schema = read("docs/pg-migration-ddl/self_built_tables_pg.sql"); String migration = read("docs/pg-migration-ddl/update_lims_sxt_quyang_zhongzhi_shenqing_biz_status_20260723.sql"); String qingyandanLinkMigration = read("docs/pg-migration-ddl/update_lims_sxt_quyang_zhongzhi_shenqing_qingyandan_link_20260723.sql"); require(entity, "@TableName(\"lims_sxt_quyang_zhongzhi_shenqing\")", "sampling termination entity must map the application table"); require(entity, "private String bizStatus;", "entity must expose biz_status"); require(entity, "private String fTenantId;", "entity must expose the composite primary-key tenant id"); require(mapper, "SuperMapper", "sampling termination mapper must support status updates"); require(childEntity, "@TableName(\"lims_sxt_quyang_zhongzhi_shenqing_zixiang\")", "sampling termination child entity must map selected sampling tasks"); require(childEntity, "@TableField(\"qingyandan_id\")", "sampling termination child must retain its selected qingyandan id"); require(childMapper, "SuperMapper", "sampling termination child mapper must load selected sampling tasks"); require(bizStatus, "DELETED(\"deleted\", \"已废弃\")", "sampling termination must reuse the existing deleted status"); requireAbsent(bizStatus, "TERMINATED(", "sampling termination must not introduce a separate terminated status"); require(service, "findQuyangZhongzhiShenqingByFlow", "flow synchronization must locate sampling termination applications"); require(service, "syncQuyangZhongzhiShenqingStarted", "start events must set sampling termination applications to processing"); require(service, "syncQuyangZhongzhiShenqingEnded", "end events must set sampling termination applications to completed"); require(service, "syncApprovedQuyangTerminationStatus", "approved termination events must synchronize linked sampling applications"); require(service, "BizStatus.DELETED", "approved termination must set the sampling status to deleted"); require(service, "BizStatus.PENDING_FETCH", "only pending sampling applications may be terminated"); require(service, "terminatePendingQingyandan(LimsSxtQuyangZhongzhiShenqingZixiangEntity child)", "termination must update the qingyandan id saved by the selected child"); require(service, "多个取样终止申请关联同一流程任务", "duplicate sampling termination flow bindings must be rejected"); require(service, "getFTenantId", "sampling termination status updates must be tenant-scoped"); require(schema, "biz_status varchar(50) DEFAULT 'pending'", "fresh PostgreSQL schema must default sampling termination applications to pending"); require(schema, "qingyandan_id varchar(50)", "fresh PostgreSQL schema must retain selected qingyandan ids"); require(migration, "ALTER TABLE lims_sxt_quyang_zhongzhi_shenqing", "existing PostgreSQL deployments must receive the status column migration"); require(migration, "ADD COLUMN IF NOT EXISTS biz_status varchar(50);", "migration must add the status column without a default before historical backfill"); require(migration, "SET biz_status = CASE", "migration must backfill existing application statuses"); require(migration, "OR (biz_status = 'pending' AND f_flow_state IN (1, 2, 3, 4, 5, 6, 7, 8, 9))", "migration must correct pending defaults created while importing historical non-pending workflows"); requireOrder(migration, "UPDATE lims_sxt_quyang_zhongzhi_shenqing", "ALTER COLUMN biz_status SET DEFAULT 'pending'", "migration must backfill historical statuses before applying the default"); require(qingyandanLinkMigration, "ADD COLUMN IF NOT EXISTS qingyandan_id varchar(50)", "existing PostgreSQL deployments must receive the qingyandan link column"); } private static String read(String relativePath) throws IOException { return new String(Files.readAllBytes(REPOSITORY_ROOT.resolve(relativePath)), StandardCharsets.UTF_8); } private static void require(String source, String expected, String message) { if (!source.contains(expected)) { throw new AssertionError(message); } } private static void requireAbsent(String source, String unexpected, String message) { if (source.contains(unexpected)) { throw new AssertionError(message); } } private static void requireOrder(String source, String first, String second, String message) { if (source.indexOf(first) >= source.indexOf(second)) { throw new AssertionError(message); } } }