告警计时器接口文档(泰额版)
模块:标签告警计时器(Label Alert Timer)
服务:LabelAlertTimerAppService
范围:泰额版后端,数据在租户业务库(非antis-foodlabeling-host)
认证:Authorization: Bearer {token};业务请求建议带__tenant: {tenantId}
JSON:camelCase
Base URL 示例:http://127.0.0.1:19002(以实际部署为准)
更新日期:2026-08-07
1. 业务说明
| 概念 | 说明 |
|---|---|
| 用途 | 跟踪已经打印的标签过期时间,供 App / 前端做倒计时与警告列表 |
| 与打印关系 | 过期与「能不能打印」无关;打印接口不会因计时器已过期而拒绝打印 |
| 过期时刻 | 与 Print Log「Expiration」列同源(ReportsPrintLogExpiryHelper.TryResolveExpiryDateTime) |
| 批次维度 | 同一 BatchId 无论打印多少张,仅一条计时器(取 CopyIndex 最小的 fl_label_print_task) |
| 无过期不上列表 | 模板无法解析过期时刻时,不写入计时器、不出现在列表 |
| 列表范围 | 门店级:该 locationId 下未软删的全部计时器(不限当前用户自己打印) |
| 状态 | running(未过期)/ expired(已过期) |
| 软删 | 用户可删除计时器;删除后不再出现在列表,不影响历史打印任务 |
写入时机
UsAppLabelingAppService.PrintAsync/ReprintAsync成功创建批次后自动写入(LabelAlertTimerWriteHelper.TryCreateFromPrintBatchAsync)- 幂等重试(相同
clientRequestId)返回前也会补写一次(按BatchId唯一索引去重;含软删记录也不再插入)
建表
| 项 | 说明 |
|---|---|
| 脚本 | 泰额版/.../module/food-labeling-us/scripts/fl_label_alert_timer.sql |
| 表名 | fl_label_alert_timer |
| 新租户 | 开通时嵌入资源自动执行 |
| 已有租户 | 需用具备 CREATE 权限的账号在业务库手动执行(业务账号 netteam 通常无建表权限) |
主要字段:BatchId(唯一)、PrintTaskId、LabelId、LocationId、PrintedAt、ExpiresAt、DurationSeconds、Title、Subtitle、IsDeleted。
2. 接口一览
| 功能 | 方法 | 路由 | 说明 |
|---|---|---|---|
| 分页列表 | POST | /api/app/label-alert-timer/list |
locationId 必填 |
| App 警告列表 | POST | /api/app/label-alert-timer/app-list |
推荐 App 使用;locationId 可空(走已选门店缓存) |
| 软删除 | DELETE | /api/app/label-alert-timer/{id} |
软删计时器 |
| 查询过期/倒计时 | POST | /api/app/label-alert-timer/check-expired |
单条状态查询;仅展示,不拦打印 |
全部需登录。列表 / 删除 / 查询均校验当前账号可访问对应门店。
获取 Token(App)
POST /api/app/th-app-auth/login
Content-Type: application/json
{ "email": "mai@123.com", "password": "123456", "tenantId": "可选-租户Id" }
后续请求头:
Authorization: Bearer {token}
__tenant: {tenantId}
Content-Type: application/json
3. 分页列表
POST /api/app/label-alert-timer/list
请求
{
"locationId": "3a21220f-db37-3e32-7390-d55f64cd62a8",
"skipCount": 1,
"maxResultCount": 20,
"dateDay": "2026-08-07"
}
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
| locationId | string | 是 | 当前门店 Id;空则报错「门店Id不能为空」 |
| skipCount | number | 是 | 页码(从 1 开始,与项目分页约定一致) |
| maxResultCount | number | 是 | 每页条数 |
| dateDay | string | 否 | yyyy-MM-dd,按 PrintedAt 自然日筛选 |
响应
{
"pageIndex": 1,
"pageSize": 20,
"totalCount": 1,
"totalPages": 1,
"items": [
{
"id": "1987654321000123456",
"batchId": "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee",
"printTaskId": "bbbbbbbb-cccc-dddd-eeee-ffffffffffff",
"labelId": "label-id-001",
"labelCode": "LB_001",
"title": "Chicken Prep (4 hours)",
"subtitle": "4 hours Completes at 2:30 PM",
"totalTime": 14400,
"remainingTime": 7200,
"status": "running",
"expiresAt": "2026-08-07T14:30:00",
"printedAt": "2026-08-07T10:30:00",
"locationId": "3a21220f-db37-3e32-7390-d55f64cd62a8",
"productName": "Grilled Chicken"
}
]
}
列表项字段(items[])
| 字段 | 类型 | 说明 |
|---|---|---|
| id | string | 计时器主键 |
| batchId | string | 打印批次 Id |
| printTaskId | string | 代表任务 Id(CopyIndex 最小) |
| labelId | string | 标签 Id |
| labelCode | string \ | null |
| title | string | 标题(含时长文案) |
| subtitle | string | 副标题(含完成时刻文案) |
| totalTime | number | 总时长(秒),同库字段 DurationSeconds |
| remainingTime | number | 剩余秒数,max(0, ExpiresAt - now);App 倒计时用此字段 |
| status | string | running / expired |
| expiresAt | string | 过期时刻 |
| printedAt | string | 打印时刻 |
| locationId | string | 门店 Id |
| productName | string \ | null |
排序:先 ExpiresAt 降序,再 PrintedAt 降序。
4. App 警告列表(推荐)
POST /api/app/label-alert-timer/app-list
当前登录账号可访问的门店下警告列表;出参结构与第 3 节 list 完全相同(含 remainingTime 倒计时)。
请求
{
"locationId": "3a21220f-db37-3e32-7390-d55f64cd62a8",
"skipCount": 1,
"maxResultCount": 50
}
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
| locationId | string | 否 | 当前门店;为空时取 POST /api/app/us-app-auth/select-admin-scope-location 写入的已选门店缓存 |
| skipCount | number | 是 | 页码(从 1 开始) |
| maxResultCount | number | 是 | 每页条数 |
| dateDay | string | 否 | yyyy-MM-dd,按 PrintedAt 筛选 |
门店解析规则
- 入参
locationId有值 → 用入参 - 入参为空 → 读管理员已选门店缓存
- 仍无门店 → 400:「请先选择门店或传入 locationId」
- 有门店但当前账号不可访问 → 权限校验失败(与
list相同)
倒计时对接
| 字段 | App 用法 |
|---|---|
| remainingTime | 初始剩余秒数;进入页面后可本地每秒 -1,或定时重新拉列表校正 |
| totalTime | 进度条分母:progress = (totalTime - remainingTime) / totalTime |
| status | expired 时 remainingTime 为 0,可高亮/置顶 |
| expiresAt | 展示绝对过期时间;与 Print Log Expiration 对齐 |
5. 软删除
DELETE /api/app/label-alert-timer/{id}
| 项 | 说明 |
|---|---|
| 路径参数 id | 计时器主键 |
| 权限 | 校验当前用户可访问该计时器所属 LocationId |
| 行为 | IsDeleted=1,DeletionTime=now |
| 不存在/已删 | 报错「计时器不存在或已删除」 |
无响应体(成功即可)。
6. 查询过期/倒计时状态
POST /api/app/label-alert-timer/check-expired
仅查询已打印批次的过期状态与剩余秒数,供单条展示。
不得用于拦截打印;打印流程不要依赖本接口结果做「禁止打印」。
请求
至少提供 timerId、batchId、printTaskId 之一(优先级:timerId > batchId > printTaskId):
{
"batchId": "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee"
}
| 字段 | 说明 |
|---|---|
| timerId | 计时器 Id |
| batchId | 打印批次 Id |
| printTaskId | 打印任务 Id(同批次任意任务均可,会反查 BatchId) |
未提供任一标识 → 「请至少提供 timerId、batchId 或 printTaskId 之一」。
响应(找到记录)
{
"found": true,
"isExpired": false,
"expiresAt": "2026-08-07T14:30:00",
"remainingSeconds": 7200,
"status": "running",
"title": "Chicken Prep (4 hours)",
"subtitle": "4 hours Completes at 2:30 PM",
"timerId": "1987654321000123456",
"batchId": "aaaaaaaa-bbbb-cccc-dddd-eeeeeeeeeeee"
}
响应(无记录)
{
"found": false,
"isExpired": false,
"remainingSeconds": 0
}
| 字段 | 说明 |
|---|---|
| found | 是否找到未删除的计时器 |
| isExpired | 是否已过期;无记录时为 false |
| remainingSeconds | 剩余秒数(已过期或无记录为 0);与列表的 remainingTime 含义相同 |
| status | running / expired;无记录时可能为空 |
| expiresAt / title / subtitle / timerId / batchId | 找到记录时有值 |
7. 常见错误文案
| 场景 | 文案 |
|---|---|
| 入参为空 | 入参不能为空 |
| 未登录 | 用户未登录 |
| list 未传门店 | 门店Id不能为空 |
| app-list 无门店且无缓存 | 请先选择门店或传入 locationId |
| 删除 Id 为空 | 计时器Id不能为空 |
| 记录不存在/已删 | 计时器不存在或已删除 |
| check-expired 无标识 | 请至少提供 timerId、batchId 或 printTaskId 之一 |
| 无门店权限 | 由门店权限校验抛出(与打印日志门店校验一致) |
8. curl 示例
# 1) 登录拿 Token(按实际环境替换)
curl -s -X POST "http://127.0.0.1:19002/api/app/th-app-auth/login" \
-H "Content-Type: application/json" \
-d '{"email":"mai@123.com","password":"123456","tenantId":"TENANT_ID"}'
# 2) App 警告列表(含倒计时)
curl -s -X POST "http://127.0.0.1:19002/api/app/label-alert-timer/app-list" \
-H "Authorization: Bearer TOKEN" \
-H "__tenant: TENANT_ID" \
-H "Content-Type: application/json" \
-d '{"locationId":"LOCATION_ID","skipCount":1,"maxResultCount":50}'
# 3) 通用分页列表
curl -s -X POST "http://127.0.0.1:19002/api/app/label-alert-timer/list" \
-H "Authorization: Bearer TOKEN" \
-H "__tenant: TENANT_ID" \
-H "Content-Type: application/json" \
-d '{"locationId":"LOCATION_ID","skipCount":1,"maxResultCount":20}'
# 4) 单条过期/倒计时查询(仅展示)
curl -s -X POST "http://127.0.0.1:19002/api/app/label-alert-timer/check-expired" \
-H "Authorization: Bearer TOKEN" \
-H "__tenant: TENANT_ID" \
-H "Content-Type: application/json" \
-d '{"batchId":"YOUR_BATCH_ID"}'
# 5) 软删除
curl -s -X DELETE "http://127.0.0.1:19002/api/app/label-alert-timer/TIMER_ID" \
-H "Authorization: Bearer TOKEN" \
-H "__tenant: TENANT_ID"
9. 前端 / App 对接建议
- 警告页:优先调
app-list;用remainingTime(秒)做倒计时;status=expired可高亮。 - 不要做打印前过期拦截:过期与可否打印无关;计时器在打印成功后才写入。
- 与 Print Log 一致:展示过期时间时与 Print Log Expiration 列对齐,避免两套算法。
- 删除:左滑/长按调 DELETE;仅隐藏计时器,不影响历史打印任务。
- 校正:长时间停留页面时,可定时重拉
app-list,避免本地倒计时漂移。