@resolveio/server-lib 22.3.190 → 22.3.191
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -239,6 +239,22 @@ export interface ResolveIOSupportCustomerReplyPolicyInput {
|
|
|
239
239
|
releasePolicy?: ResolveIOAIManagerHotfixFirstReleasePolicy;
|
|
240
240
|
releaseGatePassed?: boolean;
|
|
241
241
|
}
|
|
242
|
+
export type ResolveIOSupportClarificationMissingField = 'reproduction_blocker' | 'expected_result' | 'observed_result' | 'account_customer_context' | 'example_record_or_action_path';
|
|
243
|
+
export interface ResolveIOSupportClarificationContract {
|
|
244
|
+
contractId: string;
|
|
245
|
+
status: 'ready' | 'blocked';
|
|
246
|
+
missingField: ResolveIOSupportClarificationMissingField;
|
|
247
|
+
question: string;
|
|
248
|
+
sourceBlockers: string[];
|
|
249
|
+
oneQuestionOnly: boolean;
|
|
250
|
+
customerFacingDraftAllowed: boolean;
|
|
251
|
+
customerSendAllowed: boolean;
|
|
252
|
+
parksTicketUntilCustomerReply: boolean;
|
|
253
|
+
nextCommands: string[];
|
|
254
|
+
forbiddenActions: string[];
|
|
255
|
+
requiredEvidence: string[];
|
|
256
|
+
createdAt: string;
|
|
257
|
+
}
|
|
242
258
|
export interface ResolveIOSupportCustomerReplyPolicy {
|
|
243
259
|
action: ResolveIOSupportCustomerReplyAction;
|
|
244
260
|
canDraftCustomerReply: boolean;
|
|
@@ -248,6 +264,7 @@ export interface ResolveIOSupportCustomerReplyPolicy {
|
|
|
248
264
|
reason: string;
|
|
249
265
|
requiredEvidence: string[];
|
|
250
266
|
clarificationQuestion?: string;
|
|
267
|
+
clarificationContract?: ResolveIOSupportClarificationContract;
|
|
251
268
|
humanReviewPacket?: ResolveIOSupportHumanReviewPacket;
|
|
252
269
|
draftBasis?: {
|
|
253
270
|
issueClass: ResolveIOSupportIssueClass;
|
|
@@ -835,6 +852,13 @@ export declare function validateResolveIOSupportDiagnosisGate(value: any, option
|
|
|
835
852
|
maxOwnerFiles?: number;
|
|
836
853
|
}): ResolveIOSupportDiagnosisGateValidation;
|
|
837
854
|
export declare function evaluateResolveIOSupportBusinessProofReadiness(input?: ResolveIOSupportBusinessProofReadinessInput): ResolveIOSupportBusinessProofReadiness;
|
|
855
|
+
export declare function buildResolveIOSupportClarificationContract(gate: ResolveIOSupportDiagnosisGate | undefined, blockers?: string[], now?: Date | string): ResolveIOSupportClarificationContract;
|
|
856
|
+
export declare function validateResolveIOSupportClarificationContract(value: any): {
|
|
857
|
+
valid: boolean;
|
|
858
|
+
status: 'ready' | 'blocked';
|
|
859
|
+
blockers: string[];
|
|
860
|
+
normalized: ResolveIOSupportClarificationContract;
|
|
861
|
+
};
|
|
838
862
|
export declare function decideResolveIOSupportCustomerReplyPolicy(input?: ResolveIOSupportCustomerReplyPolicyInput): ResolveIOSupportCustomerReplyPolicy;
|
|
839
863
|
export declare function buildResolveIOSupportIssueClassProbes(value: any): ResolveIOSupportIssueClassProbe[];
|
|
840
864
|
export declare function validateResolveIOSupportIssueClassProbePlan(value: any, diagnosisGate?: any, now?: Date | string): ResolveIOSupportIssueClassProbePlanValidation;
|
|
@@ -55,6 +55,8 @@ exports.normalizeResolveIOSupportDiagnosisGate = normalizeResolveIOSupportDiagno
|
|
|
55
55
|
exports.extractResolveIOSupportDiagnosisGateFromText = extractResolveIOSupportDiagnosisGateFromText;
|
|
56
56
|
exports.validateResolveIOSupportDiagnosisGate = validateResolveIOSupportDiagnosisGate;
|
|
57
57
|
exports.evaluateResolveIOSupportBusinessProofReadiness = evaluateResolveIOSupportBusinessProofReadiness;
|
|
58
|
+
exports.buildResolveIOSupportClarificationContract = buildResolveIOSupportClarificationContract;
|
|
59
|
+
exports.validateResolveIOSupportClarificationContract = validateResolveIOSupportClarificationContract;
|
|
58
60
|
exports.decideResolveIOSupportCustomerReplyPolicy = decideResolveIOSupportCustomerReplyPolicy;
|
|
59
61
|
exports.buildResolveIOSupportIssueClassProbes = buildResolveIOSupportIssueClassProbes;
|
|
60
62
|
exports.validateResolveIOSupportIssueClassProbePlan = validateResolveIOSupportIssueClassProbePlan;
|
|
@@ -1628,6 +1630,105 @@ function buildSupportClarificationQuestion(gate, blockers) {
|
|
|
1628
1630
|
}
|
|
1629
1631
|
return 'Can you send one concrete example record, screen, or action path where this issue still occurs?';
|
|
1630
1632
|
}
|
|
1633
|
+
function resolveSupportClarificationMissingField(gate, blockers) {
|
|
1634
|
+
if ((gate === null || gate === void 0 ? void 0 : gate.issue_case.reproduction_status) === 'blocked' && gate.issue_case.reproduction_blocker) {
|
|
1635
|
+
return 'reproduction_blocker';
|
|
1636
|
+
}
|
|
1637
|
+
if (blockers.some(function (blocker) { return /expected_result/.test(blocker); })) {
|
|
1638
|
+
return 'expected_result';
|
|
1639
|
+
}
|
|
1640
|
+
if (blockers.some(function (blocker) { return /observed_result/.test(blocker); })) {
|
|
1641
|
+
return 'observed_result';
|
|
1642
|
+
}
|
|
1643
|
+
if (blockers.some(function (blocker) { return /account_customer_context/.test(blocker); })) {
|
|
1644
|
+
return 'account_customer_context';
|
|
1645
|
+
}
|
|
1646
|
+
return 'example_record_or_action_path';
|
|
1647
|
+
}
|
|
1648
|
+
function buildResolveIOSupportClarificationContract(gate, blockers, now) {
|
|
1649
|
+
if (blockers === void 0) { blockers = []; }
|
|
1650
|
+
var sourceBlockers = cleanList(blockers, 20, 500);
|
|
1651
|
+
var missingField = resolveSupportClarificationMissingField(gate, sourceBlockers);
|
|
1652
|
+
var question = buildSupportClarificationQuestion(gate, sourceBlockers);
|
|
1653
|
+
var createdAt = isoNow(now);
|
|
1654
|
+
return {
|
|
1655
|
+
contractId: "support-clarification-".concat(hashResolveIOSupportV5Evidence({
|
|
1656
|
+
missingField: missingField,
|
|
1657
|
+
question: question,
|
|
1658
|
+
sourceBlockers: sourceBlockers,
|
|
1659
|
+
ticketRoute: gate === null || gate === void 0 ? void 0 : gate.issue_case.route_module,
|
|
1660
|
+
createdAt: createdAt.slice(0, 16)
|
|
1661
|
+
}).slice(0, 16)),
|
|
1662
|
+
status: 'ready',
|
|
1663
|
+
missingField: missingField,
|
|
1664
|
+
question: question,
|
|
1665
|
+
sourceBlockers: sourceBlockers,
|
|
1666
|
+
oneQuestionOnly: (question.match(/\?/g) || []).length === 1,
|
|
1667
|
+
customerFacingDraftAllowed: true,
|
|
1668
|
+
customerSendAllowed: false,
|
|
1669
|
+
parksTicketUntilCustomerReply: true,
|
|
1670
|
+
nextCommands: ['review_customer_clarification', 'send_after_human_review', 'park_ticket_until_customer_reply'],
|
|
1671
|
+
forbiddenActions: [
|
|
1672
|
+
'Do not run product repair from a guessed reproduction path.',
|
|
1673
|
+
'Do not ask multiple customer questions in one automated clarification.',
|
|
1674
|
+
'Do not mark the ticket resolved from a clarification draft.'
|
|
1675
|
+
],
|
|
1676
|
+
requiredEvidence: [
|
|
1677
|
+
"missing_field=".concat(missingField),
|
|
1678
|
+
'one customer-facing question',
|
|
1679
|
+
'human approval before send',
|
|
1680
|
+
'park_ticket_until_customer_reply'
|
|
1681
|
+
],
|
|
1682
|
+
createdAt: createdAt
|
|
1683
|
+
};
|
|
1684
|
+
}
|
|
1685
|
+
function validateResolveIOSupportClarificationContract(value) {
|
|
1686
|
+
var source = cleanObject(value);
|
|
1687
|
+
var missingField = cleanText(source.missingField || source.missing_field, 120);
|
|
1688
|
+
var question = cleanText(source.question, 1000);
|
|
1689
|
+
var sourceBlockers = cleanList(source.sourceBlockers || source.source_blockers, 20, 500);
|
|
1690
|
+
var questionMarkCount = (question.match(/\?/g) || []).length;
|
|
1691
|
+
var normalized = {
|
|
1692
|
+
contractId: cleanText(source.contractId || source.contract_id, 160),
|
|
1693
|
+
status: source.status === 'ready' ? 'ready' : 'blocked',
|
|
1694
|
+
missingField: missingField,
|
|
1695
|
+
question: question,
|
|
1696
|
+
sourceBlockers: sourceBlockers,
|
|
1697
|
+
oneQuestionOnly: source.oneQuestionOnly === true || source.one_question_only === true || questionMarkCount === 1,
|
|
1698
|
+
customerFacingDraftAllowed: source.customerFacingDraftAllowed === true || source.customer_facing_draft_allowed === true,
|
|
1699
|
+
customerSendAllowed: source.customerSendAllowed === true || source.customer_send_allowed === true,
|
|
1700
|
+
parksTicketUntilCustomerReply: source.parksTicketUntilCustomerReply === true || source.parks_ticket_until_customer_reply === true,
|
|
1701
|
+
nextCommands: cleanList(source.nextCommands || source.next_commands, 12, 200),
|
|
1702
|
+
forbiddenActions: cleanList(source.forbiddenActions || source.forbidden_actions, 12, 500),
|
|
1703
|
+
requiredEvidence: cleanList(source.requiredEvidence || source.required_evidence, 12, 500),
|
|
1704
|
+
createdAt: cleanText(source.createdAt || source.created_at, 120)
|
|
1705
|
+
};
|
|
1706
|
+
var validMissingFields = [
|
|
1707
|
+
'reproduction_blocker',
|
|
1708
|
+
'expected_result',
|
|
1709
|
+
'observed_result',
|
|
1710
|
+
'account_customer_context',
|
|
1711
|
+
'example_record_or_action_path'
|
|
1712
|
+
];
|
|
1713
|
+
var blockers = [
|
|
1714
|
+
normalized.contractId ? '' : 'Clarification contract is missing contractId.',
|
|
1715
|
+
validMissingFields.includes(normalized.missingField) ? '' : 'Clarification contract is missing a valid missingField.',
|
|
1716
|
+
question.length >= 20 && question.length <= 500 ? '' : 'Clarification question must be 20-500 characters.',
|
|
1717
|
+
questionMarkCount === 1 && normalized.oneQuestionOnly ? '' : 'Clarification contract must contain exactly one customer question.',
|
|
1718
|
+
normalized.customerFacingDraftAllowed === true ? '' : 'Clarification draft must be customer-facing so the operator can review it.',
|
|
1719
|
+
normalized.customerSendAllowed === false ? '' : 'Clarification contract must never allow automatic customer send.',
|
|
1720
|
+
normalized.parksTicketUntilCustomerReply === true ? '' : 'Clarification contract must park the ticket until customer reply.',
|
|
1721
|
+
normalized.nextCommands.includes('park_ticket_until_customer_reply') ? '' : 'Clarification nextCommands must include park_ticket_until_customer_reply.',
|
|
1722
|
+
normalized.forbiddenActions.length ? '' : 'Clarification contract must include forbiddenActions.'
|
|
1723
|
+
].filter(Boolean);
|
|
1724
|
+
normalized.status = blockers.length ? 'blocked' : 'ready';
|
|
1725
|
+
return {
|
|
1726
|
+
valid: blockers.length === 0,
|
|
1727
|
+
status: normalized.status,
|
|
1728
|
+
blockers: blockers,
|
|
1729
|
+
normalized: normalized
|
|
1730
|
+
};
|
|
1731
|
+
}
|
|
1631
1732
|
function buildResolveIOSupportHumanReviewPacket(input) {
|
|
1632
1733
|
return {
|
|
1633
1734
|
reviewType: input.reviewType,
|
|
@@ -1708,7 +1809,33 @@ function decideResolveIOSupportCustomerReplyPolicy(input) {
|
|
|
1708
1809
|
var canAskCustomer = (gate === null || gate === void 0 ? void 0 : gate.issue_case.reproduction_status) === 'blocked'
|
|
1709
1810
|
|| diagnosisValidation.blockers.some(function (blocker) { return /expected_result|observed_result|account_customer_context/.test(blocker); });
|
|
1710
1811
|
if (canAskCustomer) {
|
|
1711
|
-
var
|
|
1812
|
+
var clarificationValidation = validateResolveIOSupportClarificationContract(buildResolveIOSupportClarificationContract(gate, diagnosisValidation.blockers));
|
|
1813
|
+
var clarificationContract = clarificationValidation.normalized;
|
|
1814
|
+
if (!clarificationValidation.valid) {
|
|
1815
|
+
return {
|
|
1816
|
+
action: 'hold_internal',
|
|
1817
|
+
canDraftCustomerReply: false,
|
|
1818
|
+
canSendCustomerReply: false,
|
|
1819
|
+
confidenceLevel: confidenceLevel,
|
|
1820
|
+
safety: 'internal_hold',
|
|
1821
|
+
reason: 'support_reply_clarification_contract_invalid',
|
|
1822
|
+
requiredEvidence: requiredEvidence,
|
|
1823
|
+
clarificationContract: clarificationContract,
|
|
1824
|
+
humanReviewPacket: buildResolveIOSupportHumanReviewPacket({
|
|
1825
|
+
reviewType: 'internal_hold',
|
|
1826
|
+
title: 'Repair Clarification Contract',
|
|
1827
|
+
summary: 'Customer clarification is blocked until the one-question clarification contract validates.',
|
|
1828
|
+
primaryAction: 'repair_support_clarification_contract',
|
|
1829
|
+
safety: 'internal_hold',
|
|
1830
|
+
reason: 'support_reply_clarification_contract_invalid',
|
|
1831
|
+
blockers: clarificationValidation.blockers,
|
|
1832
|
+
requiredEvidence: requiredEvidence,
|
|
1833
|
+
nextCommands: ['repair_clarification_contract', 'rerun_reply_policy'],
|
|
1834
|
+
forbiddenActions: ['Do not send a malformed or multi-question clarification.'],
|
|
1835
|
+
costRisk: 'free_or_deterministic'
|
|
1836
|
+
})
|
|
1837
|
+
};
|
|
1838
|
+
}
|
|
1712
1839
|
return {
|
|
1713
1840
|
action: 'ask_clarification',
|
|
1714
1841
|
canDraftCustomerReply: true,
|
|
@@ -1716,21 +1843,22 @@ function decideResolveIOSupportCustomerReplyPolicy(input) {
|
|
|
1716
1843
|
confidenceLevel: confidenceLevel,
|
|
1717
1844
|
safety: 'needs_clarification',
|
|
1718
1845
|
reason: 'support_reply_waiting_on_customer_reproduction_detail',
|
|
1719
|
-
requiredEvidence: requiredEvidence,
|
|
1720
|
-
clarificationQuestion:
|
|
1846
|
+
requiredEvidence: Array.from(new Set(__spreadArray(__spreadArray([], __read(requiredEvidence), false), __read(clarificationContract.requiredEvidence), false))),
|
|
1847
|
+
clarificationQuestion: clarificationContract.question,
|
|
1848
|
+
clarificationContract: clarificationContract,
|
|
1721
1849
|
humanReviewPacket: buildResolveIOSupportHumanReviewPacket({
|
|
1722
1850
|
reviewType: 'customer_clarification',
|
|
1723
1851
|
title: 'Review Customer Clarification',
|
|
1724
1852
|
summary: 'The runner needs one customer detail before it can reproduce or continue safely.',
|
|
1725
1853
|
primaryAction: 'review_customer_clarification',
|
|
1726
|
-
question:
|
|
1727
|
-
customerFacingDraftAllowed:
|
|
1854
|
+
question: clarificationContract.question,
|
|
1855
|
+
customerFacingDraftAllowed: clarificationContract.customerFacingDraftAllowed,
|
|
1728
1856
|
safety: 'needs_clarification',
|
|
1729
1857
|
reason: 'support_reply_waiting_on_customer_reproduction_detail',
|
|
1730
|
-
blockers:
|
|
1731
|
-
requiredEvidence: requiredEvidence,
|
|
1732
|
-
nextCommands:
|
|
1733
|
-
forbiddenActions:
|
|
1858
|
+
blockers: clarificationContract.sourceBlockers,
|
|
1859
|
+
requiredEvidence: clarificationContract.requiredEvidence,
|
|
1860
|
+
nextCommands: clarificationContract.nextCommands,
|
|
1861
|
+
forbiddenActions: clarificationContract.forbiddenActions,
|
|
1734
1862
|
costRisk: 'release_or_customer_send'
|
|
1735
1863
|
})
|
|
1736
1864
|
};
|