feat:核销打印兑换券

This commit is contained in:
dzc committed 2026-09-04 17:34:02 +08:00
1 parent fb90b477b9
commit d517f45f38
11 files changed
+1560 -75

No files matched your search

+123
View File
@@ -102,9 +102,16 @@ class ServiceOrderEvidenceImage {
const ServiceOrderEvidenceImage({
required this.id,
required this.evidenceType,
this.evidenceTypeName,
required this.evidenceRole,
this.evidenceRoleName,
required this.sequenceNo,
required this.status,
this.statusName,
this.similarity,
this.similarityThreshold,
this.hardId,
this.capturedAt,
this.imageHash,
this.imageUrl,
this.failureReason,
@@ -117,15 +124,39 @@ class ServiceOrderEvidenceImage {
/// 服务端稳定证据类型编码。
final String evidenceType;
/// 服务端按稳定编码转换的证据类型中文名称。
final String? evidenceTypeName;
/// 服务端稳定图片角色编码。
final String evidenceRole;
/// 服务端按稳定编码转换的图片角色中文名称。
final String? evidenceRoleName;
/// 同一角色下的图片序号。
final int sequenceNo;
/// 服务端证据状态,取 PENDING、AVAILABLE 或 UNAVAILABLE。
final String status;
/// 服务端按稳定编码转换的证据状态中文名称。
final String? statusName;
/// 人脸识别相似度快照,范围为 0 到 1,非人脸凭证允许为空。
@JsonKey(fromJson: JsonTool.anyToNullableDouble)
final double? similarity;
/// 人脸识别采用的阈值快照,范围为 0 到 1。
@JsonKey(fromJson: JsonTool.anyToNullableDouble)
final double? similarityThreshold;
/// 采集该凭证的服务端设备 ID。
@JsonKey(fromJson: JsonTool.anyToString)
final String? hardId;
/// 终端真正完成识别的本地采集时间。
final DateTime? capturedAt;
/// 服务端已登记的图片 SHA-256。
final String? imageHash;
@@ -143,6 +174,98 @@ class ServiceOrderEvidenceImage {
Map<String, dynamic> toJson() => _$ServiceOrderEvidenceImageToJson(this);
}
/// 服务端打印任务的只读快照,用于核销完整详情展示和兑换券重打定位。
@JsonSerializable()
class ServicePrintRecord {
/// 创建一条不写入终端本地数据库的服务端打印任务快照。
const ServicePrintRecord({
required this.id,
required this.orderId,
this.hardId,
this.hardName,
this.printerHardId,
this.printerHardName,
required this.printType,
required this.printNo,
required this.retryVersion,
required this.attemptCount,
required this.status,
this.failureStage,
this.lastError,
this.printedAt,
this.reprintReason,
this.pic,
this.createTime,
});
/// 服务端 hard_invoice 打印任务主键。
@JsonKey(fromJson: JsonTool.anyToRequiredString)
final String id;
/// 打印凭证所属的服务端订单主键。
@JsonKey(fromJson: JsonTool.anyToRequiredString)
final String orderId;
/// 产生该任务的食堂或超市业务终端 ID。
@JsonKey(fromJson: JsonTool.anyToString)
final String? hardId;
/// 产生该任务的食堂或超市业务终端名称。
final String? hardName;
/// 服务端绑定的逻辑打印机资产 ID。
@JsonKey(fromJson: JsonTool.anyToString)
final String? printerHardId;
/// 服务端绑定的逻辑打印机资产名称。
final String? printerHardName;
/// 凭证类型编码,1 为发票,2 为核销兑换券。
@JsonKey(defaultValue: '1')
final String printType;
/// 同一订单和凭证类型下从 1 开始的打印序号。
@JsonKey(defaultValue: 1)
final int printNo;
/// 失败任务的人工重试版本,用于终端过滤过期 MQTT 消息。
@JsonKey(defaultValue: 0)
final int retryVersion;
/// 终端已经执行的 USB 打印尝试次数。
@JsonKey(defaultValue: 0)
final int attemptCount;
/// 服务端打印任务状态编码,取 0 到 4。
@JsonKey(defaultValue: '')
final String status;
/// 最近一次失败阶段的稳定编码,成功和未处理任务允许为空。
final String? failureStage;
/// 最近一次可展示的失败摘要,不包含认证或支付凭证。
final String? lastError;
/// 终端确认完整写入 USB 打印机的服务端记录时间。
final DateTime? printedAt;
/// 人工重新打印时填写的原因,首次打印允许为空。
final String? reprintReason;
/// 后端生成的打印凭证图片地址,生成前或生成失败时允许为空。
final String? pic;
/// 服务端打印任务创建时间。
final DateTime? createTime;
/// 从终端专用在线接口解析打印任务。
factory ServicePrintRecord.fromJson(Map<String, dynamic> json) =>
_$ServicePrintRecordFromJson(json);
/// 转换为测试和诊断使用的 JSON。
Map<String, dynamic> toJson() => _$ServicePrintRecordToJson(this);
}
/// 按终端订单号对账返回的服务端订单和全部证据位置。
@JsonSerializable()
class ServiceOrderEvidenceResolve {
@@ -70,9 +70,19 @@ ServiceOrderEvidenceImage _$ServiceOrderEvidenceImageFromJson(
ServiceOrderEvidenceImage(
id: JsonTool.anyToRequiredString(json['id']),
evidenceType: json['evidenceType'] as String,
evidenceTypeName: json['evidenceTypeName'] as String?,
evidenceRole: json['evidenceRole'] as String,
evidenceRoleName: json['evidenceRoleName'] as String?,
sequenceNo: (json['sequenceNo'] as num).toInt(),
status: json['status'] as String,
statusName: json['statusName'] as String?,
similarity: JsonTool.anyToNullableDouble(json['similarity']),
similarityThreshold:
JsonTool.anyToNullableDouble(json['similarityThreshold']),
hardId: JsonTool.anyToString(json['hardId']),
capturedAt: json['capturedAt'] == null
? null
: DateTime.parse(json['capturedAt'] as String),
imageHash: json['imageHash'] as String?,
imageUrl: json['imageUrl'] as String?,
failureReason: json['failureReason'] as String?,
@@ -83,14 +93,67 @@ Map<String, dynamic> _$ServiceOrderEvidenceImageToJson(
<String, dynamic>{
'id': instance.id,
'evidenceType': instance.evidenceType,
'evidenceTypeName': instance.evidenceTypeName,
'evidenceRole': instance.evidenceRole,
'evidenceRoleName': instance.evidenceRoleName,
'sequenceNo': instance.sequenceNo,
'status': instance.status,
'statusName': instance.statusName,
'similarity': instance.similarity,
'similarityThreshold': instance.similarityThreshold,
'hardId': instance.hardId,
'capturedAt': instance.capturedAt?.toIso8601String(),
'imageHash': instance.imageHash,
'imageUrl': instance.imageUrl,
'failureReason': instance.failureReason,
};
ServicePrintRecord _$ServicePrintRecordFromJson(Map<String, dynamic> json) =>
ServicePrintRecord(
id: JsonTool.anyToRequiredString(json['id']),
orderId: JsonTool.anyToRequiredString(json['orderId']),
hardId: JsonTool.anyToString(json['hardId']),
hardName: json['hardName'] as String?,
printerHardId: JsonTool.anyToString(json['printerHardId']),
printerHardName: json['printerHardName'] as String?,
printType: json['printType'] as String? ?? '1',
printNo: (json['printNo'] as num?)?.toInt() ?? 1,
retryVersion: (json['retryVersion'] as num?)?.toInt() ?? 0,
attemptCount: (json['attemptCount'] as num?)?.toInt() ?? 0,
status: json['status'] as String? ?? '',
failureStage: json['failureStage'] as String?,
lastError: json['lastError'] as String?,
printedAt: json['printedAt'] == null
? null
: DateTime.parse(json['printedAt'] as String),
reprintReason: json['reprintReason'] as String?,
pic: json['pic'] as String?,
createTime: json['createTime'] == null
? null
: DateTime.parse(json['createTime'] as String),
);
Map<String, dynamic> _$ServicePrintRecordToJson(ServicePrintRecord instance) =>
<String, dynamic>{
'id': instance.id,
'orderId': instance.orderId,
'hardId': instance.hardId,
'hardName': instance.hardName,
'printerHardId': instance.printerHardId,
'printerHardName': instance.printerHardName,
'printType': instance.printType,
'printNo': instance.printNo,
'retryVersion': instance.retryVersion,
'attemptCount': instance.attemptCount,
'status': instance.status,
'failureStage': instance.failureStage,
'lastError': instance.lastError,
'printedAt': instance.printedAt?.toIso8601String(),
'reprintReason': instance.reprintReason,
'pic': instance.pic,
'createTime': instance.createTime?.toIso8601String(),
};
ServiceOrderEvidenceResolve _$ServiceOrderEvidenceResolveFromJson(
Map<String, dynamic> json) =>
ServiceOrderEvidenceResolve(