@fun-xyz/fiat-contract 0.11.1 → 0.11.3
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.
- package/README.md +6 -0
- package/dist/{chunk-TXI4KLBL.mjs → chunk-EXLSD4UP.mjs} +11 -4
- package/dist/index.js +15 -6
- package/dist/index.mjs +6 -4
- package/dist/table.js +10 -3
- package/dist/table.mjs +1 -1
- package/dist/types.d.ts +15 -4
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -78,6 +78,12 @@ this package is [ENG-5268](https://linear.app/funxyz/issue/ENG-5268).
|
|
|
78
78
|
13. **Providerless is terminal-routing-only.** `FiatStepResponse.provider` may be absent only for
|
|
79
79
|
`BLOCKED`, including `ALL_PROVIDERS_DECLINED` when routing selected no provider. Every other state
|
|
80
80
|
remains provider-bound and requires `provider`; provider-specific blocked responses may keep it.
|
|
81
|
+
14. **Path commitment is not a quote.** A response may carry `routingSessionRef` while pricing is
|
|
82
|
+
legitimately deferred for provider auth or activation. Transitions echo that opaque reference in
|
|
83
|
+
`params`; clients submit it unchanged. `Quote.quoteRef` remains required whenever a real `Quote`
|
|
84
|
+
is present, and PAY must never be exposed without real current economics.
|
|
85
|
+
15. **KYC may precede pricing.** Provider auth or activation may legitimately defer pricing, so a
|
|
86
|
+
KYC state may omit `quote`. A real `Quote` still requires `quoteRef`, and PAY is never quote-less.
|
|
81
87
|
|
|
82
88
|
## KYC SDK hints, results, and client delivery
|
|
83
89
|
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
// package.json
|
|
2
|
-
var version = "0.11.
|
|
2
|
+
var version = "0.11.3";
|
|
3
3
|
|
|
4
4
|
// src/table.ts
|
|
5
5
|
var TABLE_VERSION = version;
|
|
@@ -102,7 +102,13 @@ var TRANSITION_TABLE = {
|
|
|
102
102
|
docStatus: "SPECIFIED",
|
|
103
103
|
allowedTransitions: [
|
|
104
104
|
{ id: "start", mode: "SUBMIT", endpoint: "POST /fiat/session" },
|
|
105
|
-
{ id: "verify", mode: "SUBMIT", endpoint: "POST /fiat/session/verify" }
|
|
105
|
+
{ id: "verify", mode: "SUBMIT", endpoint: "POST /fiat/session/verify" },
|
|
106
|
+
{
|
|
107
|
+
id: "report_auth_result",
|
|
108
|
+
mode: "CLIENT_SURFACE",
|
|
109
|
+
endpoint: "POST /fiat/session/verify",
|
|
110
|
+
note: "Reports a provider-owned authentication surface result; the backend alone reassesses and selects the next state."
|
|
111
|
+
}
|
|
106
112
|
],
|
|
107
113
|
mayReturn: [
|
|
108
114
|
"SESSION_AUTH",
|
|
@@ -116,7 +122,8 @@ var TRANSITION_TABLE = {
|
|
|
116
122
|
notes: [
|
|
117
123
|
"A bad code re-enters this same state with error {category: USER_ERROR, code: BAD_CODE} \u2014 banner, not a screen change.",
|
|
118
124
|
"No resend affordance is specified in either doc (known gap, FE doc Screen 2).",
|
|
119
|
-
"A provider-owned surface may declare client-executed delivery from allowlisted CURRENT_SESSION_INPUTS only."
|
|
125
|
+
"A provider-owned surface may declare client-executed delivery from allowlisted CURRENT_SESSION_INPUTS only.",
|
|
126
|
+
"A provider-owned authentication surface reports through CLIENT_SURFACE; it is not a user-entered OTP submission."
|
|
120
127
|
]
|
|
121
128
|
},
|
|
122
129
|
"KYC/CAPTURE": {
|
|
@@ -507,4 +514,4 @@ export {
|
|
|
507
514
|
tableEntry,
|
|
508
515
|
isTerminal
|
|
509
516
|
};
|
|
510
|
-
//# sourceMappingURL=chunk-
|
|
517
|
+
//# sourceMappingURL=chunk-EXLSD4UP.mjs.map
|
package/dist/index.js
CHANGED
|
@@ -777,7 +777,7 @@ var SessionAuthStateSchema = $sessionAuthState;
|
|
|
777
777
|
var $kycCaptureState = obj({
|
|
778
778
|
kind: import_zod.z.literal("KYC"),
|
|
779
779
|
phase: import_zod.z.literal("CAPTURE"),
|
|
780
|
-
quote: $quote,
|
|
780
|
+
quote: $quote.optional(),
|
|
781
781
|
surface: $surface,
|
|
782
782
|
error: $failureReason.optional()
|
|
783
783
|
});
|
|
@@ -785,7 +785,7 @@ var KycCaptureStateSchema = $kycCaptureState;
|
|
|
785
785
|
var $kycInputRequiredState = obj({
|
|
786
786
|
kind: import_zod.z.literal("KYC"),
|
|
787
787
|
phase: import_zod.z.literal("INPUT_REQUIRED"),
|
|
788
|
-
quote: $quote,
|
|
788
|
+
quote: $quote.optional(),
|
|
789
789
|
form: $formDescriptor,
|
|
790
790
|
error: $failureReason.optional()
|
|
791
791
|
});
|
|
@@ -793,7 +793,7 @@ var KycInputRequiredStateSchema = $kycInputRequiredState;
|
|
|
793
793
|
var $kycNoActionRequiredState = obj({
|
|
794
794
|
kind: import_zod.z.literal("KYC"),
|
|
795
795
|
phase: import_zod.z.literal("NO_ACTION_REQUIRED"),
|
|
796
|
-
quote: $quote,
|
|
796
|
+
quote: $quote.optional(),
|
|
797
797
|
reason: import_zod.z.enum(["IN_REVIEW", "ON_HOLD", "REJECTED"]),
|
|
798
798
|
retryAfter: import_zod.z.string().optional(),
|
|
799
799
|
failureReason: $failureReason.optional(),
|
|
@@ -874,19 +874,21 @@ var $providerBoundStepResponse = obj({
|
|
|
874
874
|
state: $providerBoundFlowState,
|
|
875
875
|
provider: $provider,
|
|
876
876
|
transitions: import_zod.z.array($transition),
|
|
877
|
+
routingSessionRef: import_zod.z.string().optional(),
|
|
877
878
|
orderId: import_zod.z.string().optional()
|
|
878
879
|
});
|
|
879
880
|
var $blockedStepResponse = obj({
|
|
880
881
|
state: $blockedState,
|
|
881
882
|
provider: $provider.optional(),
|
|
882
883
|
transitions: import_zod.z.array($transition),
|
|
884
|
+
routingSessionRef: import_zod.z.string().optional(),
|
|
883
885
|
orderId: import_zod.z.string().optional()
|
|
884
886
|
});
|
|
885
887
|
var $stepResponse = import_zod.z.union([$providerBoundStepResponse, $blockedStepResponse]);
|
|
886
888
|
var FiatStepResponseSchema = $stepResponse;
|
|
887
889
|
|
|
888
890
|
// package.json
|
|
889
|
-
var version = "0.11.
|
|
891
|
+
var version = "0.11.3";
|
|
890
892
|
|
|
891
893
|
// src/table.ts
|
|
892
894
|
var TABLE_VERSION = version;
|
|
@@ -989,7 +991,13 @@ var TRANSITION_TABLE = {
|
|
|
989
991
|
docStatus: "SPECIFIED",
|
|
990
992
|
allowedTransitions: [
|
|
991
993
|
{ id: "start", mode: "SUBMIT", endpoint: "POST /fiat/session" },
|
|
992
|
-
{ id: "verify", mode: "SUBMIT", endpoint: "POST /fiat/session/verify" }
|
|
994
|
+
{ id: "verify", mode: "SUBMIT", endpoint: "POST /fiat/session/verify" },
|
|
995
|
+
{
|
|
996
|
+
id: "report_auth_result",
|
|
997
|
+
mode: "CLIENT_SURFACE",
|
|
998
|
+
endpoint: "POST /fiat/session/verify",
|
|
999
|
+
note: "Reports a provider-owned authentication surface result; the backend alone reassesses and selects the next state."
|
|
1000
|
+
}
|
|
993
1001
|
],
|
|
994
1002
|
mayReturn: [
|
|
995
1003
|
"SESSION_AUTH",
|
|
@@ -1003,7 +1011,8 @@ var TRANSITION_TABLE = {
|
|
|
1003
1011
|
notes: [
|
|
1004
1012
|
"A bad code re-enters this same state with error {category: USER_ERROR, code: BAD_CODE} \u2014 banner, not a screen change.",
|
|
1005
1013
|
"No resend affordance is specified in either doc (known gap, FE doc Screen 2).",
|
|
1006
|
-
"A provider-owned surface may declare client-executed delivery from allowlisted CURRENT_SESSION_INPUTS only."
|
|
1014
|
+
"A provider-owned surface may declare client-executed delivery from allowlisted CURRENT_SESSION_INPUTS only.",
|
|
1015
|
+
"A provider-owned authentication surface reports through CLIENT_SURFACE; it is not a user-entered OTP submission."
|
|
1007
1016
|
]
|
|
1008
1017
|
},
|
|
1009
1018
|
"KYC/CAPTURE": {
|
package/dist/index.mjs
CHANGED
|
@@ -12,7 +12,7 @@ import {
|
|
|
12
12
|
tableEntry,
|
|
13
13
|
unofferedEndpoints,
|
|
14
14
|
unreachableStates
|
|
15
|
-
} from "./chunk-
|
|
15
|
+
} from "./chunk-EXLSD4UP.mjs";
|
|
16
16
|
|
|
17
17
|
// src/codes.ts
|
|
18
18
|
var COUNTRY_CURRENCY_LIST = [
|
|
@@ -676,7 +676,7 @@ var SessionAuthStateSchema = $sessionAuthState;
|
|
|
676
676
|
var $kycCaptureState = obj({
|
|
677
677
|
kind: z.literal("KYC"),
|
|
678
678
|
phase: z.literal("CAPTURE"),
|
|
679
|
-
quote: $quote,
|
|
679
|
+
quote: $quote.optional(),
|
|
680
680
|
surface: $surface,
|
|
681
681
|
error: $failureReason.optional()
|
|
682
682
|
});
|
|
@@ -684,7 +684,7 @@ var KycCaptureStateSchema = $kycCaptureState;
|
|
|
684
684
|
var $kycInputRequiredState = obj({
|
|
685
685
|
kind: z.literal("KYC"),
|
|
686
686
|
phase: z.literal("INPUT_REQUIRED"),
|
|
687
|
-
quote: $quote,
|
|
687
|
+
quote: $quote.optional(),
|
|
688
688
|
form: $formDescriptor,
|
|
689
689
|
error: $failureReason.optional()
|
|
690
690
|
});
|
|
@@ -692,7 +692,7 @@ var KycInputRequiredStateSchema = $kycInputRequiredState;
|
|
|
692
692
|
var $kycNoActionRequiredState = obj({
|
|
693
693
|
kind: z.literal("KYC"),
|
|
694
694
|
phase: z.literal("NO_ACTION_REQUIRED"),
|
|
695
|
-
quote: $quote,
|
|
695
|
+
quote: $quote.optional(),
|
|
696
696
|
reason: z.enum(["IN_REVIEW", "ON_HOLD", "REJECTED"]),
|
|
697
697
|
retryAfter: z.string().optional(),
|
|
698
698
|
failureReason: $failureReason.optional(),
|
|
@@ -773,12 +773,14 @@ var $providerBoundStepResponse = obj({
|
|
|
773
773
|
state: $providerBoundFlowState,
|
|
774
774
|
provider: $provider,
|
|
775
775
|
transitions: z.array($transition),
|
|
776
|
+
routingSessionRef: z.string().optional(),
|
|
776
777
|
orderId: z.string().optional()
|
|
777
778
|
});
|
|
778
779
|
var $blockedStepResponse = obj({
|
|
779
780
|
state: $blockedState,
|
|
780
781
|
provider: $provider.optional(),
|
|
781
782
|
transitions: z.array($transition),
|
|
783
|
+
routingSessionRef: z.string().optional(),
|
|
782
784
|
orderId: z.string().optional()
|
|
783
785
|
});
|
|
784
786
|
var $stepResponse = z.union([$providerBoundStepResponse, $blockedStepResponse]);
|
package/dist/table.js
CHANGED
|
@@ -36,7 +36,7 @@ __export(table_exports, {
|
|
|
36
36
|
module.exports = __toCommonJS(table_exports);
|
|
37
37
|
|
|
38
38
|
// package.json
|
|
39
|
-
var version = "0.11.
|
|
39
|
+
var version = "0.11.3";
|
|
40
40
|
|
|
41
41
|
// src/table.ts
|
|
42
42
|
var TABLE_VERSION = version;
|
|
@@ -139,7 +139,13 @@ var TRANSITION_TABLE = {
|
|
|
139
139
|
docStatus: "SPECIFIED",
|
|
140
140
|
allowedTransitions: [
|
|
141
141
|
{ id: "start", mode: "SUBMIT", endpoint: "POST /fiat/session" },
|
|
142
|
-
{ id: "verify", mode: "SUBMIT", endpoint: "POST /fiat/session/verify" }
|
|
142
|
+
{ id: "verify", mode: "SUBMIT", endpoint: "POST /fiat/session/verify" },
|
|
143
|
+
{
|
|
144
|
+
id: "report_auth_result",
|
|
145
|
+
mode: "CLIENT_SURFACE",
|
|
146
|
+
endpoint: "POST /fiat/session/verify",
|
|
147
|
+
note: "Reports a provider-owned authentication surface result; the backend alone reassesses and selects the next state."
|
|
148
|
+
}
|
|
143
149
|
],
|
|
144
150
|
mayReturn: [
|
|
145
151
|
"SESSION_AUTH",
|
|
@@ -153,7 +159,8 @@ var TRANSITION_TABLE = {
|
|
|
153
159
|
notes: [
|
|
154
160
|
"A bad code re-enters this same state with error {category: USER_ERROR, code: BAD_CODE} \u2014 banner, not a screen change.",
|
|
155
161
|
"No resend affordance is specified in either doc (known gap, FE doc Screen 2).",
|
|
156
|
-
"A provider-owned surface may declare client-executed delivery from allowlisted CURRENT_SESSION_INPUTS only."
|
|
162
|
+
"A provider-owned surface may declare client-executed delivery from allowlisted CURRENT_SESSION_INPUTS only.",
|
|
163
|
+
"A provider-owned authentication surface reports through CLIENT_SURFACE; it is not a user-entered OTP submission."
|
|
157
164
|
]
|
|
158
165
|
},
|
|
159
166
|
"KYC/CAPTURE": {
|
package/dist/table.mjs
CHANGED
package/dist/types.d.ts
CHANGED
|
@@ -544,23 +544,26 @@ export type FlowState =
|
|
|
544
544
|
surface?: Surface;
|
|
545
545
|
error?: FailureReason;
|
|
546
546
|
}
|
|
547
|
-
/**
|
|
547
|
+
/**
|
|
548
|
+
* Pre-order KYC normally carries the routed quote so the entry screen can keep price visible.
|
|
549
|
+
* `quote` may be absent when provider auth or activation gates pricing.
|
|
550
|
+
*/
|
|
548
551
|
| {
|
|
549
552
|
kind: 'KYC';
|
|
550
553
|
phase: 'CAPTURE';
|
|
551
|
-
quote
|
|
554
|
+
quote?: Quote;
|
|
552
555
|
surface: Surface;
|
|
553
556
|
error?: FailureReason;
|
|
554
557
|
} | {
|
|
555
558
|
kind: 'KYC';
|
|
556
559
|
phase: 'INPUT_REQUIRED';
|
|
557
|
-
quote
|
|
560
|
+
quote?: Quote;
|
|
558
561
|
form: FormDescriptor;
|
|
559
562
|
error?: FailureReason;
|
|
560
563
|
} | {
|
|
561
564
|
kind: 'KYC';
|
|
562
565
|
phase: 'NO_ACTION_REQUIRED';
|
|
563
|
-
quote
|
|
566
|
+
quote?: Quote;
|
|
564
567
|
/**
|
|
565
568
|
* Note the deliberate name collision (Charles's nit, review 2026-08-14): `ON_HOLD` appears
|
|
566
569
|
* here as a KYC reason *and* in `OrderStatus`. They are different things and both names come
|
|
@@ -641,6 +644,14 @@ export type BlockedReason = 'REGION_UNSUPPORTED' | 'ASSET_UNSUPPORTED' | 'ALL_PR
|
|
|
641
644
|
*/
|
|
642
645
|
type FiatStepResponseBase = {
|
|
643
646
|
transitions: Transition[];
|
|
647
|
+
/**
|
|
648
|
+
* Stable identity for a routing continuation before provider pricing is observable.
|
|
649
|
+
*
|
|
650
|
+
* A quote-less CONTINUE/PENDING response carries this instead of fabricating a `Quote` or
|
|
651
|
+
* `quoteRef`. It may remain present after a real quote is promoted so the backend can preserve
|
|
652
|
+
* the committed provider path independently from the quote binding.
|
|
653
|
+
*/
|
|
654
|
+
routingSessionRef?: string;
|
|
644
655
|
/** TODO(open-decision): `orderId` placement — see `PAYMENT{INSTRUCT}.orderId` above. */
|
|
645
656
|
orderId?: string;
|
|
646
657
|
};
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fun-xyz/fiat-contract",
|
|
3
|
-
"version": "0.11.
|
|
3
|
+
"version": "0.11.3",
|
|
4
4
|
"description": "Published conformance contract for Fun's headless fiat onramp: FlowState/Transition types, zod schemas, the transition table as data, recorded fixtures, assertion helpers.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"repository": {
|