账单
This commit is contained in:
@@ -0,0 +1,427 @@
|
||||
# 小程序订单与账单接口文档
|
||||
|
||||
> 适用端:微信小程序(h5 仓库,Taro)
|
||||
> 覆盖接口:订单列表 / 订单详情、账单列表 / 账单详情
|
||||
> 更新日期:2026-08-14
|
||||
|
||||
## 通用约定
|
||||
|
||||
| 项 | 说明 |
|
||||
|---|---|
|
||||
| 根地址 | `BASE_URL`(见 `src/utils/request.ts`,如 `http://localhost:8000/index.php`) |
|
||||
| 认证 | 请求头 `Authorization: Bearer {token}`,token 来自登录接口,本地存储 key `auth_token` |
|
||||
| 响应包络 | `{ success: boolean, data: T, msg?: string, showType?: number }` |
|
||||
| 分页结构 | `{ data: T[], total: number, pageSize: number, current: number }`(账单列表在此结构上附加 `summary`) |
|
||||
| 失败处理 | `success=false` 时 `msg` 为中文错误信息(含参数校验失败);HTTP 401 表示登录过期,需重新登录 |
|
||||
| 金额字段 | 一律为**字符串**(decimal 序列化,如 `"140.00"`),直接展示即可;参与计算需自行转 number |
|
||||
| 门店隔离 | 两个列表均强制按当前用户绑定门店过滤,无需也不能传门店参数 |
|
||||
|
||||
## 状态枚举
|
||||
|
||||
**订单状态(status)**
|
||||
|
||||
| 值 | 名称 | 说明 |
|
||||
|---|---|---|
|
||||
| 0 | 待接单 | 下单成功待后台接单,**仅此状态可取消** |
|
||||
| 1 | 已接单 | 后台已接单,等待归集生成采购单 |
|
||||
| 2 | 采购中 | 已归集进采购单 |
|
||||
| 3 | 配送中 | |
|
||||
| 4 | 已完成 | |
|
||||
| 9 | 已取消 | |
|
||||
|
||||
**账单支付进度(pay_state)**——由后端推导,覆盖原始支付状态(status)的展示口径
|
||||
|
||||
| 值 | 名称 | 推导条件 | 说明 |
|
||||
|---|---|---|---|
|
||||
| 0 | 待支付 | status=0 且 payment_id=0 | `can_pay=true`,可发起合并付款 |
|
||||
| 1 | 审核中 | status=0 且 payment_id>0 | 已提交合并付款凭证,待后台审核;**审核拒绝后自动回到待支付** |
|
||||
| 2 | 已支付 | status=1 | 线上审核通过或后台线下收款登记 |
|
||||
|
||||
---
|
||||
|
||||
## GET /mini/order
|
||||
|
||||
门店历史订单列表,按订货日期倒序(同日期按 ID 倒序)分页。行数据附带**商品预览**(前 3 条明细),完整明细请调订单详情。
|
||||
|
||||
- **权限**:需登录且已绑定正常门店
|
||||
|
||||
### 请求参数
|
||||
|
||||
| 参数 | 类型 | 必填 | 说明 |
|
||||
|---|---|---|---|
|
||||
| status | number | 否 | 订单状态(见枚举表),不传=全部 |
|
||||
| start_date | string | 否 | 订货日期起,`Y-m-d`;可配合 `/mini/order/summary` 返回的 `period_label` 下钻 |
|
||||
| end_date | string | 否 | 订货日期止,`Y-m-d`,不得早于 start_date |
|
||||
| page | number | 否 | 页码,默认 1 |
|
||||
| pageSize | number | 否 | 每页数量,默认 10,**最大 50** |
|
||||
|
||||
### 响应示例
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"msg": "ok",
|
||||
"data": {
|
||||
"data": [
|
||||
{
|
||||
"id": 1024,
|
||||
"order_no": "SO202608140001",
|
||||
"order_date": "2026-08-14",
|
||||
"status": 0,
|
||||
"status_name": "待接单",
|
||||
"can_cancel": true,
|
||||
"total_quantity": 8,
|
||||
"total_weight": "0.000",
|
||||
"total_amount": "44.00",
|
||||
"remark": "下午送到",
|
||||
"purchase_id": 0,
|
||||
"bill_id": 0,
|
||||
"created_at": "2026-08-14 09:30:00",
|
||||
"item_count": 4,
|
||||
"items": [
|
||||
{ "product_name": "白菜", "quantity": 2, "unit": "件" },
|
||||
{ "product_name": "土豆", "quantity": 2, "unit": "件" },
|
||||
{ "product_name": "番茄", "quantity": 2, "unit": "件" }
|
||||
]
|
||||
}
|
||||
],
|
||||
"total": 36,
|
||||
"pageSize": 10,
|
||||
"current": 1
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 字段说明(列表行)
|
||||
|
||||
| 字段 | 类型 | 说明 |
|
||||
|---|---|---|
|
||||
| id | number | 订单 ID |
|
||||
| order_no | string | 订单编号(SO 前缀) |
|
||||
| order_date | string | 订货日期 `Y-m-d` |
|
||||
| status | number | 订单状态(见枚举表) |
|
||||
| **status_name** | string | 状态中文名,**直接展示,前端不要再硬编码映射** |
|
||||
| **can_cancel** | boolean | 是否可取消(=待接单);取消按钮据此渲染 |
|
||||
| total_quantity | number | 订货总数量(件/包数) |
|
||||
| total_weight | string | 总称重(斤,手动录入参考值,常为 0) |
|
||||
| total_amount | string | 订单金额 |
|
||||
| remark | string | 订单备注,可能为空字符串 |
|
||||
| purchase_id | number | 关联采购单 ID,0=未归集 |
|
||||
| bill_id | number | 关联账单 ID,0=未出账(>0 可跳账单详情) |
|
||||
| created_at | string | 下单时间 `Y-m-d H:i:s` |
|
||||
| **item_count** | number | 明细种数(如「共 4 种」) |
|
||||
| **items** | array | 商品预览,**仅前 3 条**(`product_name` / `quantity` / `unit`),完整明细走详情接口 |
|
||||
|
||||
---
|
||||
|
||||
## GET /mini/order/{id}
|
||||
|
||||
订单详情(校验本店归属),返回订单全部字段 + 完整明细(`items` 数组,含下单时商品快照)。
|
||||
|
||||
- **权限**:需登录且已绑定正常门店;非本店订单返回 `success=false`「订单不存在」
|
||||
|
||||
### 响应示例
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"msg": "ok",
|
||||
"data": {
|
||||
"id": 1024,
|
||||
"order_no": "SO202608140001",
|
||||
"store_id": 3,
|
||||
"order_date": "2026-08-14",
|
||||
"total_quantity": 8,
|
||||
"total_weight": "0.000",
|
||||
"total_amount": "44.00",
|
||||
"status": 0,
|
||||
"remark": "下午送到",
|
||||
"purchase_id": 0,
|
||||
"bill_id": 0,
|
||||
"created_at": "2026-08-14 09:30:00",
|
||||
"items": [
|
||||
{
|
||||
"id": 501,
|
||||
"order_id": 1024,
|
||||
"product_id": 11,
|
||||
"product_name": "白菜",
|
||||
"product_spec": "约30斤/件",
|
||||
"unit": "件",
|
||||
"price": "5.50",
|
||||
"quantity": 2,
|
||||
"weight": "0.000",
|
||||
"amount": "11.00",
|
||||
"remark": ""
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 字段说明
|
||||
|
||||
订单本体字段同列表行(无 `status_name` / `can_cancel` / 预览字段,状态展示沿用列表行数据或自行映射);`items` 为完整明细:
|
||||
|
||||
| 字段 | 类型 | 说明 |
|
||||
|---|---|---|
|
||||
| product_name / product_spec / unit | string | 下单时商品快照(品名/规格包规/单位),商品档案后续变更不影响 |
|
||||
| price | string | 下单时门店等级实际价快照 |
|
||||
| quantity | number | 订货量(件/包数) |
|
||||
| weight | string | 称重(斤,参考值) |
|
||||
| amount | string | 明细金额 = price × quantity |
|
||||
|
||||
---
|
||||
|
||||
## GET /mini/bill
|
||||
|
||||
门店账单列表(采购单完成后由后台按门店生成,门店端只读),按账单日期倒序分页。响应在分页结构上**附加 `summary` 待支付汇总**(仅按门店口径统计,不受筛选参数影响),供页面头部与合并付款入口展示。
|
||||
|
||||
- **权限**:需登录且已绑定正常门店
|
||||
|
||||
### 请求参数
|
||||
|
||||
| 参数 | 类型 | 必填 | 说明 |
|
||||
|---|---|---|---|
|
||||
| status | number | 否 | 原始支付状态:0 未支付(含审核中)/ 1 已支付,不传=全部 |
|
||||
| payable | number | 否 | 传 `1` = 仅可发起付款的账单(未支付且未在审核中),**合并付款选择页专用** |
|
||||
| start_date | string | 否 | 账单日期起,`Y-m-d` |
|
||||
| end_date | string | 否 | 账单日期止,`Y-m-d`,不得早于 start_date |
|
||||
| page | number | 否 | 页码,默认 1 |
|
||||
| pageSize | number | 否 | 每页数量,默认 10,**最大 50** |
|
||||
|
||||
### 响应示例
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"msg": "ok",
|
||||
"data": {
|
||||
"data": [
|
||||
{
|
||||
"id": 88,
|
||||
"bill_no": "ZD202608140001",
|
||||
"bill_date": "2026-08-14",
|
||||
"purchase_id": 31,
|
||||
"purchase": { "id": 31, "purchase_no": "PO202608130001", "purchase_date": "2026-08-13" },
|
||||
"product_amount": "100.00",
|
||||
"delivery_fee": "10.00",
|
||||
"box_num": 2,
|
||||
"tray_num": 1,
|
||||
"box_price": "5.00",
|
||||
"tray_price": "20.00",
|
||||
"added_amount": "30.00",
|
||||
"total_amount": "140.00",
|
||||
"status": 0,
|
||||
"status_name": "未支付",
|
||||
"pay_state": 0,
|
||||
"pay_state_name": "待支付",
|
||||
"can_pay": true,
|
||||
"payment_id": 0,
|
||||
"settlement_date": "2026-08-17",
|
||||
"paid_at": null,
|
||||
"pay_remark": "",
|
||||
"remark": "",
|
||||
"created_at": "2026-08-14 03:17:01"
|
||||
}
|
||||
],
|
||||
"total": 12,
|
||||
"pageSize": 10,
|
||||
"current": 1,
|
||||
"summary": { "unpaid_count": 3, "unpaid_amount": "420.50" }
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 字段说明(列表行)
|
||||
|
||||
| 字段 | 类型 | 说明 |
|
||||
|---|---|---|
|
||||
| id | number | 账单 ID |
|
||||
| bill_no | string | 账单编号(ZD 前缀) |
|
||||
| bill_date | string | 账单日期(出账日)`Y-m-d` |
|
||||
| purchase_id | number | 关联采购单 ID |
|
||||
| purchase | object \| null | 关联采购单 `{ id, purchase_no, purchase_date }` |
|
||||
| product_amount | string | 商品金额(订单汇总快照,不可修改) |
|
||||
| delivery_fee | string | 配送费 |
|
||||
| box_num / tray_num | number | 周转筐 / 周转托盘数量 |
|
||||
| box_price / tray_price | string | 筐 / 托盘单价(出账时快照) |
|
||||
| added_amount | string | 附加金额 = box_num×box_price + tray_num×tray_price |
|
||||
| total_amount | string | **账单总金额 = 商品金额 + 配送费 + 附加金额** |
|
||||
| status | number | 原始支付状态:0 未支付 / 1 已支付(展示用 pay_state 系列字段) |
|
||||
| status_name | string | 支付状态中文名 |
|
||||
| **pay_state** | number | 支付进度:0 待支付 / 1 审核中 / 2 已支付(见枚举表) |
|
||||
| **pay_state_name** | string | 支付进度中文名,**列表状态标签直接用它** |
|
||||
| **can_pay** | boolean | 是否可勾选发起合并付款(=待支付) |
|
||||
| payment_id | number | 关联支付记录 ID,0=未发起付款;审核中时可跳支付记录详情查看进度 |
|
||||
| **settlement_date** | string | 应结算日期 = 账单日期 + 门店回款周期天数 |
|
||||
| paid_at | string \| null | 付款时间(已支付时非空) |
|
||||
| pay_remark | string | 付款备注(如「微信支付(支付单号 ZF…)」、线下收款说明) |
|
||||
| remark | string | 账单备注 |
|
||||
| created_at | string | 出账时间 |
|
||||
|
||||
### summary 字段
|
||||
|
||||
| 字段 | 类型 | 说明 |
|
||||
|---|---|---|
|
||||
| unpaid_count | number | 待支付账单笔数(**含审核中**) |
|
||||
| unpaid_amount | string | 待支付金额合计(含审核中) |
|
||||
|
||||
---
|
||||
|
||||
## GET /mini/bill/{id}
|
||||
|
||||
账单详情(校验本店归属):账单信息(字段同列表行)+ 合并后的商品明细 + 关联订单。
|
||||
|
||||
- **权限**:需登录且已绑定正常门店;非本店账单返回 `success=false`「账单不存在」
|
||||
|
||||
### 响应示例
|
||||
|
||||
```json
|
||||
{
|
||||
"success": true,
|
||||
"msg": "ok",
|
||||
"data": {
|
||||
"bill": { "id": 88, "bill_no": "ZD202608140001", "...": "(字段同列表行)" },
|
||||
"items": [
|
||||
{
|
||||
"product_id": 11,
|
||||
"product_name": "白菜",
|
||||
"product_spec": "约30斤/件",
|
||||
"unit": "件",
|
||||
"price": "5.50",
|
||||
"quantity": 20,
|
||||
"weight": "0.000",
|
||||
"amount": "110.00"
|
||||
}
|
||||
],
|
||||
"orders": [
|
||||
{
|
||||
"id": 1024,
|
||||
"order_no": "SO202608130001",
|
||||
"order_date": "2026-08-13",
|
||||
"total_quantity": 8,
|
||||
"total_weight": "0.000",
|
||||
"total_amount": "44.00",
|
||||
"status": 4
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
### 字段说明
|
||||
|
||||
- **bill**:与列表行完全一致(含 `pay_state_name` / `can_pay` / `settlement_date` 等派生字段)
|
||||
- **items**:按商品聚合的合并明细(跨本账单全部订单),`price` 为加权平均口径(Σ金额÷Σ数量,保证 单价×数量=金额);`quantity` 为合计数量(number)、`amount` 为合计金额
|
||||
- **orders**:本账单关联的门店订单(单价明细可继续下钻 `GET /mini/order/{id}`),`status` 为订单状态枚举
|
||||
|
||||
---
|
||||
|
||||
## 前端接入示例
|
||||
|
||||
`src/types/order.ts` 关键类型(列表行替换为接口返回,**删除本地 `ORDER_STATUS_MAP` 硬编码**):
|
||||
|
||||
```ts
|
||||
/** 订单列表行(状态名/可取消/商品预览均由后端给出) */
|
||||
export interface OrderListItem {
|
||||
id: number
|
||||
order_no: string
|
||||
order_date: string
|
||||
status: number
|
||||
status_name: string
|
||||
can_cancel: boolean
|
||||
total_quantity: number
|
||||
total_weight: string
|
||||
total_amount: string
|
||||
remark: string
|
||||
purchase_id: number
|
||||
bill_id: number
|
||||
created_at: string
|
||||
item_count: number
|
||||
items: Array<{ product_name: string; quantity: number; unit: string }>
|
||||
}
|
||||
```
|
||||
|
||||
`src/services/bill.ts`(**替代旧 `statement.ts`——旧 `/mini/statement` 已下线**):
|
||||
|
||||
```ts
|
||||
import { get } from '@/utils/request'
|
||||
import type { PaginatedData } from '@/types/api'
|
||||
|
||||
/** 账单(列表行与详情的 bill 字段一致) */
|
||||
export interface Bill {
|
||||
id: number
|
||||
bill_no: string
|
||||
bill_date: string
|
||||
purchase_id: number
|
||||
purchase: { id: number; purchase_no: string; purchase_date: string } | null
|
||||
product_amount: string
|
||||
delivery_fee: string
|
||||
box_num: number
|
||||
tray_num: number
|
||||
box_price: string
|
||||
tray_price: string
|
||||
added_amount: string
|
||||
total_amount: string
|
||||
status: 0 | 1
|
||||
status_name: string
|
||||
/** 支付进度:0 待支付 / 1 审核中 / 2 已支付 */
|
||||
pay_state: 0 | 1 | 2
|
||||
pay_state_name: string
|
||||
can_pay: boolean
|
||||
payment_id: number
|
||||
settlement_date: string
|
||||
paid_at: string | null
|
||||
pay_remark: string
|
||||
remark: string
|
||||
created_at: string
|
||||
}
|
||||
|
||||
export interface BillSummary {
|
||||
unpaid_count: number
|
||||
unpaid_amount: string
|
||||
}
|
||||
|
||||
export interface BillDetail {
|
||||
bill: Bill
|
||||
items: Array<{
|
||||
product_id: number; product_name: string; product_spec: string
|
||||
unit: string; price: string; quantity: number; weight: string; amount: string
|
||||
}>
|
||||
orders: Array<{
|
||||
id: number; order_no: string; order_date: string
|
||||
total_quantity: number; total_weight: string; total_amount: string; status: number
|
||||
}>
|
||||
}
|
||||
|
||||
/** 账单列表:GET /mini/bill(payable=1 为合并付款选择页口径) */
|
||||
export function getBillListApi(
|
||||
params: { status?: number; payable?: 1; start_date?: string; end_date?: string; page?: number; pageSize?: number } = {},
|
||||
) {
|
||||
return get<PaginatedData<Bill> & { summary: BillSummary }>('/mini/bill', { data: params })
|
||||
}
|
||||
|
||||
/** 账单详情:GET /mini/bill/{id} */
|
||||
export function getBillDetailApi(id: number) {
|
||||
return get<BillDetail>(`/mini/bill/${id}`)
|
||||
}
|
||||
```
|
||||
|
||||
订单列表行商品预览渲染建议:
|
||||
|
||||
```tsx
|
||||
<Text className='order-item__preview'>
|
||||
{order.items.map(i => `${i.product_name}×${i.quantity}`).join('、')}
|
||||
{order.item_count > 3 ? ` 等${order.item_count}种` : ''}
|
||||
</Text>
|
||||
```
|
||||
|
||||
## 注意事项
|
||||
|
||||
1. **状态文案一律用接口返回的 `status_name` / `pay_state_name`**:订单状态为 6 态(0/1/2/3/4/9),h5 现有 `ORDER_STATUS_MAP` 是旧 5 态(缺采购中/配送中),继续硬编码会显示异常。
|
||||
2. **账单状态标签用 `pay_state_name` 而非 `status`**:`status=0` 同时覆盖「待支付」与「审核中」两种展示;`payable=1` 筛选与 `can_pay` 同口径(待支付),合并付款页直接用它。
|
||||
3. **审核拒绝后账单自动回到待支付**(payment_id 归零),列表刷新即可重新勾选付款,无需额外处理。
|
||||
4. `summary` 统计的是**全部门店口径**(含审核中),与列表筛选参数无关;筛选「已支付」时 summary 仍返回待支付汇总。
|
||||
5. 订单列表 `items` 仅为前 3 条预览(`item_count` 为总种数),完整明细必须调详情接口;两个详情接口均校验门店归属,跨店访问返回「不存在」。
|
||||
6. `settlement_date` 由门店回款周期实时计算(门店改周期后历史账单随之变化),如需固化口径请后续提需求加快照列。
|
||||
7. 参数校验失败与业务失败一样返回 `success=false` + 中文 `msg`(HTTP 200),无需特殊分支处理。
|
||||
Reference in New Issue
Block a user