文件
hl-api-changelog/changelogs-v2/2026-09/27_8361_团期报销核单一团一张-新增接口-管理后台.md
Mimingguang 6901219b95 docs(8361): ③团期核单迁入财务域,frontend_ref 改指 9a28a7a8
用户改拍「团期核单归财务域(免原型对齐),finance/settlement 团期产品 tab
即预留位」。order-v2/batch/detail 旧 Tab 随 081966ff 下线,财务域落地
9a28a7a8:团期产品 tab 改走 GB-ADM-001 /v3/admin/order/group-batch,
行弹层挂 GroupSettlementPanel 读 reports/group+finalize/confirm。
status_note 补迁移说明,updated_at 翻 2026-09-28。
2026-09-28 20:00:35 +08:00

30 KiB


schema: "hl-changelog/v2" ticket: "8361" title: "团期报销核单「一团一张报账单」——团期核单 finalize/confirm/reports 三端点新增 + 台账应收整团聚合一行 + 报账单 biz 三字段 + 搜索兼容团号 + 核单 summary 新增 SETTLED" consumer: "admin" author: "yst" change_type: "新增接口" backend_status: "merged" gateway_status: "pending" frontend_status: "verified" frontend_owner: "mmg" frontend_ref: "9a28a7a8dc12a0c041c616ac3b1000c53847b8a6" target_release: "v2.1" verified_at: "2026-09-27" status_note: "Epic #8361 五 PR(#8366/#8367/#8368/#8400/#8406)已全部合并 dev-v3,尚未部署测试服、网关未实测。前端需动三处:①应收台账行按 rowType 分流(GROUP_BATCH 行 id 是团期批次 ID,按订单详情跳转必 404);②报账单列表按 bizType 分流展示(GROUP_BATCH 行展示 bizNo 团号);③新增团期核单页(finalize/confirm/reports 三端点 + settlementStatus 新增 SETTLED 态)。【2026-09-27 mmg】①应收台账 rowType 分流 + ②报账单 bizType 分流已交付(276de5f1):GROUP_BATCH 行跳团期详情不跳订单详情、详情「团号」取 bizNo(行快照兜底)、搜索兼容团号文案对齐;receivable/reimburse 两 spec 18 例全绿。③团期核单页 defer——原型快照 Sep 17 早于本 Epic 无其设计(prototype fidelity 不可无原型建财务新页),后端 §11 明说可随后迭代不阻塞,待原型刷新后续做,故 frontend_status 保持 pending。【2026-09-27 mmg ③】团期核单页已交付(1c555f54):用户拍板不算财务域不等原型,详情页「核单结算」后新增「团期核单」tab——reports/group 空壳范式先判 finalized、finalize 节点门 TRIP_FINISHED/REVIEWING 置灰内联、confirm 仅「FINALIZED+待复核」、SETTLED 无人工结清口、金额/ID 全字符串 null 显 —;新建 api/order-v3/groupSettlement.js+GroupSettlementTab.vue,API spec 4 例+组件 spec 10 例+详情页 spec 共 28 例全绿,checkpoint 全绿。Epic ①②③全部闭环,翻 verified。【2026-09-28 mmg ③迁】用户改拍「团期核单归财务域(免原型对齐),finance/settlement 团期产品 tab 即预留位」:先把 order-v2/batch/detail 的「团期核单」Tab 下线(081966ff),再落地财务域(9a28a7a8)——团期产品 tab 数据源由空调常规 /v3/admin/order-settlement/tasks(仅常规 CORE 无团期批次,即"接口不对"根因)改走 GB-ADM-001 /v3/admin/order/group-batch(订单域接口财务只读,pageNo/departFrom/departTo/opsStage 七桶),行弹层挂 GroupSettlementPanel(原 GroupSettlementTab 迁入)读 reports/group+finalize/confirm;应收/已收权威字段直显不反算,未建团行(groupBatchId=null)不放入口。恢复 api/order-v3/groupSettlement.js,新增 index.spec 锁双 tab 数据源+参数名+列 render+弹层入参,三 spec 22 例全绿,checkpoint 全绿。ref 由 1c555f54 改指 9a28a7a8。" updated_at: "2026-09-28" base: "dev-v3"

团期报销核单「一团一张报账单」(管理后台)

服务: hl-order-service-v3(团期核单三端点)+ hl-finance(台账应收 / 报账单列表) Epic: #8361 PR: #8366(G1 多态 DDL)+ #8367(G2 三端点)+ #8368(G3 一团一张推送)+ #8400(G4 台账整团聚合/搜索/反向联动)+ #8406(biz 三字段 + keyword 团号)


1. 接口背景

原核单链路只有「一户一张报账单」(按订单 orderId 聚合)。团期(出团批次)场景下,财务需要按整团做核单、复核、回款跟踪。本次 Epic 把核单与报账单从「一户一张」泛化为「一个业务对象一张」:

  • 团期维度新增「一团一核单」三端点(finalize 核单 → confirm 财务复核并推一团一张报账单 → reports/group 读核单表),快照落库一团一行。
  • 报账单 fin_reimburse 改 biz_type + biz_id 多态关联:ORDER(一户一张,不变)/ GROUP_BATCH(一团一张,新增)。
  • 应收台账对团期批次整团聚合一行(不按户拆),行上补 rowType/groupBatchId 鉴别字段。
  • 报账单列表补 bizType/bizId/bizNo 三字段;报账单搜索与台账 keyword 均兼容团号。
  • 一团一张报账单 RECEIVABLE 全收后,自动反向把团期核单快照 settlementStatus 回写 SETTLED(已结清)。

2. 变更清单

# 变更 方法 路径 类型 摘要
1 完成团期核单 POST /v3/admin/order/group-batch/{groupBatchId}/settlement/finalize 新增接口 按团聚合落核单快照,幂等
2 团期核单财务复核 POST /v3/admin/order/group-batch/{groupBatchId}/settlement/confirm 新增接口 复核通过 + 同事务推一团一张报账单
3 查询团期核单表 GET /v3/admin/order/group-batch/{groupBatchId}/settlement/reports/group 新增接口 读 active 快照;未核单返回 finalized=false 空壳
4 应收台账分页 GET /admin/finance/receipt/receivable/page 修改接口 行新增 rowType/groupBatchId;团期整团聚合一行;keyword 兼容团号
5 报账单分页 GET /admin/finance/reimburses/page 修改接口 行新增 bizType/bizId/bizNo;orderNo 入参扩为同时匹配团号 biz_no
6 团期核单 summary — (端点 1/2/3 的出参 GroupSettlementRespVO) 修改接口 settlementStatus 新增枚举值 SETTLED(全收自动回写,非人工触发)

3. 接口详情

端点 使用场景 认证 幂等性 限流
POST finalize 团期出行完毕后,核单员按团聚合落核单快照 网关 JWT;角色须 SUPER_ADMIN / ADMIN / FINANCE(缺 589507) 幂等:重复提交返回既有 active 快照,不重复落库 网关统一限流
POST confirm 财务复核团期核单,通过后推一团一张报账单 同 finalize 状态门 + CAS 挡重复复核;推送侧 uk_biz_version(biz_type,biz_id,version_no) 撞号重查兜底返回既有单;推送失败整单回滚(review_status 停 PENDING),可安全重试 网关统一限流
GET reports/group 团期核单表展示(核单前/后都调) 网关 JWT;须 group-batch:finance:view 权限码(缺 589507) 只读 网关统一限流
GET receivable/page 财务收款-应收台账 网关 JWT(finance 域先例,无方法级权限注解) 只读 网关统一限流
GET reimburses/page 报账款列表(复核视角) 网关 JWT 只读 网关统一限流

金额/ID 序列化约定:GroupSettlementRespVO 的所有 BigDecimal 金额字段与 Long ID 字段均序列化为 JSON 字符串(防精度丢失);台账行/报账单行的 Long ID 为字符串,BigDecimal 金额为 JSON number。

4. 接口入参

4.1 路径 / Query 参数

团期核单三端点(均无请求体):

参数 位置 类型 必填 说明
groupBatchId path Long 是 团期 ID,必须 ≥ 1(否则 400「团期 ID 必须大于 0」)

应收台账分页 GET /admin/finance/receipt/receivable/page(query):

参数 类型 必填 说明
page int 是 页码,从 1 起
pageSize int 是 每页条数
keyword string 否 搜索关键字(团号 batch_no / 客户姓名 / 产品名 / 订单号 模糊,任一命中);空=不限。注:只模糊匹配团号本身,不匹配团期名称/期次
receivableStatus string 否 UNPAID 待收款 / PARTIAL 部分收款 / DONE 已收讫;空或非法值=不按收款状态过滤

报账单分页 GET /admin/finance/reimburses/page(query):

参数 类型 必填 说明
page int 是 页码
pageSize int 是 每页条数
status string 否 单据状态(枚举见 §6);空=全部
direction string 否 PAYABLE 公司应付报账人 / RECEIVABLE 报账人应回款 / BALANCED 两清;空=全部
orderNo string 否 订单号/团号(模糊,同时匹配 order_no 与 biz_no——团期报账单 order_no 为空,按团号 biz_no 也能搜到);空=不限
reporterName string 否 报账人姓名(模糊);空=不限

4.2 请求体字段

三端点均无请求体;两个分页接口均为 GET query 传参,无请求体。

5. 出参字段

5.1 GroupSettlementRespVO(finalize / confirm / reports/group 三端点共用)

外层统一包装 {"code":200,"success":true,"data":{...}},下表为 data 结构:

字段 类型 说明
finalized boolean 是否已有核单快照;false=尚未核单,快照字段全 null,只填团期基本信息段(batchNo/productName/departDate/batchStatus),不抛 404
groupSettlementId string(Long) 团期核单快照 ID
groupBatchId string(Long) 团期 ID
batchNo string 团期号,例 20261001-01
productName string 产品名称快照
departDate string(date) 出发日期 yyyy-MM-dd
batchStatus string 团期状态(GroupBatchStatus 码,见 §6)
settledOrderCount int 已核单子订单户数
totalActiveOrderCount int 在团子订单总户数(仅排除已取消)
subOrderTotalActualCost string(BigDecimal) 子订单实际成本合计
subOrderTotalProfit string(BigDecimal) 子订单毛利合计
sharedCostTotal string(BigDecimal) 团期共享成本合计
sharedCostByType array 共享成本按类型汇总,元素见下表
grandTotalCost string(BigDecimal) 团期总成本(子订单成本合计 + 共享成本合计)
actualTravelerCount int 实际出行人数
perPersonSharedCost string(BigDecimal) 或 null 人均共享成本;出行人数为 0 时为 null
groupAdvanceApproved string(BigDecimal) 整团预支已批合计(scope=GROUP_BATCH;资金拨付提示,不计入 grandTotalCost)
groupAdvancePending string(BigDecimal) 整团预支待批合计(仅提示,不参与成本/毛利公式)
groupTotalAmount string(BigDecimal) 全团应收总额(一团一张报账单净额输入)
groupPaidAmount string(BigDecimal) 全团已付总额
reviewStatus string 复核状态:PENDING 待复核 / APPROVED 已复核 / RETURNED 已退回
settlementStatus string 核单状态:PENDING 待核单 / FINALIZED 已核单 / SETTLED 已结清(新增,见 §6)
flowStatus string 团期流程状态快照:TRIP_FINISHED / REVIEWING / SETTLED(confirm 通过后翻 SETTLED;独立于团期本体状态机,不动 order_group_batch.batch_status)
settledBy string(Long) 核单人 ID
settledByName string 核单人姓名快照
settledAt string(datetime) 团核单完成时间 yyyy-MM-dd HH:mm:ss
remark string 备注
createTime string(datetime) 快照创建时间

sharedCostByType[] 元素(SharedCostByTypeVO):

字段 类型 说明
costType string 成本类型码:BUS 整团大巴 / LEADER 领队 / PHOTOGRAPHER 摄影 / OTHER 其他
costTypeDesc string 成本类型中文标签
total string(BigDecimal) 该类型成本合计

5.2 应收台账行 ReceiptReceivableRowRespVO(receivable/page 的 data.records[])

字段 类型 说明
rowType string 新增。ORDER 订单行 / GROUP_BATCH 团期整团聚合行。行点击/跳转策略必须按本字段分流
id string(Long) rowType=ORDER 时为订单 ID(可跳订单详情);rowType=GROUP_BATCH 时挂团期批次 ID(与 groupBatchId 同值),按订单 ID 跳详情必 404
groupBatchId string(Long) 或 null 新增。rowType=GROUP_BATCH 时有值;ORDER 行恒 null
orderNo string rowType=ORDER 为订单号;GROUP_BATCH 行挂团号 batch_no
teamNo string 团号;GROUP_BATCH 行同为团号 batch_no
productName string 产品名(GROUP_BATCH 行为团期名)
customerName string 或 null 客户姓名;GROUP_BATCH 团行恒 null(整团无单一客户)
customerPhone string 或 null 客户手机号(明文,内部财务对账用);GROUP_BATCH 团行恒 null
orderStatus string rowType=ORDER 为 OrderStatus 枚举值;rowType=GROUP_BATCH 为 GroupBatchStatus 码——两套枚举空间按 rowType 分流
orderStatusName string 上述状态的中文名
receivableStatus string UNPAID 待收款 / PARTIAL 部分收款 / DONE 已收讫
receivableStatusName string 收款状态中文名
receivableAmount number 应收总额(取消单归 0)。团行:已核单团读快照全团应收;未核单团按在团子订单实时求和
paidAmount number 已收金额(毛额,退款不回减)。团行结清(SETTLED)后顶满应收
collectedAmount number 代收金额。已核单团的未结清欠收挂本列(一团一张报账单已推送,全团尾款=主报账人代收口径);未核单团恒 0
balanceAmount number 欠收金额。与 collectedAmount 互斥、合计恒等于实时待收尾款;团行结清后归 0

团期整团聚合行为(新增):页内命中的团期子订单按 groupBatchId 折叠——每团只出一行台账,同团其余子订单行丢弃,total 按页内折叠数修正。已知近似(后端拍板接受):折叠在页内做,同团子订单跨页时该团在每页各出一行;DONE 筛选视图下 total 为近似值,跨页行数/total 可能有偏差。

5.3 报账单行 ReimburseRowRespVO(reimburses/page 的 data.records[])

只列本次新增三字段(其余字段不变:id/reimburseNo/reporterName/reporterRole/direction/collectableAmount/actualCollectedAmount/underCollectAmount/advanceAmount/cashPaidAmount/netAmount/settleAmount/receivedAmount/remainingAmount/status/reviewByName/reviewTime/createTime):

字段 类型 说明
bizType string 新增。ORDER 订单单(一户一张)/ GROUP_BATCH 团期单(一团一张);前端按本字段分流展示——GROUP_BATCH 行展示 bizNo(团号)
bizId string(Long) 新增。bizType=ORDER 为订单 ID;GROUP_BATCH 为团期批次 ID(勿按订单 ID 跳详情)
bizNo string 新增。bizType=ORDER 为订单号;GROUP_BATCH 为团号 batch_no

既有字段语义修订:

字段 修订
orderId bizType=GROUP_BATCH 团期单恒 null
orderNo bizType=GROUP_BATCH 团期单恒 null,团号看 bizNo

6. 枚举 / 数据字典

rowType(台账行类型,新增):ORDER 订单行 / GROUP_BATCH 团期整团聚合行。

bizType(报账单业务对象类型,新增):ORDER 订单单(一户一张)/ GROUP_BATCH 团期单(一团一张)。

settlementStatus(团期核单状态,本次新增 SETTLED):

值 中文 说明
PENDING 待核单 快照未 finalize(reports/group 空壳态不出现本值,看 finalized=false)
FINALIZED 已核单 finalize 完成,待财务复核
SETTLED 已结清 新增。一团一张报账单 RECEIVABLE 全收后由后端监听端自动回写(FINALIZED→SETTLED),非任何人工端点触发;confirm 不会把 settlementStatus 翻成 SETTLED(confirm 翻的是 reviewStatus 与 flowStatus)

reviewStatus(复核状态):PENDING 待复核 / APPROVED 已复核 / RETURNED 已退回。

flowStatus(快照内流程状态):TRIP_FINISHED / REVIEWING / SETTLED。

GroupBatchStatus(团期状态,GROUP_BATCH 台账行的 orderStatus 与核单快照 batchStatus 用):RECRUITING 招募中 / RESOURCE_PREPARING 资源准备中 / MATERIAL_PREPARING 物料准备中 / PENDING_DEPARTURE 待出发 / TRAVELLING 出行中 / TRIP_FINISHED 出行完毕 / REVIEWING 核单中 / SETTLED 已结算 / CANCELLED 已取消。

OrderStatus(订单粗状态,ORDER 台账行的 orderStatus 用):PENDING_PAY 待支付 / CUSTOMIZING 定制中 / PENDING_DEPARTURE 待出行 / TRAVELLING 出行中 / COMPLETED 已完成 / CANCELLED 已取消。

receivableStatus(收款状态):UNPAID 待收款 / PARTIAL 部分收款 / DONE 已收讫。

报账单 status:PENDING 待复核 / APPROVED 已批准 / PARTIAL_RECEIVED 部分收讫 / PAID 已付讫 / RECEIVED 已回款 / CLOSED 两清 / RETURNED 已退回。

direction(报账方向):PAYABLE 公司应付报账人 / RECEIVABLE 报账人应回款 / BALANCED 两清。

costType(共享成本类型):BUS 整团大巴 / LEADER 领队 / PHOTOGRAPHER 摄影 / OTHER 其他。

7. 错误码

外层结构 {"code":错误码,"message":"文案","data":null,"success":false}。

错误码 触发端点 文案({0} 为占位) 处置建议
400 三端点 团期 ID 必须大于 0 参数校验失败
589500 三端点 团期不存在 检查 groupBatchId
589507 三端点 无操作权限(当前角色未授予团期权限,或该团期不在您名下) finalize/confirm 需 SUPER_ADMIN/ADMIN/FINANCE;reports/group 需 group-batch:finance:view
584133 finalize 该团期未配置主报账人,请先在团期人员配置中设置主报账人后再核单 去团期人员配置设主
584134 finalize 该团期存在 {0} 个主报账人,一团只能有一个主报账人,请先去重后再核单 去重主报账人
584135 finalize 团期子订单 {0} 尚未确认行程,请全团子订单都确认行程后再核单({0}=子订单 ID) 催该户确认行程
584136 confirm 该团期尚未完成核单,请先完成核单后再做财务复核 先 finalize
584137 confirm 当前团期核单状态不允许财务复核(须为已核单且待复核),操作已回滚 刷新快照状态;并发复核败者也会命中
584138 finalize 团期当前状态为「{0}」,未到核单节点(需出行完毕或核单中),不允许核单({0}=当前 batchStatus) 等团期到 TRIP_FINISHED/REVIEWING

8. 示例

8.1 典型成功——finalize 后读团期核单表

POST /v3/admin/order/group-batch/2097250563497385985/settlement/finalize(无请求体)→ 响应与 GET reports/group 同构:

{
  "code": 200,
  "success": true,
  "data": {
    "finalized": true,
    "groupSettlementId": "9101234567890123456",
    "groupBatchId": "2097250563497385985",
    "batchNo": "20261001-01",
    "productName": "呼伦贝尔草原 5 日游",
    "departDate": "2026-10-01",
    "batchStatus": "REVIEWING",
    "settledOrderCount": 5,
    "totalActiveOrderCount": 6,
    "subOrderTotalActualCost": "45600.00",
    "subOrderTotalProfit": "8400.00",
    "sharedCostTotal": "3200.00",
    "sharedCostByType": [
      {"costType": "BUS", "costTypeDesc": "整团大巴", "total": "2000.00"},
      {"costType": "LEADER", "costTypeDesc": "领队", "total": "1200.00"}
    ],
    "grandTotalCost": "48800.00",
    "actualTravelerCount": 18,
    "perPersonSharedCost": "177.78",
    "groupAdvanceApproved": "5000.00",
    "groupAdvancePending": "0.00",
    "groupTotalAmount": "54000.00",
    "groupPaidAmount": "48000.00",
    "reviewStatus": "PENDING",
    "settlementStatus": "FINALIZED",
    "flowStatus": "REVIEWING",
    "settledBy": "40001",
    "settledByName": "王财务",
    "settledAt": "2026-09-27 12:00:00",
    "remark": "团核单",
    "createTime": "2026-09-27 12:00:00"
  }
}

台账分页典型响应(GET /admin/finance/receipt/receivable/page?page=1&pageSize=20&keyword=20261001):

{
  "code": 200,
  "success": true,
  "data": {
    "records": [
      {
        "rowType": "ORDER",
        "id": "2097000000000000001",
        "groupBatchId": null,
        "orderNo": "HL20260920001",
        "teamNo": "T-0920-01",
        "productName": "阿尔山 3 日游",
        "customerName": "张三",
        "customerPhone": "13800001111",
        "orderStatus": "COMPLETED",
        "orderStatusName": "已完成",
        "receivableStatus": "PARTIAL",
        "receivableStatusName": "部分收款",
        "receivableAmount": 6000.00,
        "paidAmount": 3000.00,
        "collectedAmount": 0,
        "balanceAmount": 3000.00
      },
      {
        "rowType": "GROUP_BATCH",
        "id": "2097250563497385985",
        "groupBatchId": "2097250563497385985",
        "orderNo": "20261001-01",
        "teamNo": "20261001-01",
        "productName": "呼伦贝尔草原 5 日游",
        "customerName": null,
        "customerPhone": null,
        "orderStatus": "SETTLED",
        "orderStatusName": "已结算",
        "receivableStatus": "DONE",
        "receivableStatusName": "已收讫",
        "receivableAmount": 54000.00,
        "paidAmount": 54000.00,
        "collectedAmount": 0,
        "balanceAmount": 0
      }
    ],
    "total": 2,
    "page": 1,
    "pageSize": 20
  }
}

8.2 边界——未核单团读核单表(finalized=false 空壳)+ 报账单 GROUP_BATCH 行

GET reports/group(该团尚未 finalize)——不抛 404,快照字段全 null,前端展示「尚未核单」占位:

{
  "code": 200,
  "success": true,
  "data": {
    "finalized": false,
    "groupSettlementId": null,
    "groupBatchId": "2097250563497385985",
    "batchNo": "20261001-01",
    "productName": "呼伦贝尔草原 5 日游",
    "departDate": "2026-10-01",
    "batchStatus": "TRIP_FINISHED",
    "settledOrderCount": null,
    "totalActiveOrderCount": null,
    "subOrderTotalActualCost": null,
    "subOrderTotalProfit": null,
    "sharedCostTotal": null,
    "sharedCostByType": null,
    "grandTotalCost": null,
    "actualTravelerCount": null,
    "perPersonSharedCost": null,
    "groupAdvanceApproved": null,
    "groupAdvancePending": null,
    "groupTotalAmount": null,
    "groupPaidAmount": null,
    "reviewStatus": null,
    "settlementStatus": null,
    "flowStatus": null,
    "settledBy": null,
    "settledByName": null,
    "settledAt": null,
    "remark": null,
    "createTime": null
  }
}

报账单列表中的团期单(GET /admin/finance/reimburses/page?page=1&pageSize=20&orderNo=20261001,按团号搜到)——orderId/orderNo 恒 null,团号看 bizNo:

{
  "code": 200,
  "success": true,
  "data": {
    "records": [
      {
        "id": "9123456789012345678",
        "reimburseNo": "BZ-20260927-0001",
        "orderId": null,
        "orderNo": null,
        "bizType": "GROUP_BATCH",
        "bizId": "2097250563497385985",
        "bizNo": "20261001-01",
        "reporterName": "李领队",
        "reporterRole": "GUIDE",
        "direction": "RECEIVABLE",
        "collectableAmount": 54000.00,
        "actualCollectedAmount": 48000.00,
        "underCollectAmount": 6000.00,
        "advanceAmount": 0,
        "cashPaidAmount": 0,
        "netAmount": 6000.00,
        "settleAmount": 6000.00,
        "receivedAmount": 0,
        "remainingAmount": 6000.00,
        "status": "APPROVED",
        "reviewByName": "王财务",
        "reviewTime": "2026-09-27 12:30:00",
        "createTime": "2026-09-27 12:30:00"
      }
    ],
    "total": 1,
    "page": 1,
    "pageSize": 20
  }
}

8.3 业务失败——confirm 时团期未核单(584136)

POST confirm(该团尚未 finalize):

{"code": 584136, "message": "该团期尚未完成核单,请先完成核单后再做财务复核", "data": null, "success": false}

finalize 时团期状态未到核单节点(584138,{0} 透出当前状态):

{"code": 584138, "message": "团期当前状态为「TRAVELLING」,未到核单节点(需出行完毕或核单中),不允许核单", "data": null, "success": false}

9. 业务边界

适用:

  • finalize:团期状态须为 TRIP_FINISHED(出行完毕)或 REVIEWING(核单中);全团恰好 1 个 PRIMARY 主报账人;全团在团子订单(不含已取消)均已确认行程。
  • confirm:须已存在 active 核单快照且为「FINALIZED + 待复核 PENDING」。
  • 台账/报账单列表的 GROUP_BATCH 行:仅团期批次订单(有 groupBatchId 关联)才会聚合/出现;散单(ORDER 行)行为完全不变。

不适用:

  • 招募中~出行中的团期不允许 finalize(584138)——共享成本未录、子订单成本未发生,快照无意义。
  • 未 finalize 的团期不允许 confirm(584136)。
  • SETTLED / CANCELLED 团期同样不允许 finalize(584138,fail-closed 闭集)。

特殊边界:

  • 重复 finalize:幂等返回既有快照,不重复落库、不报错。
  • 并发 confirm:CAS 败者报 584137,不静默成功。
  • confirm 推送报账单失败:整单回滚(review_status 停 PENDING),可安全重试;推送幂等由 uk_biz_version 兜底。
  • settlementStatus=SETTLED 只能由「一团一张报账单 RECEIVABLE 全收」自动回写,无人工端点能置该态;部分回款不触发。
  • 团期回款不回写子订单 paid_amount:台账团行已核单后金额读团快照,子订单级欠收停留在订金态属预期,全团回款进度由报账单承接。

10. 修改前后对比

字段级

接口 字段 原来 现在
receivable/page 行 rowType 无此字段 新增,ORDER / GROUP_BATCH
receivable/page 行 groupBatchId 无此字段 新增;GROUP_BATCH 行有值,ORDER 行恒 null
receivable/page 行 id 恒为订单 ID GROUP_BATCH 行挂团期批次 ID(勿跳订单详情)
receivable/page 行 customerName / customerPhone 恒有值 GROUP_BATCH 行恒 null
receivable/page 行 orderStatus / orderStatusName 恒为 OrderStatus 枚举 GROUP_BATCH 行为 GroupBatchStatus 码(两套枚举按 rowType 分流)
receivable/page 入参 keyword 团号(散团 team_no)/客户姓名/产品名/订单号 四字段模糊 追加兼容团期团号 batch_no(命中的团整团进入结果集并折叠成 GROUP_BATCH 行)
reimburses/page 行 bizType / bizId / bizNo 无此三字段 新增;GROUP_BATCH 行 orderId/orderNo 恒 null
reimburses/page 入参 orderNo 仅模糊匹配 order_no 同时模糊匹配 order_no 与 biz_no(团号可搜到团期单)
GroupSettlementRespVO settlementStatus PENDING / FINALIZED 追加 SETTLED(全收自动回写)

行为级

行为 原来 现在
台账团期订单展示 逐户一行(团期子订单每户一行台账) 整团聚合一行(页内折叠,total 按折叠数修正)
台账行数/total 订单粒度精确计数 团折叠后 total 为近似值(跨页折叠 + DONE 视图粗筛假阳性剔除,后端拍板接受)
报账单生成 只有订单核单「一户一张」 团期 confirm 追加「一团一张」(biz_type=GROUP_BATCH,单号同为 BZ- 前缀)
报账单 biz 关联 order_id 单列 biz_type + biz_id 多态(ORDER 单 biz 三字段与旧 order 字段同值)

11. 影响评估 / 回滚

破坏兼容评估:

  • 新增端点(finalize/confirm/reports/group):纯新增,无兼容风险。
  • 台账/报账单列表新增字段:纯追加,旧前端忽略新字段可继续工作。
  • 行为级不兼容(唯一必须前端同步的点):台账对团期子订单不再逐户出行。旧前端若把每行当订单、按 id 跳订单详情,GROUP_BATCH 行会 404;且团期子订单行数变少。旧前端没有团期入口时感知为「团期订单从台账消失、多了一个点不开的行」。

前端同步上线建议:台账 rowType 分流与报账单 bizType 分流随后端同窗口上线;团期核单页(三端点)可随后迭代,不阻塞。

回滚方案:后端回滚 #8406/#8400/#8368/#8367/#8366 五个合并提交(逆序)。回滚后台账恢复逐户一行、新增字段消失;已落库的 GROUP_BATCH 报账单与团期核单快照保留在库但不再被读写。前端对新增字段若做了「有则展示」的容错,回滚零改动;若强依赖 rowType 分流,回滚后分流逻辑永不命中 GROUP_BATCH 分支,自然降级为 ORDER 行为。

12. 注意事项

  1. rowType 分流是硬要求:GROUP_BATCH 行的 id 是团期批次 ID(与 groupBatchId 同值),严禁当订单 ID 跳订单详情(必 404)。
  2. 两套状态枚举空间:台账行 orderStatus 在 GROUP_BATCH 行是 GroupBatchStatus 码(9 态)、ORDER 行是 OrderStatus 码(6 态),翻译展示必须按 rowType 选字典,不可混用(两边都有 TRAVELLING/SETTLED/CANCELLED 等同名值但语义层级不同)。
  3. 金额与 ID 序列化:GroupSettlementRespVO 的 BigDecimal 金额与 Long ID 全是 JSON 字符串;台账行/报账单行 Long ID 是字符串、金额是 number。
  4. keyword 只匹配团号本身(batch_no LIKE),不匹配团期名称/期次;台账团行上的标识就是团号(orderNo/teamNo 同挂 batch_no)。
  5. SETTLED 无人工触发口:settlementStatus=SETTLED 只由回款全收自动回写;前端不要提供「手动结清」按钮,也不要在 confirm 后期望 settlementStatus 立即变 SETTLED(confirm 翻的是 reviewStatus/flowStatus)。
  6. 空壳范式:reports/group 用 finalized=false + 全 null 表示未核单,不是 404;前端先判 finalized 再渲染快照区。
  7. 报账单列表 GROUP_BATCH 行 orderId/orderNo 恒 null,展示层一律取 bizNo;报账单详情接口 GET /admin/finance/reimburses/{id} 路径不变、按报账单 id 查,两种 bizType 通用。
  8. 团期回款不回写子订单 paid_amount,勿因「子订单仍显示欠收」报 bug——全团回款进度看报账单与台账团行。

13. 关联 / 联系人