Complete the selective V2 checkpoint with its minimal AgentBus, object-storage, replay persistence, and validated-workbench shared dependency closure.
442 lines
15 KiB
JSON
442 lines
15 KiB
JSON
{
|
|
"$schema": "https://json-schema.org/draft/2020-12/schema",
|
|
"$id": "https://th-hotel.local/schemas/booking-candidate-decision-v2.schema.json",
|
|
"title": "CandidateDecisionV2",
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": [
|
|
"contract_meta",
|
|
"decision_origin",
|
|
"result_disposition",
|
|
"input_hash",
|
|
"target_decisions",
|
|
"derived_actions",
|
|
"risk_items",
|
|
"unclassified_source_texts",
|
|
"agent_trace_ref",
|
|
"issues",
|
|
"evidence_refs"
|
|
],
|
|
"properties": {
|
|
"contract_meta": { "$ref": "#/$defs/contractMeta" },
|
|
"decision_origin": { "enum": ["DETERMINISTIC", "AGENT", "FAIL_CLOSED"] },
|
|
"result_disposition": {
|
|
"enum": ["IN_SCOPE_TASKS", "GENERAL_NOTIFICATION", "RISK_NOTIFICATION", "IGNORED_DIRECTION"]
|
|
},
|
|
"input_hash": { "$ref": "#/$defs/sha256" },
|
|
"target_decisions": {
|
|
"type": "array",
|
|
"items": { "$ref": "#/$defs/targetDecision" }
|
|
},
|
|
"derived_actions": {
|
|
"type": "array",
|
|
"items": { "$ref": "#/$defs/derivedAction" }
|
|
},
|
|
"risk_items": {
|
|
"type": "array",
|
|
"items": { "$ref": "#/$defs/riskItem" }
|
|
},
|
|
"unclassified_source_texts": {
|
|
"type": "array",
|
|
"items": { "$ref": "#/$defs/unclassifiedSourceText" }
|
|
},
|
|
"agent_trace_ref": { "$ref": "#/$defs/nullableNonBlank" },
|
|
"issues": {
|
|
"type": "array",
|
|
"items": { "$ref": "#/$defs/contractIssue" }
|
|
},
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
},
|
|
"allOf": [
|
|
{
|
|
"if": { "properties": { "result_disposition": { "const": "IGNORED_DIRECTION" } } },
|
|
"then": {
|
|
"properties": {
|
|
"target_decisions": { "maxItems": 0 },
|
|
"derived_actions": { "maxItems": 0 },
|
|
"risk_items": { "maxItems": 0 },
|
|
"unclassified_source_texts": { "maxItems": 0 }
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"if": { "properties": { "result_disposition": { "const": "IN_SCOPE_TASKS" } } },
|
|
"then": {
|
|
"anyOf": [
|
|
{ "properties": { "target_decisions": { "minItems": 1 } } },
|
|
{ "properties": { "derived_actions": { "minItems": 1 } } }
|
|
]
|
|
}
|
|
},
|
|
{
|
|
"if": { "properties": { "result_disposition": { "const": "RISK_NOTIFICATION" } } },
|
|
"then": {
|
|
"properties": {
|
|
"target_decisions": { "maxItems": 0 },
|
|
"derived_actions": { "maxItems": 0 },
|
|
"risk_items": { "minItems": 1 }
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"if": { "properties": { "result_disposition": { "const": "GENERAL_NOTIFICATION" } } },
|
|
"then": {
|
|
"properties": {
|
|
"target_decisions": { "maxItems": 0 },
|
|
"derived_actions": { "maxItems": 0 },
|
|
"risk_items": { "maxItems": 0 },
|
|
"unclassified_source_texts": { "minItems": 1 }
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"if": { "properties": { "decision_origin": { "const": "FAIL_CLOSED" } } },
|
|
"then": { "properties": { "result_disposition": { "const": "RISK_NOTIFICATION" } } }
|
|
}
|
|
],
|
|
"$defs": {
|
|
"nonBlank": { "type": "string", "minLength": 1 },
|
|
"nullableNonBlank": { "type": ["string", "null"], "minLength": 1 },
|
|
"sha256": { "type": "string", "pattern": "^[a-f0-9]{64}$" },
|
|
"evidenceIdList": {
|
|
"type": "array",
|
|
"items": { "$ref": "#/$defs/nonBlank" },
|
|
"uniqueItems": true
|
|
},
|
|
"contractMeta": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": [
|
|
"contract_version",
|
|
"catalog_version",
|
|
"parser_version",
|
|
"agent_profile_version",
|
|
"processing_run_id",
|
|
"source_message_id",
|
|
"source_revision"
|
|
],
|
|
"properties": {
|
|
"contract_version": { "const": "booking-contracts-v2" },
|
|
"catalog_version": { "$ref": "#/$defs/nonBlank" },
|
|
"parser_version": { "$ref": "#/$defs/nonBlank" },
|
|
"agent_profile_version": { "$ref": "#/$defs/nonBlank" },
|
|
"processing_run_id": { "$ref": "#/$defs/nonBlank" },
|
|
"source_message_id": { "$ref": "#/$defs/nonBlank" },
|
|
"source_revision": { "type": "integer", "minimum": 0 }
|
|
}
|
|
},
|
|
"targetDecision": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": [
|
|
"target_decision_id",
|
|
"business_type",
|
|
"action_kind",
|
|
"target_identity",
|
|
"task_payload",
|
|
"linked_actions",
|
|
"issues",
|
|
"evidence_refs"
|
|
],
|
|
"properties": {
|
|
"target_decision_id": { "$ref": "#/$defs/nonBlank" },
|
|
"business_type": {
|
|
"enum": [
|
|
"NEW_BOOKING",
|
|
"UPDATE_BOOKING",
|
|
"CANCEL_BOOKING",
|
|
"TRACE_RESERVATION_NOTES",
|
|
"ROOMING_LIST"
|
|
]
|
|
},
|
|
"action_kind": {
|
|
"enum": [
|
|
"CREATE_BOOKING",
|
|
"UPDATE_BOOKING",
|
|
"CANCEL_BOOKING",
|
|
"CREATE_TRACE",
|
|
"CREATE_ROOMING_LIST_NOTICE"
|
|
]
|
|
},
|
|
"target_identity": { "$ref": "#/$defs/targetIdentity" },
|
|
"task_payload": {
|
|
"oneOf": [
|
|
{ "$ref": "#/$defs/newBookingTaskPayload" },
|
|
{ "$ref": "#/$defs/updateBookingTaskPayload" },
|
|
{ "$ref": "#/$defs/cancelBookingTaskPayload" },
|
|
{ "$ref": "#/$defs/traceTaskPayload" },
|
|
{ "$ref": "#/$defs/roomingListTaskPayload" }
|
|
]
|
|
},
|
|
"linked_actions": {
|
|
"type": "array",
|
|
"items": { "$ref": "#/$defs/linkedAction" }
|
|
},
|
|
"issues": {
|
|
"type": "array",
|
|
"items": { "$ref": "#/$defs/contractIssue" }
|
|
},
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
},
|
|
"allOf": [
|
|
{
|
|
"if": { "properties": { "business_type": { "const": "NEW_BOOKING" } } },
|
|
"then": {
|
|
"properties": {
|
|
"action_kind": { "const": "CREATE_BOOKING" },
|
|
"task_payload": { "$ref": "#/$defs/newBookingTaskPayload" }
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"if": { "properties": { "business_type": { "const": "UPDATE_BOOKING" } } },
|
|
"then": {
|
|
"properties": {
|
|
"action_kind": { "const": "UPDATE_BOOKING" },
|
|
"task_payload": { "$ref": "#/$defs/updateBookingTaskPayload" }
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"if": { "properties": { "business_type": { "const": "CANCEL_BOOKING" } } },
|
|
"then": {
|
|
"properties": {
|
|
"action_kind": { "const": "CANCEL_BOOKING" },
|
|
"task_payload": { "$ref": "#/$defs/cancelBookingTaskPayload" }
|
|
}
|
|
}
|
|
},
|
|
{
|
|
"if": { "properties": { "business_type": { "const": "TRACE_RESERVATION_NOTES" } } },
|
|
"then": { "properties": { "task_payload": { "$ref": "#/$defs/traceTaskPayload" } } }
|
|
},
|
|
{
|
|
"if": { "properties": { "business_type": { "const": "ROOMING_LIST" } } },
|
|
"then": { "properties": { "task_payload": { "$ref": "#/$defs/roomingListTaskPayload" } } }
|
|
}
|
|
]
|
|
},
|
|
"targetIdentity": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["target_ref", "resolution_status", "group_code", "names", "order_id", "confirmation_number"],
|
|
"properties": {
|
|
"target_ref": { "$ref": "#/$defs/nonBlank" },
|
|
"resolution_status": { "enum": ["RESOLVED", "UNRESOLVED", "AMBIGUOUS", "CONFLICT"] },
|
|
"group_code": { "$ref": "#/$defs/nullableNonBlank" },
|
|
"names": { "type": "array", "items": { "$ref": "#/$defs/nonBlank" }, "uniqueItems": true },
|
|
"order_id": { "$ref": "#/$defs/nullableNonBlank" },
|
|
"confirmation_number": { "$ref": "#/$defs/nullableNonBlank" }
|
|
}
|
|
},
|
|
"roomItem": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["room_type", "quantity"],
|
|
"properties": {
|
|
"room_type": { "$ref": "#/$defs/nonBlank" },
|
|
"quantity": { "type": "integer", "minimum": 0 }
|
|
}
|
|
},
|
|
"candidateRoomItem": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": [
|
|
"room_item_ref",
|
|
"source_room_raw",
|
|
"source_room_name",
|
|
"room_type",
|
|
"quantity",
|
|
"source_price_display",
|
|
"evidence_refs"
|
|
],
|
|
"properties": {
|
|
"room_item_ref": { "type": ["string", "null"] },
|
|
"source_room_raw": { "type": ["string", "null"] },
|
|
"source_room_name": { "type": ["string", "null"] },
|
|
"room_type": { "type": ["string", "null"] },
|
|
"quantity": { "type": ["number", "null"] },
|
|
"source_price_display": { "type": ["string", "null"] },
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
}
|
|
},
|
|
"newUpdateBookingProperties": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": [
|
|
"payload_type",
|
|
"booking_type",
|
|
"source_unit_ref",
|
|
"arrival_date",
|
|
"departure_date",
|
|
"room_items",
|
|
"rate_code",
|
|
"breakfast_included",
|
|
"breakfast_restaurant_code"
|
|
],
|
|
"properties": {
|
|
"payload_type": { "enum": ["NEW_BOOKING", "UPDATE_BOOKING"] },
|
|
"booking_type": { "type": ["string", "null"] },
|
|
"source_unit_ref": { "type": ["string", "null"] },
|
|
"arrival_date": { "type": ["string", "null"] },
|
|
"departure_date": { "type": ["string", "null"] },
|
|
"room_items": { "type": "array", "items": { "$ref": "#/$defs/candidateRoomItem" } },
|
|
"rate_code": { "type": ["string", "null"] },
|
|
"breakfast_included": { "type": ["boolean", "null"] },
|
|
"breakfast_restaurant_code": { "type": ["string", "null"] }
|
|
}
|
|
},
|
|
"newBookingTaskPayload": {
|
|
"$ref": "#/$defs/newUpdateBookingProperties",
|
|
"properties": { "payload_type": { "const": "NEW_BOOKING" } }
|
|
},
|
|
"updateBookingTaskPayload": {
|
|
"$ref": "#/$defs/newUpdateBookingProperties",
|
|
"properties": { "payload_type": { "const": "UPDATE_BOOKING" } }
|
|
},
|
|
"cancelBookingTaskPayload": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["payload_type"],
|
|
"properties": {
|
|
"payload_type": { "const": "CANCEL_BOOKING" }
|
|
}
|
|
},
|
|
"traceTaskPayload": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["payload_type", "service_items", "department_code"],
|
|
"properties": {
|
|
"payload_type": { "const": "TRACE" },
|
|
"service_items": { "type": "array", "items": { "$ref": "#/$defs/traceServiceItem" }, "minItems": 1 },
|
|
"department_code": { "type": ["string", "null"], "enum": ["FO", "FO+HSK", null] }
|
|
}
|
|
},
|
|
"traceServiceItem": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["service_item_id", "service_type", "service_text", "room_type", "quantity", "evidence_refs"],
|
|
"properties": {
|
|
"service_item_id": { "$ref": "#/$defs/nonBlank" },
|
|
"service_type": { "enum": ["GENERAL_SERVICE", "EXTRA_BED"] },
|
|
"service_text": { "$ref": "#/$defs/nonBlank" },
|
|
"room_type": { "type": ["string", "null"] },
|
|
"quantity": { "type": ["number", "null"] },
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
}
|
|
},
|
|
"roomingListTaskPayload": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["payload_type", "attachment_id", "material_evidence_refs"],
|
|
"properties": {
|
|
"payload_type": { "const": "ROOMING_LIST" },
|
|
"attachment_id": { "$ref": "#/$defs/nonBlank" },
|
|
"material_evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
}
|
|
},
|
|
"linkedAction": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["linked_action_id", "linked_action_type", "source_target_ref", "target_target_ref", "evidence_refs"],
|
|
"properties": {
|
|
"linked_action_id": { "$ref": "#/$defs/nonBlank" },
|
|
"linked_action_type": {
|
|
"const": "GROUP_CODE_REPLACEMENT"
|
|
},
|
|
"source_target_ref": { "$ref": "#/$defs/nonBlank" },
|
|
"target_target_ref": { "$ref": "#/$defs/nonBlank" },
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
}
|
|
},
|
|
"derivedAction": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": [
|
|
"derived_action_id",
|
|
"derived_action_type",
|
|
"source_target_ref",
|
|
"actual_target_decision_id",
|
|
"room_items",
|
|
"issues",
|
|
"evidence_refs"
|
|
],
|
|
"properties": {
|
|
"derived_action_id": { "$ref": "#/$defs/nonBlank" },
|
|
"derived_action_type": { "enum": ["ALLOTMENT_SOURCE_DEDUCTION", "ALLOTMENT_SOURCE_WHOLE_CANCEL"] },
|
|
"source_target_ref": { "$ref": "#/$defs/nonBlank" },
|
|
"actual_target_decision_id": { "$ref": "#/$defs/nullableNonBlank" },
|
|
"room_items": { "type": "array", "items": { "$ref": "#/$defs/deductionRoomItem" } },
|
|
"issues": { "type": "array", "items": { "$ref": "#/$defs/contractIssue" } },
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
},
|
|
"allOf": [
|
|
{
|
|
"if": { "properties": { "derived_action_type": { "const": "ALLOTMENT_SOURCE_DEDUCTION" } } },
|
|
"then": {
|
|
"properties": {
|
|
"actual_target_decision_id": { "$ref": "#/$defs/nonBlank" }
|
|
}
|
|
},
|
|
"else": {
|
|
"properties": {
|
|
"actual_target_decision_id": { "type": "null" },
|
|
"room_items": { "maxItems": 0 }
|
|
}
|
|
}
|
|
}
|
|
]
|
|
},
|
|
"deductionRoomItem": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["room_item_ref", "room_type", "quantity", "evidence_refs"],
|
|
"properties": {
|
|
"room_item_ref": { "type": ["string", "null"] },
|
|
"room_type": { "type": ["string", "null"] },
|
|
"quantity": { "type": ["number", "null"] },
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
}
|
|
},
|
|
"riskItem": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["risk_item_id", "risk_code", "target_ref", "source_text", "issues", "evidence_refs"],
|
|
"properties": {
|
|
"risk_item_id": { "$ref": "#/$defs/nonBlank" },
|
|
"risk_code": { "$ref": "#/$defs/nonBlank" },
|
|
"target_ref": { "$ref": "#/$defs/nullableNonBlank" },
|
|
"source_text": { "type": ["string", "null"] },
|
|
"issues": { "type": "array", "items": { "$ref": "#/$defs/contractIssue" } },
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
}
|
|
},
|
|
"unclassifiedSourceText": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["source_text_id", "sequence", "original_text", "evidence_refs"],
|
|
"properties": {
|
|
"source_text_id": { "$ref": "#/$defs/nonBlank" },
|
|
"sequence": { "type": "integer", "minimum": 0 },
|
|
"original_text": { "$ref": "#/$defs/nonBlank" },
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" }
|
|
}
|
|
},
|
|
"contractIssue": {
|
|
"type": "object",
|
|
"additionalProperties": false,
|
|
"required": ["issue_id", "code", "severity", "scope", "target_ref", "message_key", "evidence_refs", "retryable"],
|
|
"properties": {
|
|
"issue_id": { "$ref": "#/$defs/nonBlank" },
|
|
"code": { "$ref": "#/$defs/nonBlank" },
|
|
"severity": { "enum": ["INFO", "WARNING", "ERROR", "BLOCKER"] },
|
|
"scope": { "enum": ["MESSAGE", "TARGET", "FIELD", "DERIVED_ACTION", "RISK_ITEM"] },
|
|
"target_ref": { "$ref": "#/$defs/nullableNonBlank" },
|
|
"message_key": { "$ref": "#/$defs/nonBlank" },
|
|
"evidence_refs": { "$ref": "#/$defs/evidenceIdList" },
|
|
"retryable": { "type": "boolean" }
|
|
}
|
|
}
|
|
}
|
|
}
|