@nokinc-flur/sdk 1.0.5 → 1.0.6

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/dist/index.cjs CHANGED
@@ -26,11 +26,24 @@ __export(index_exports, {
26
26
  AccountMembershipSchema: () => AccountMembershipSchema,
27
27
  AccountSchema: () => AccountSchema,
28
28
  ApiCredentialPublicSchema: () => ApiCredentialPublicSchema,
29
+ COLLECTION_INTENT_STATUSES: () => COLLECTION_INTENT_STATUSES,
30
+ COLLECTION_PAYMENT_STATUSES: () => COLLECTION_PAYMENT_STATUSES,
31
+ CUSTODIAL_MODES: () => CUSTODIAL_MODES,
32
+ CollectionIntentSchema: () => CollectionIntentSchema,
33
+ CollectionPaymentResultSchema: () => CollectionPaymentResultSchema,
34
+ CollectionPaymentSchema: () => CollectionPaymentSchema,
35
+ CollectionReportSummarySchema: () => CollectionReportSummarySchema,
36
+ CollectionStatementSchema: () => CollectionStatementSchema,
29
37
  ConsumerOACRecordSchema: () => OACRecordSchema,
30
38
  ConsumerOACSchema: () => ConsumerOACSchema,
31
39
  ConsumerPaymentClaimSchema: () => ConsumerPaymentClaimSchema,
32
40
  ConsumerSettleResultSchema: () => ConsumerSettleResultSchema,
33
41
  ConsumerSettlementSchema: () => ConsumerSettlementSchema,
42
+ CreateCollectionIntentInputSchema: () => CreateCollectionIntentInputSchema,
43
+ CreatePayoutDestinationInputSchema: () => CreatePayoutDestinationInputSchema,
44
+ CreatePayoutInputSchema: () => CreatePayoutInputSchema,
45
+ CreateWithdrawalInputSchema: () => CreateWithdrawalInputSchema,
46
+ CreateWithdrawalResultSchema: () => CreateWithdrawalResultSchema,
34
47
  DeviceKeyRecordSchema: () => DeviceKeyRecordSchema,
35
48
  DisableOfflineInputSchema: () => DisableOfflineInputSchema,
36
49
  DisableOfflineResultSchema: () => DisableOfflineResultSchema,
@@ -43,8 +56,14 @@ __export(index_exports, {
43
56
  FlurError: () => FlurError,
44
57
  FlurExpiredError: () => FlurExpiredError,
45
58
  FlurReplayError: () => FlurReplayError,
59
+ IngestFundingResultSchema: () => IngestFundingResultSchema,
46
60
  IssueOACInputSchema: () => IssueOACInputSchema,
61
+ ListPayoutDestinationsResultSchema: () => ListPayoutDestinationsResultSchema,
47
62
  MEMBERSHIP_ROLES: () => MEMBERSHIP_ROLES,
63
+ MERCHANT_PAYOUT_STATUSES: () => MERCHANT_PAYOUT_STATUSES,
64
+ MERCHANT_PROFILE_STATUSES: () => MERCHANT_PROFILE_STATUSES,
65
+ MerchantPayoutSchema: () => MerchantPayoutSchema,
66
+ MerchantProfileSchema: () => MerchantProfileSchema,
48
67
  MintedApiCredentialSchema: () => MintedApiCredentialSchema,
49
68
  NGN_CURRENCY_CODE: () => NGN_CURRENCY_CODE,
50
69
  NG_COUNTRY_CODE: () => NG_COUNTRY_CODE,
@@ -59,25 +78,46 @@ __export(index_exports, {
59
78
  OfflineStateResultSchema: () => OfflineStateResultSchema,
60
79
  OfflineStatusResultSchema: () => OfflineStatusResultSchema,
61
80
  OfflineTokenSchema: () => OfflineTokenSchema,
81
+ PARTNER_FUNDING_DIRECTIONS: () => PARTNER_FUNDING_DIRECTIONS,
82
+ PARTNER_FUNDING_STATUSES: () => PARTNER_FUNDING_STATUSES,
83
+ PARTNER_KINDS: () => PARTNER_KINDS,
84
+ PARTNER_PROFILE_STATUSES: () => PARTNER_PROFILE_STATUSES,
62
85
  PARTNER_SCOPES: () => PARTNER_SCOPES,
63
86
  PASS_KINDS: () => PASS_KINDS,
64
87
  PASS_STATES: () => PASS_STATES,
65
88
  PAYLOAD_FORMAT_INDICATOR_VALUE: () => PAYLOAD_FORMAT_INDICATOR_VALUE,
89
+ PAYOUT_DESTINATION_STATUSES: () => PAYOUT_DESTINATION_STATUSES,
66
90
  POINT_OF_INITIATION: () => POINT_OF_INITIATION,
91
+ PartnerFundingEventInputSchema: () => PartnerFundingEventInputSchema,
92
+ PartnerFundingSchema: () => PartnerFundingSchema,
93
+ PartnerProfileSchema: () => PartnerProfileSchema,
67
94
  PassMetadataSchema: () => PassMetadataSchema,
68
95
  PassSchema: () => PassSchema,
96
+ PayCollectionInputSchema: () => PayCollectionInputSchema,
69
97
  PaymentClaimSchema: () => PaymentClaimSchema,
98
+ PayoutDestinationSchema: () => PayoutDestinationSchema,
99
+ PayoutEventInputSchema: () => PayoutEventInputSchema,
100
+ ProviderEventInputSchema: () => ProviderEventInputSchema,
101
+ ProviderEventRecordSchema: () => ProviderEventRecordSchema,
102
+ PublicCollectionIntentSchema: () => PublicCollectionIntentSchema,
70
103
  RECEIPT_CHANNELS: () => RECEIPT_CHANNELS,
71
104
  RECEIPT_KINDS: () => RECEIPT_KINDS,
72
105
  REPLAY_WINDOW_MS: () => REPLAY_WINDOW_MS,
73
106
  ReceiptPayloadSchema: () => ReceiptPayloadSchema,
74
107
  ReceiptSchema: () => ReceiptSchema,
108
+ ReconciliationReportSchema: () => ReconciliationReportSchema,
109
+ RecordPayoutEventResultSchema: () => RecordPayoutEventResultSchema,
75
110
  RedemptionSchema: () => RedemptionSchema,
76
111
  RegisterDeviceKeyInputSchema: () => RegisterDeviceKeyInputSchema,
77
112
  RevokeDeviceKeyInputSchema: () => RevokeDeviceKeyInputSchema,
113
+ SETTLEMENT_SCHEDULES: () => SETTLEMENT_SCHEDULES,
78
114
  SettleResponseSchema: () => SettleResponseSchema,
79
115
  SettlementSchema: () => SettlementSchema,
80
116
  SignedConsumerOACSchema: () => SignedConsumerOACSchema,
117
+ UpsertMerchantProfileInputSchema: () => UpsertMerchantProfileInputSchema,
118
+ UpsertPartnerProfileInputSchema: () => UpsertPartnerProfileInputSchema,
119
+ WITHDRAWAL_STATES: () => WITHDRAWAL_STATES,
120
+ WithdrawalSchema: () => WithdrawalSchema,
81
121
  bodySha256Hex: () => bodySha256Hex,
82
122
  buildAuthorization: () => buildAuthorization,
83
123
  buildOAC: () => buildOAC,
@@ -94,10 +134,16 @@ __export(index_exports, {
94
134
  crc16ccittHex: () => crc16ccittHex,
95
135
  createAccountsClient: () => createAccountsClient,
96
136
  createApiCredentialsAdminClient: () => createApiCredentialsAdminClient,
137
+ createCollectionsClient: () => createCollectionsClient,
138
+ createConsumerCollectionsClient: () => createConsumerCollectionsClient,
139
+ createConsumerWithdrawalsClient: () => createConsumerWithdrawalsClient,
97
140
  createFlurPartnerClient: () => createFlurPartnerClient,
98
141
  createHmacFetch: () => createHmacFetch,
99
142
  createMeOfflineClient: () => createMeOfflineClient,
100
143
  createOfflineSettlementsClient: () => createOfflineSettlementsClient,
144
+ createPartnerCollectionsClient: () => createPartnerCollectionsClient,
145
+ createPartnerFundingClient: () => createPartnerFundingClient,
146
+ createPartnerProfileAdminClient: () => createPartnerProfileAdminClient,
101
147
  createPassesClient: () => createPassesClient,
102
148
  createReceiptsClient: () => createReceiptsClient,
103
149
  decodeAuthorizationQR: () => decodeAuthorizationQR,
@@ -145,7 +191,7 @@ __export(index_exports, {
145
191
  module.exports = __toCommonJS(index_exports);
146
192
 
147
193
  // src/client.ts
148
- var import_zod3 = require("zod");
194
+ var import_zod4 = require("zod");
149
195
 
150
196
  // src/contracts.ts
151
197
  var import_zod = require("zod");
@@ -533,6 +579,341 @@ function moneyMinorToNumber(amountMinor) {
533
579
  return asNumber;
534
580
  }
535
581
 
582
+ // src/collections/client.ts
583
+ var import_zod3 = require("zod");
584
+ var MERCHANT_PROFILE_STATUSES = [
585
+ "pending",
586
+ "active",
587
+ "suspended",
588
+ "closed"
589
+ ];
590
+ var SETTLEMENT_SCHEDULES = ["manual", "daily", "t1"];
591
+ var COLLECTION_INTENT_STATUSES = [
592
+ "created",
593
+ "pending",
594
+ "paid",
595
+ "expired",
596
+ "cancelled",
597
+ "failed",
598
+ "reversed"
599
+ ];
600
+ var COLLECTION_PAYMENT_STATUSES = [
601
+ "pending",
602
+ "paid",
603
+ "failed",
604
+ "reversed"
605
+ ];
606
+ var MERCHANT_PAYOUT_STATUSES = [
607
+ "requested",
608
+ "processing",
609
+ "paid",
610
+ "failed",
611
+ "cancelled"
612
+ ];
613
+ var MoneyKoboSchema = import_zod3.z.number().int().positive().max(Number.MAX_SAFE_INTEGER);
614
+ var MetadataSchema = import_zod3.z.record(
615
+ import_zod3.z.union([import_zod3.z.string(), import_zod3.z.number(), import_zod3.z.boolean(), import_zod3.z.null()])
616
+ );
617
+ var CurrencySchema2 = import_zod3.z.string().trim().length(3).transform((value) => value.toUpperCase());
618
+ var ReferenceSchema = import_zod3.z.string().trim().min(6).max(128).regex(/^[A-Za-z0-9._:-]+$/);
619
+ var MerchantProfileSchema = import_zod3.z.object({
620
+ accountId: import_zod3.z.string().uuid(),
621
+ legalName: import_zod3.z.string(),
622
+ tradingName: import_zod3.z.string(),
623
+ merchantCategoryCode: import_zod3.z.string().regex(/^\d{4}$/),
624
+ nqrMerchantId: import_zod3.z.string(),
625
+ settlementBankCode: import_zod3.z.string(),
626
+ settlementAccountNumber: import_zod3.z.string(),
627
+ settlementAccountName: import_zod3.z.string(),
628
+ settlementSchedule: import_zod3.z.enum(SETTLEMENT_SCHEDULES),
629
+ status: import_zod3.z.enum(MERCHANT_PROFILE_STATUSES),
630
+ offlineEnabled: import_zod3.z.boolean(),
631
+ perTxLimitKobo: MoneyKoboSchema,
632
+ dailyLimitKobo: MoneyKoboSchema,
633
+ metadata: MetadataSchema,
634
+ createdAtMs: import_zod3.z.number().int().nonnegative(),
635
+ updatedAtMs: import_zod3.z.number().int().nonnegative()
636
+ });
637
+ var UpsertMerchantProfileInputSchema = import_zod3.z.object({
638
+ legalName: import_zod3.z.string().trim().min(1).max(200),
639
+ tradingName: import_zod3.z.string().trim().min(1).max(25),
640
+ merchantCategoryCode: import_zod3.z.string().trim().regex(/^\d{4}$/),
641
+ nqrMerchantId: import_zod3.z.string().trim().min(3).max(64),
642
+ settlementBankCode: import_zod3.z.string().trim().min(2).max(16),
643
+ settlementAccountNumber: import_zod3.z.string().trim().min(5).max(32),
644
+ settlementAccountName: import_zod3.z.string().trim().min(1).max(200),
645
+ settlementSchedule: import_zod3.z.enum(SETTLEMENT_SCHEDULES).optional(),
646
+ status: import_zod3.z.enum(MERCHANT_PROFILE_STATUSES).optional(),
647
+ offlineEnabled: import_zod3.z.boolean().optional(),
648
+ perTxLimitKobo: MoneyKoboSchema.optional(),
649
+ dailyLimitKobo: MoneyKoboSchema.optional(),
650
+ metadata: MetadataSchema.optional()
651
+ });
652
+ var CollectionIntentSchema = import_zod3.z.object({
653
+ intentId: import_zod3.z.string().uuid(),
654
+ accountId: import_zod3.z.string().uuid(),
655
+ terminalId: import_zod3.z.string().uuid().nullable(),
656
+ reference: import_zod3.z.string(),
657
+ amountKobo: import_zod3.z.number().int().positive().nullable(),
658
+ currency: import_zod3.z.string().length(3),
659
+ status: import_zod3.z.enum(COLLECTION_INTENT_STATUSES),
660
+ description: import_zod3.z.string().nullable(),
661
+ nqrPayload: import_zod3.z.string(),
662
+ provider: import_zod3.z.string(),
663
+ providerReference: import_zod3.z.string().nullable(),
664
+ metadata: MetadataSchema,
665
+ expiresAtMs: import_zod3.z.number().int().nonnegative().nullable(),
666
+ paidAtMs: import_zod3.z.number().int().nonnegative().nullable(),
667
+ createdAtMs: import_zod3.z.number().int().nonnegative(),
668
+ updatedAtMs: import_zod3.z.number().int().nonnegative()
669
+ });
670
+ var CreateCollectionIntentInputSchema = import_zod3.z.object({
671
+ reference: ReferenceSchema.optional(),
672
+ amountKobo: MoneyKoboSchema.optional(),
673
+ currency: CurrencySchema2.optional(),
674
+ terminalId: import_zod3.z.string().uuid().optional(),
675
+ terminalLabel: import_zod3.z.string().trim().min(1).max(25).optional(),
676
+ merchantCity: import_zod3.z.string().trim().min(1).max(15).optional(),
677
+ description: import_zod3.z.string().trim().min(1).max(280).optional(),
678
+ expiresAtMs: import_zod3.z.number().int().positive().optional(),
679
+ provider: import_zod3.z.string().trim().min(1).max(40).optional(),
680
+ metadata: MetadataSchema.optional()
681
+ });
682
+ var PublicCollectionIntentSchema = import_zod3.z.object({
683
+ intentId: import_zod3.z.string().uuid(),
684
+ reference: import_zod3.z.string(),
685
+ amountKobo: import_zod3.z.number().int().positive().nullable(),
686
+ currency: import_zod3.z.string().length(3),
687
+ status: import_zod3.z.enum(COLLECTION_INTENT_STATUSES),
688
+ merchantAccountId: import_zod3.z.string().uuid(),
689
+ merchantName: import_zod3.z.string(),
690
+ merchantCategoryCode: import_zod3.z.string(),
691
+ description: import_zod3.z.string().nullable(),
692
+ expiresAtMs: import_zod3.z.number().int().nonnegative().nullable()
693
+ });
694
+ var PayCollectionInputSchema = import_zod3.z.object({
695
+ reference: ReferenceSchema,
696
+ amountKobo: MoneyKoboSchema.optional(),
697
+ currency: CurrencySchema2.optional(),
698
+ idempotencyKey: import_zod3.z.string().trim().min(8).max(160).optional()
699
+ });
700
+ var CollectionPaymentSchema = import_zod3.z.object({
701
+ paymentId: import_zod3.z.string().uuid(),
702
+ intentId: import_zod3.z.string().uuid(),
703
+ accountId: import_zod3.z.string().uuid(),
704
+ payerUserId: import_zod3.z.string().uuid().nullable(),
705
+ merchantOwnerUserId: import_zod3.z.string().uuid(),
706
+ amountKobo: MoneyKoboSchema,
707
+ currency: import_zod3.z.string().length(3),
708
+ status: import_zod3.z.enum(COLLECTION_PAYMENT_STATUSES),
709
+ provider: import_zod3.z.string(),
710
+ providerReference: import_zod3.z.string().nullable(),
711
+ idempotencyKey: import_zod3.z.string().nullable(),
712
+ ledgerRef: import_zod3.z.string(),
713
+ failureCode: import_zod3.z.string().nullable(),
714
+ failureMessage: import_zod3.z.string().nullable(),
715
+ paidAtMs: import_zod3.z.number().int().nonnegative().nullable(),
716
+ createdAtMs: import_zod3.z.number().int().nonnegative(),
717
+ updatedAtMs: import_zod3.z.number().int().nonnegative()
718
+ });
719
+ var CollectionPaymentResultSchema = import_zod3.z.object({
720
+ payment: CollectionPaymentSchema,
721
+ intent: CollectionIntentSchema,
722
+ receipt: import_zod3.z.unknown().optional(),
723
+ replayed: import_zod3.z.boolean()
724
+ });
725
+ var CollectionReportSummarySchema = import_zod3.z.object({
726
+ accountId: import_zod3.z.string().uuid(),
727
+ fromMs: import_zod3.z.number().int().nonnegative(),
728
+ toMs: import_zod3.z.number().int().nonnegative(),
729
+ currency: import_zod3.z.string().length(3),
730
+ paidCount: import_zod3.z.number().int().nonnegative(),
731
+ paidAmountKobo: import_zod3.z.number().int().nonnegative(),
732
+ pendingCount: import_zod3.z.number().int().nonnegative(),
733
+ failedCount: import_zod3.z.number().int().nonnegative(),
734
+ reversedCount: import_zod3.z.number().int().nonnegative(),
735
+ availableBalanceKobo: import_zod3.z.number().int().nonnegative()
736
+ });
737
+ var CollectionStatementSchema = import_zod3.z.object({
738
+ accountId: import_zod3.z.string().uuid(),
739
+ year: import_zod3.z.number().int(),
740
+ month: import_zod3.z.number().int().min(1).max(12),
741
+ currency: import_zod3.z.string().length(3),
742
+ totalPaidKobo: import_zod3.z.number().int().nonnegative(),
743
+ items: import_zod3.z.array(CollectionPaymentSchema)
744
+ });
745
+ var CreatePayoutInputSchema = import_zod3.z.object({
746
+ amountKobo: MoneyKoboSchema,
747
+ currency: CurrencySchema2.optional(),
748
+ idempotencyKey: import_zod3.z.string().trim().min(8).max(160)
749
+ });
750
+ var MerchantPayoutSchema = import_zod3.z.object({
751
+ payoutId: import_zod3.z.string().uuid(),
752
+ accountId: import_zod3.z.string().uuid(),
753
+ amountKobo: MoneyKoboSchema,
754
+ currency: import_zod3.z.string().length(3),
755
+ status: import_zod3.z.enum(MERCHANT_PAYOUT_STATUSES),
756
+ idempotencyKey: import_zod3.z.string().nullable(),
757
+ ledgerRef: import_zod3.z.string(),
758
+ providerReference: import_zod3.z.string().nullable(),
759
+ requestedByUserId: import_zod3.z.string().uuid().nullable(),
760
+ failureCode: import_zod3.z.string().nullable(),
761
+ failureMessage: import_zod3.z.string().nullable(),
762
+ createdAtMs: import_zod3.z.number().int().nonnegative(),
763
+ updatedAtMs: import_zod3.z.number().int().nonnegative()
764
+ });
765
+ var ProviderEventInputSchema = import_zod3.z.object({
766
+ provider: import_zod3.z.string().trim().min(1).max(80),
767
+ eventId: import_zod3.z.string().trim().min(1).max(160),
768
+ eventType: import_zod3.z.string().trim().min(1).max(120),
769
+ payload: import_zod3.z.record(import_zod3.z.unknown()).optional()
770
+ });
771
+ var ProviderEventRecordSchema = import_zod3.z.object({
772
+ id: import_zod3.z.string().uuid(),
773
+ provider: import_zod3.z.string(),
774
+ eventId: import_zod3.z.string(),
775
+ eventType: import_zod3.z.string(),
776
+ signatureVerified: import_zod3.z.boolean(),
777
+ receivedAtMs: import_zod3.z.number().int().nonnegative(),
778
+ processedAtMs: import_zod3.z.number().int().nonnegative().nullable()
779
+ });
780
+ function createCollectionsClient(opts) {
781
+ const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
782
+ if (!fetchImpl) {
783
+ throw new Error(
784
+ "createCollectionsClient: no fetch implementation available"
785
+ );
786
+ }
787
+ const baseUrl = opts.baseUrl.replace(/\/$/, "");
788
+ async function call(method, path, body, parser) {
789
+ const init2 = {
790
+ method,
791
+ headers: { accept: "application/json" }
792
+ };
793
+ if (body !== void 0) {
794
+ init2.body = JSON.stringify(body);
795
+ init2.headers = { ...init2.headers, "content-type": "application/json" };
796
+ }
797
+ const resp = await fetchImpl(`${baseUrl}${path}`, init2);
798
+ const text = await resp.text();
799
+ let raw;
800
+ if (text) {
801
+ try {
802
+ raw = JSON.parse(text);
803
+ } catch {
804
+ raw = text;
805
+ }
806
+ }
807
+ if (!resp.ok) {
808
+ const code = raw && typeof raw === "object" && "code" in raw && typeof raw.code === "string" ? raw.code : `http_${resp.status}`;
809
+ const message = raw && typeof raw === "object" && "message" in raw && typeof raw.message === "string" ? raw.message : `request failed with status ${resp.status}`;
810
+ throw new FlurApiError(resp.status, code, message, raw);
811
+ }
812
+ return parser(raw);
813
+ }
814
+ return {
815
+ upsertMerchantProfile: (accountId, input) => call(
816
+ "PUT",
817
+ `/v1/accounts/${encodeURIComponent(accountId)}/merchant-profile`,
818
+ UpsertMerchantProfileInputSchema.parse(input),
819
+ (raw) => MerchantProfileSchema.parse(raw)
820
+ ),
821
+ getMerchantProfile: (accountId) => call(
822
+ "GET",
823
+ `/v1/accounts/${encodeURIComponent(accountId)}/merchant-profile`,
824
+ void 0,
825
+ (raw) => MerchantProfileSchema.parse(raw)
826
+ ),
827
+ createIntent: (input) => call(
828
+ "POST",
829
+ "/v1/collections/intents",
830
+ CreateCollectionIntentInputSchema.parse(input),
831
+ (raw) => CollectionIntentSchema.parse(raw)
832
+ ),
833
+ getIntent: (intentId) => call(
834
+ "GET",
835
+ `/v1/collections/intents/${encodeURIComponent(intentId)}`,
836
+ void 0,
837
+ (raw) => CollectionIntentSchema.parse(raw)
838
+ ),
839
+ resolveIntent: (reference) => call(
840
+ "GET",
841
+ `/v1/collections/resolve/${encodeURIComponent(reference)}`,
842
+ void 0,
843
+ (raw) => PublicCollectionIntentSchema.parse(raw)
844
+ ),
845
+ pay: (input) => call(
846
+ "POST",
847
+ "/v1/collections/pay",
848
+ PayCollectionInputSchema.parse(input),
849
+ (raw) => CollectionPaymentResultSchema.parse(raw)
850
+ ),
851
+ reportSummary: (input) => {
852
+ const qs = new URLSearchParams({
853
+ fromMs: String(input.fromMs),
854
+ toMs: String(input.toMs)
855
+ });
856
+ if (input.currency) qs.set("currency", input.currency);
857
+ return call(
858
+ "GET",
859
+ `/v1/collections/reports/summary?${qs.toString()}`,
860
+ void 0,
861
+ (raw) => CollectionReportSummarySchema.parse(raw)
862
+ );
863
+ },
864
+ monthlyStatement: (input) => {
865
+ const qs = new URLSearchParams({
866
+ year: String(input.year),
867
+ month: String(input.month)
868
+ });
869
+ if (input.currency) qs.set("currency", input.currency);
870
+ return call(
871
+ "GET",
872
+ `/v1/collections/statements/monthly?${qs.toString()}`,
873
+ void 0,
874
+ (raw) => CollectionStatementSchema.parse(raw)
875
+ );
876
+ },
877
+ createPayout: (input) => call(
878
+ "POST",
879
+ "/v1/collections/payouts",
880
+ CreatePayoutInputSchema.parse(input),
881
+ (raw) => MerchantPayoutSchema.parse(raw)
882
+ ),
883
+ getPayout: (payoutId) => call(
884
+ "GET",
885
+ `/v1/collections/payouts/${encodeURIComponent(payoutId)}`,
886
+ void 0,
887
+ (raw) => MerchantPayoutSchema.parse(raw)
888
+ ),
889
+ recordProviderEvent: (input) => call(
890
+ "POST",
891
+ "/v1/collections/provider-events",
892
+ ProviderEventInputSchema.parse(input),
893
+ (raw) => ProviderEventRecordSchema.parse(raw)
894
+ )
895
+ };
896
+ }
897
+ function createPartnerCollectionsClient(opts) {
898
+ const client = createCollectionsClient(opts);
899
+ return {
900
+ createIntent: client.createIntent,
901
+ getIntent: client.getIntent,
902
+ reportSummary: client.reportSummary,
903
+ monthlyStatement: client.monthlyStatement,
904
+ createPayout: client.createPayout,
905
+ getPayout: client.getPayout,
906
+ recordProviderEvent: client.recordProviderEvent
907
+ };
908
+ }
909
+ function createConsumerCollectionsClient(opts) {
910
+ const client = createCollectionsClient(opts);
911
+ return {
912
+ resolveIntent: client.resolveIntent,
913
+ pay: client.pay
914
+ };
915
+ }
916
+
536
917
  // src/client.ts
537
918
  var FlurClient = class {
538
919
  baseUrl;
@@ -781,6 +1162,36 @@ var FlurClient = class {
781
1162
  }
782
1163
  );
783
1164
  }
1165
+ async resolveCollection(reference, options) {
1166
+ return this.requestJson(
1167
+ `/v1/collections/resolve/${encodeURIComponent(reference)}`,
1168
+ {
1169
+ method: "GET",
1170
+ headers: {
1171
+ authorization: `Bearer ${options.accessToken}`
1172
+ }
1173
+ },
1174
+ void 0,
1175
+ PublicCollectionIntentSchema
1176
+ );
1177
+ }
1178
+ async payCollection(input, options) {
1179
+ const idempotencyKey = input.idempotencyKey ?? options.idempotencyKey ?? getSecureRandomUuid();
1180
+ return this.requestJson(
1181
+ "/v1/collections/pay",
1182
+ {
1183
+ method: "POST",
1184
+ headers: {
1185
+ "content-type": "application/json",
1186
+ authorization: `Bearer ${options.accessToken}`,
1187
+ "x-idempotency-key": idempotencyKey
1188
+ }
1189
+ },
1190
+ PayCollectionInputSchema,
1191
+ CollectionPaymentResultSchema,
1192
+ { ...input, idempotencyKey }
1193
+ );
1194
+ }
784
1195
  async accountSummary(options) {
785
1196
  return this.requestJson(
786
1197
  "/api/v1/account/summary",
@@ -879,7 +1290,7 @@ var FlurClient = class {
879
1290
  try {
880
1291
  body = requestSchema ? JSON.stringify(requestSchema.parse(input)) : init2.body;
881
1292
  } catch (err) {
882
- if (err instanceof import_zod3.z.ZodError) {
1293
+ if (err instanceof import_zod4.z.ZodError) {
883
1294
  throw new FlurError("Invalid request payload", "INVALID_REQUEST", {
884
1295
  details: err.flatten()
885
1296
  });
@@ -907,7 +1318,7 @@ var FlurClient = class {
907
1318
  try {
908
1319
  return responseSchema.parse(payload);
909
1320
  } catch (err) {
910
- if (err instanceof import_zod3.z.ZodError) {
1321
+ if (err instanceof import_zod4.z.ZodError) {
911
1322
  throw new FlurError(
912
1323
  "SDK contract validation failed",
913
1324
  "INVALID_REQUEST",
@@ -1365,24 +1776,24 @@ function verifyCanonical(value, signature, publicKey) {
1365
1776
  }
1366
1777
 
1367
1778
  // src/offline/oac.ts
1368
- var import_zod4 = require("zod");
1779
+ var import_zod5 = require("zod");
1369
1780
  var OAC_DEFAULT_PER_TX_KOBO = 5e5;
1370
1781
  var OAC_DEFAULT_CUMULATIVE_KOBO = 2e6;
1371
1782
  var OAC_DEFAULT_VALIDITY_MS = 24 * 60 * 60 * 1e3;
1372
- var HexString = (length) => import_zod4.z.string().regex(
1783
+ var HexString = (length) => import_zod5.z.string().regex(
1373
1784
  new RegExp(`^[0-9a-fA-F]{${length * 2}}$`),
1374
1785
  `expected ${length}-byte hex string`
1375
1786
  );
1376
- var OACSchema = import_zod4.z.object({
1377
- userId: import_zod4.z.string().min(1),
1378
- deviceId: import_zod4.z.string().min(1),
1787
+ var OACSchema = import_zod5.z.object({
1788
+ userId: import_zod5.z.string().min(1),
1789
+ deviceId: import_zod5.z.string().min(1),
1379
1790
  devicePublicKey: HexString(32),
1380
- perTxCapKobo: import_zod4.z.number().int().nonnegative(),
1381
- cumulativeCapKobo: import_zod4.z.number().int().nonnegative(),
1382
- validFromMs: import_zod4.z.number().int().nonnegative(),
1383
- validUntilMs: import_zod4.z.number().int().positive(),
1384
- counterSeed: import_zod4.z.number().int().nonnegative(),
1385
- nonce: import_zod4.z.string().min(1),
1791
+ perTxCapKobo: import_zod5.z.number().int().nonnegative(),
1792
+ cumulativeCapKobo: import_zod5.z.number().int().nonnegative(),
1793
+ validFromMs: import_zod5.z.number().int().nonnegative(),
1794
+ validUntilMs: import_zod5.z.number().int().positive(),
1795
+ counterSeed: import_zod5.z.number().int().nonnegative(),
1796
+ nonce: import_zod5.z.string().min(1),
1386
1797
  issuerSig: HexString(64)
1387
1798
  }).refine((v) => v.validUntilMs > v.validFromMs, {
1388
1799
  message: "validUntilMs must be greater than validFromMs"
@@ -1489,19 +1900,19 @@ function decodeBase45(s) {
1489
1900
  }
1490
1901
 
1491
1902
  // src/offline/messages.ts
1492
- var import_zod5 = require("zod");
1493
- var HexSig = import_zod5.z.string().regex(/^[0-9a-fA-F]{128}$/, "expected 64-byte hex signature");
1494
- var OfflinePaymentRequestSchema = import_zod5.z.object({
1495
- reference: import_zod5.z.string().min(1),
1496
- amountKobo: import_zod5.z.number().int().positive(),
1903
+ var import_zod6 = require("zod");
1904
+ var HexSig = import_zod6.z.string().regex(/^[0-9a-fA-F]{128}$/, "expected 64-byte hex signature");
1905
+ var OfflinePaymentRequestSchema = import_zod6.z.object({
1906
+ reference: import_zod6.z.string().min(1),
1907
+ amountKobo: import_zod6.z.number().int().positive(),
1497
1908
  merchantOAC: OACSchema,
1498
- expiresAtMs: import_zod5.z.number().int().positive(),
1909
+ expiresAtMs: import_zod6.z.number().int().positive(),
1499
1910
  merchantSig: HexSig
1500
1911
  });
1501
- var OfflinePaymentAuthorizationSchema = import_zod5.z.object({
1912
+ var OfflinePaymentAuthorizationSchema = import_zod6.z.object({
1502
1913
  request: OfflinePaymentRequestSchema,
1503
1914
  payerOAC: OACSchema,
1504
- payerCounter: import_zod5.z.number().int().positive(),
1915
+ payerCounter: import_zod6.z.number().int().positive(),
1505
1916
  payerSig: HexSig
1506
1917
  });
1507
1918
  function buildPaymentRequest(input) {
@@ -1610,56 +2021,56 @@ function decodeAuthorizationQR(s) {
1610
2021
  }
1611
2022
 
1612
2023
  // src/offline/settlements.ts
1613
- var import_zod6 = require("zod");
2024
+ var import_zod7 = require("zod");
1614
2025
  var import_sha256 = require("@noble/hashes/sha256");
1615
2026
  var import_utils = require("@noble/hashes/utils");
1616
- var OfflineTokenSchema = import_zod6.z.object({
1617
- tokenId: import_zod6.z.string().uuid(),
1618
- tokenSerial: import_zod6.z.string(),
1619
- issuerAccountId: import_zod6.z.string().uuid(),
1620
- payerUserId: import_zod6.z.string().uuid(),
1621
- maxAmountKobo: import_zod6.z.number().int().positive(),
1622
- currency: import_zod6.z.string().length(3),
1623
- issuedAtMs: import_zod6.z.number().int().nonnegative(),
1624
- expiresAtMs: import_zod6.z.number().int().nonnegative(),
1625
- issuerSig: import_zod6.z.string()
1626
- });
1627
- var PaymentClaimSchema = import_zod6.z.object({
1628
- encounterId: import_zod6.z.string().regex(/^[0-9a-f]{64}$/i).optional(),
1629
- tokenSerial: import_zod6.z.string(),
1630
- payerUserId: import_zod6.z.string().uuid(),
1631
- payeeUserId: import_zod6.z.string().uuid(),
1632
- payerNonce: import_zod6.z.string(),
1633
- payeeNonce: import_zod6.z.string(),
1634
- amountKobo: import_zod6.z.number().int().positive(),
1635
- currency: import_zod6.z.string().length(3).default("NGN"),
1636
- occurredAtMs: import_zod6.z.number().int().nonnegative(),
1637
- completedAtMs: import_zod6.z.number().int().nonnegative().optional(),
1638
- contextId: import_zod6.z.string().optional(),
1639
- payerPubkey: import_zod6.z.string().regex(/^[0-9a-f]{64}$/i),
1640
- payerSignature: import_zod6.z.string().regex(/^[0-9a-f]+$/i),
1641
- payeePubkey: import_zod6.z.string().regex(/^[0-9a-f]{64}$/i).optional(),
1642
- payeeSignature: import_zod6.z.string().regex(/^[0-9a-f]+$/i).optional()
1643
- });
1644
- var SettlementSchema = import_zod6.z.object({
1645
- settlementId: import_zod6.z.string().uuid(),
1646
- settlementKey: import_zod6.z.string().regex(/^[0-9a-f]{64}$/i),
1647
- encounterId: import_zod6.z.string().regex(/^[0-9a-f]{64}$/i),
1648
- issuerAccountId: import_zod6.z.string().uuid(),
1649
- tokenSerial: import_zod6.z.string(),
1650
- payerUserId: import_zod6.z.string().uuid(),
1651
- payeeUserId: import_zod6.z.string().uuid(),
1652
- amountKobo: import_zod6.z.number().int().nonnegative(),
1653
- currency: import_zod6.z.string().length(3),
1654
- receiptId: import_zod6.z.string().nullable(),
1655
- status: import_zod6.z.enum(["SETTLED", "REVIEW", "REJECTED"]),
1656
- issuerSig: import_zod6.z.string(),
1657
- createdAtMs: import_zod6.z.number().int().nonnegative()
1658
- });
1659
- var SettleResponseSchema = import_zod6.z.object({
2027
+ var OfflineTokenSchema = import_zod7.z.object({
2028
+ tokenId: import_zod7.z.string().uuid(),
2029
+ tokenSerial: import_zod7.z.string(),
2030
+ issuerAccountId: import_zod7.z.string().uuid(),
2031
+ payerUserId: import_zod7.z.string().uuid(),
2032
+ maxAmountKobo: import_zod7.z.number().int().positive(),
2033
+ currency: import_zod7.z.string().length(3),
2034
+ issuedAtMs: import_zod7.z.number().int().nonnegative(),
2035
+ expiresAtMs: import_zod7.z.number().int().nonnegative(),
2036
+ issuerSig: import_zod7.z.string()
2037
+ });
2038
+ var PaymentClaimSchema = import_zod7.z.object({
2039
+ encounterId: import_zod7.z.string().regex(/^[0-9a-f]{64}$/i).optional(),
2040
+ tokenSerial: import_zod7.z.string(),
2041
+ payerUserId: import_zod7.z.string().uuid(),
2042
+ payeeUserId: import_zod7.z.string().uuid(),
2043
+ payerNonce: import_zod7.z.string(),
2044
+ payeeNonce: import_zod7.z.string(),
2045
+ amountKobo: import_zod7.z.number().int().positive(),
2046
+ currency: import_zod7.z.string().length(3).default("NGN"),
2047
+ occurredAtMs: import_zod7.z.number().int().nonnegative(),
2048
+ completedAtMs: import_zod7.z.number().int().nonnegative().optional(),
2049
+ contextId: import_zod7.z.string().optional(),
2050
+ payerPubkey: import_zod7.z.string().regex(/^[0-9a-f]{64}$/i),
2051
+ payerSignature: import_zod7.z.string().regex(/^[0-9a-f]+$/i),
2052
+ payeePubkey: import_zod7.z.string().regex(/^[0-9a-f]{64}$/i).optional(),
2053
+ payeeSignature: import_zod7.z.string().regex(/^[0-9a-f]+$/i).optional()
2054
+ });
2055
+ var SettlementSchema = import_zod7.z.object({
2056
+ settlementId: import_zod7.z.string().uuid(),
2057
+ settlementKey: import_zod7.z.string().regex(/^[0-9a-f]{64}$/i),
2058
+ encounterId: import_zod7.z.string().regex(/^[0-9a-f]{64}$/i),
2059
+ issuerAccountId: import_zod7.z.string().uuid(),
2060
+ tokenSerial: import_zod7.z.string(),
2061
+ payerUserId: import_zod7.z.string().uuid(),
2062
+ payeeUserId: import_zod7.z.string().uuid(),
2063
+ amountKobo: import_zod7.z.number().int().nonnegative(),
2064
+ currency: import_zod7.z.string().length(3),
2065
+ receiptId: import_zod7.z.string().nullable(),
2066
+ status: import_zod7.z.enum(["SETTLED", "REVIEW", "REJECTED"]),
2067
+ issuerSig: import_zod7.z.string(),
2068
+ createdAtMs: import_zod7.z.number().int().nonnegative()
2069
+ });
2070
+ var SettleResponseSchema = import_zod7.z.object({
1660
2071
  settlement: SettlementSchema,
1661
- encounterId: import_zod6.z.string().regex(/^[0-9a-f]{64}$/i),
1662
- replayed: import_zod6.z.boolean()
2072
+ encounterId: import_zod7.z.string().regex(/^[0-9a-f]{64}$/i),
2073
+ replayed: import_zod7.z.boolean()
1663
2074
  });
1664
2075
  var ENCOUNTER_DOMAIN = "offline:v1:encounter";
1665
2076
  async function sha256Hex(input) {
@@ -1832,134 +2243,352 @@ function createHmacFetch(opts) {
1832
2243
  });
1833
2244
  }
1834
2245
 
1835
- // src/passes/pass.ts
1836
- var import_zod7 = require("zod");
1837
- var PASS_KINDS = [
1838
- "ride-ticket",
1839
- "transit-pass",
1840
- "event-ticket",
1841
- "voucher",
1842
- "loyalty",
1843
- "receipt-link"
1844
- ];
1845
- var PASS_STATES = [
1846
- "issued",
1847
- "active",
1848
- "redeemed",
1849
- "expired",
1850
- "revoked"
2246
+ // src/partner/client.ts
2247
+ var import_zod8 = require("zod");
2248
+ var import_sha2563 = require("@noble/hashes/sha256");
2249
+ var import_hmac4 = require("@noble/hashes/hmac");
2250
+ var import_utils2 = require("@noble/hashes/utils");
2251
+ var PARTNER_SCOPES = [
2252
+ "passes:write",
2253
+ "passes:read",
2254
+ "passes:redeem",
2255
+ "receipts:write",
2256
+ "receipts:read",
2257
+ "offline:issue",
2258
+ "offline:settle",
2259
+ "offline:read",
2260
+ "collections:write",
2261
+ "collections:read",
2262
+ "collections:pay",
2263
+ "collections:webhook",
2264
+ "reports:read",
2265
+ "payouts:write",
2266
+ "payouts:read",
2267
+ "partner:funding:write",
2268
+ "partner:payout:write",
2269
+ "partner:reconciliation:read"
1851
2270
  ];
1852
- var HexString2 = (length) => import_zod7.z.string().regex(
1853
- new RegExp(`^[0-9a-fA-F]{${length * 2}}$`),
1854
- `expected ${length}-byte hex string`
1855
- );
1856
- var PassMetadataSchema = import_zod7.z.record(
1857
- import_zod7.z.union([import_zod7.z.string(), import_zod7.z.number(), import_zod7.z.boolean(), import_zod7.z.null()])
1858
- );
1859
- var PassSchema = import_zod7.z.object({
1860
- passId: import_zod7.z.string().min(1),
1861
- /** Optional client/template grouping id (server may omit). */
1862
- templateId: import_zod7.z.string().min(1).optional(),
1863
- /** Optional human-facing holder identity (server may omit). The cryptographic binding
1864
- * is `holderDevicePubkey` below. */
1865
- holderUserId: import_zod7.z.string().min(1).optional(),
1866
- kind: import_zod7.z.enum(PASS_KINDS),
1867
- issuerId: import_zod7.z.string().min(1),
1868
- issuedAtMs: import_zod7.z.number().int().nonnegative(),
1869
- validFromMs: import_zod7.z.number().int().nonnegative(),
1870
- validUntilMs: import_zod7.z.number().int().positive(),
1871
- state: import_zod7.z.enum(PASS_STATES),
1872
- metadata: PassMetadataSchema,
1873
- nonce: import_zod7.z.string().min(1),
1874
- /** Device id this pass is bound to (FK to backend `device_keys`). */
1875
- holderDeviceId: import_zod7.z.string().min(1),
1876
- /** 32-byte hex Ed25519 public key of the bound device. The redemption signature
1877
- * is verified against this key — it is the security-critical binding. */
1878
- holderDevicePubkey: HexString2(32),
1879
- /** Optional fixed amount for monetary passes (vouchers, gift cards) in kobo. */
1880
- amountKobo: import_zod7.z.number().int().nonnegative().optional(),
1881
- /** ISO-4217-ish currency code; required on the wire. SDK builders default to NGN. */
1882
- currency: import_zod7.z.string().min(3).max(8),
1883
- /** Monotonic redemption counter floor. Redemption.counter MUST be > counterSeed. */
1884
- counterSeed: import_zod7.z.number().int().nonnegative(),
1885
- /** Optional cumulative spend cap in kobo across all redemptions of this pass. */
1886
- cumulativeCapKobo: import_zod7.z.number().int().nonnegative().optional(),
1887
- issuerSig: HexString2(64)
1888
- }).refine((v) => v.validUntilMs > v.validFromMs, {
1889
- message: "validUntilMs must be greater than validFromMs"
2271
+ var ApiCredentialPublicSchema = import_zod8.z.object({
2272
+ id: import_zod8.z.string().uuid(),
2273
+ accountId: import_zod8.z.string().uuid(),
2274
+ keyId: import_zod8.z.string(),
2275
+ scopes: import_zod8.z.array(import_zod8.z.enum(PARTNER_SCOPES)),
2276
+ label: import_zod8.z.string().nullable(),
2277
+ createdAtMs: import_zod8.z.number().int().nonnegative(),
2278
+ lastUsedAtMs: import_zod8.z.number().int().nonnegative().nullable(),
2279
+ revokedAtMs: import_zod8.z.number().int().nonnegative().nullable()
1890
2280
  });
1891
- function buildPass(input) {
1892
- if (input.validUntilMs <= input.validFromMs) {
1893
- throw new Error("validUntilMs must be greater than validFromMs");
1894
- }
1895
- const out = {
1896
- passId: input.passId,
1897
- kind: input.kind,
1898
- issuerId: input.issuerId,
1899
- issuedAtMs: input.issuedAtMs,
1900
- validFromMs: input.validFromMs,
1901
- validUntilMs: input.validUntilMs,
1902
- state: input.state,
1903
- metadata: input.metadata,
1904
- nonce: input.nonce,
1905
- holderDeviceId: input.holderDeviceId,
1906
- holderDevicePubkey: input.holderDevicePubkey,
1907
- currency: input.currency ?? "NGN",
1908
- counterSeed: input.counterSeed
1909
- };
1910
- if (typeof input.templateId === "string") out.templateId = input.templateId;
1911
- if (typeof input.holderUserId === "string")
1912
- out.holderUserId = input.holderUserId;
1913
- if (typeof input.amountKobo === "number") out.amountKobo = input.amountKobo;
1914
- if (typeof input.cumulativeCapKobo === "number") {
1915
- out.cumulativeCapKobo = input.cumulativeCapKobo;
1916
- }
1917
- return out;
2281
+ var MintedApiCredentialSchema = ApiCredentialPublicSchema.extend({
2282
+ secret: import_zod8.z.string().min(1)
2283
+ });
2284
+ var enc = new TextEncoder();
2285
+ async function sha256Hex2(input) {
2286
+ const data = typeof input === "string" ? enc.encode(input) : input;
2287
+ return (0, import_utils2.bytesToHex)((0, import_sha2563.sha256)(data));
1918
2288
  }
1919
- function signPass(unsigned, issuerPrivateKey) {
1920
- const issuerSig = bytesToHex(
1921
- sign(canonicalJSONBytes(unsigned), issuerPrivateKey)
1922
- );
1923
- return { ...unsigned, issuerSig };
2289
+ async function hmacSha256Hex(keyHex, message) {
2290
+ return (0, import_utils2.bytesToHex)((0, import_hmac4.hmac)(import_sha2563.sha256, enc.encode(keyHex), enc.encode(message)));
1924
2291
  }
1925
- function verifyPass(pass, issuerPublicKey) {
1926
- try {
1927
- const parsed = PassSchema.parse(pass);
1928
- const { issuerSig, ...unsigned } = parsed;
1929
- return verify(
1930
- canonicalJSONBytes(unsigned),
1931
- hexToBytes(issuerSig),
1932
- issuerPublicKey
1933
- );
1934
- } catch {
1935
- return false;
1936
- }
2292
+ function defaultNonce2() {
2293
+ const c = globalThis.crypto;
2294
+ if (c?.randomUUID) return c.randomUUID();
2295
+ return `${Date.now().toString(16)}-${Math.random().toString(16).slice(2)}`;
1937
2296
  }
1938
- function isPassWithinValidity(pass, nowMs) {
1939
- return nowMs >= pass.validFromMs && nowMs < pass.validUntilMs;
2297
+ function canonical(params) {
2298
+ return [
2299
+ params.method.toUpperCase(),
2300
+ params.path,
2301
+ params.ts,
2302
+ params.nonce,
2303
+ params.bodyHash
2304
+ ].join("\n");
1940
2305
  }
1941
-
1942
- // src/passes/redemption.ts
1943
- var import_zod8 = require("zod");
1944
- var HexSig2 = import_zod8.z.string().regex(/^[0-9a-fA-F]{128}$/, "expected 64-byte hex signature");
1945
- var RedemptionSchema = import_zod8.z.object({
1946
- pass: PassSchema,
1947
- redeemerId: import_zod8.z.string().min(1),
1948
- redeemedAtMs: import_zod8.z.number().int().nonnegative(),
1949
- /** Strictly monotonic counter scoped to a single pass. Must be > pass.counterSeed
1950
- * and > the redeemer's lastSeenCounter for this pass. */
1951
- counter: import_zod8.z.number().int().positive(),
1952
- /** Amount being redeemed in kobo (0 for non-monetary passes like ride tickets). */
1953
- amountKobo: import_zod8.z.number().int().nonnegative(),
1954
- nonce: import_zod8.z.string().min(1),
1955
- holderSig: HexSig2
1956
- });
1957
- var REDEEMABLE_STATES = /* @__PURE__ */ new Set(["issued", "active"]);
1958
- function buildRedemption(input) {
1959
- if (!REDEEMABLE_STATES.has(input.pass.state)) {
1960
- throw new Error(`pass not in redeemable state: ${input.pass.state}`);
1961
- }
1962
- if (input.redeemedAtMs < input.pass.validFromMs) {
2306
+ async function signPartnerRequest(params) {
2307
+ const ts = String(Math.floor((params.nowMs ?? Date.now()) / 1e3));
2308
+ const nonce = params.nonce ?? defaultNonce2();
2309
+ const bodyData = typeof params.body === "string" ? enc.encode(params.body) : params.body ?? new Uint8Array();
2310
+ const bodyHash = await sha256Hex2(bodyData);
2311
+ const message = canonical({
2312
+ method: params.method,
2313
+ path: params.path,
2314
+ ts,
2315
+ nonce,
2316
+ bodyHash
2317
+ });
2318
+ const signingKey = await sha256Hex2(params.secret);
2319
+ const sig = await hmacSha256Hex(signingKey, message);
2320
+ return {
2321
+ authorization: `Flur-Hmac key=${params.keyId}, ts=${ts}, nonce=${nonce}, sig=${sig}`,
2322
+ ts,
2323
+ nonce,
2324
+ bodyHash
2325
+ };
2326
+ }
2327
+ function createFlurPartnerClient(opts) {
2328
+ const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
2329
+ if (!fetchImpl) {
2330
+ throw new Error(
2331
+ "createFlurPartnerClient: no fetch implementation available"
2332
+ );
2333
+ }
2334
+ const baseUrl = opts.baseUrl.replace(/\/$/, "");
2335
+ const scopeHeader = normalizeScopeHeader(opts.scope);
2336
+ async function makeSignedInit(method, path, body) {
2337
+ const sig = await signPartnerRequest({
2338
+ keyId: opts.keyId,
2339
+ secret: opts.secret,
2340
+ method,
2341
+ path,
2342
+ body: body ?? "",
2343
+ nowMs: opts.nowMs?.(),
2344
+ nonce: opts.nonce?.()
2345
+ });
2346
+ const headers = {
2347
+ authorization: sig.authorization,
2348
+ accept: "application/json"
2349
+ };
2350
+ if (scopeHeader) headers["x-flur-scope"] = scopeHeader;
2351
+ if (body !== void 0) headers["content-type"] = "application/json";
2352
+ const init2 = { method, headers };
2353
+ if (body !== void 0) init2.body = body;
2354
+ return init2;
2355
+ }
2356
+ async function request(opts2) {
2357
+ const bodyStr = opts2.body === void 0 ? void 0 : JSON.stringify(opts2.body);
2358
+ const init2 = await makeSignedInit(opts2.method, opts2.path, bodyStr);
2359
+ const resp = await fetchImpl(`${baseUrl}${opts2.path}`, init2);
2360
+ const text = await resp.text();
2361
+ let raw;
2362
+ if (text) {
2363
+ try {
2364
+ raw = JSON.parse(text);
2365
+ } catch {
2366
+ }
2367
+ }
2368
+ if (!resp.ok) {
2369
+ const code = raw && typeof raw === "object" && "code" in raw && typeof raw.code === "string" ? raw.code : `http_${resp.status}`;
2370
+ const message = raw && typeof raw === "object" && "message" in raw && typeof raw.message === "string" ? raw.message : `request failed with status ${resp.status}`;
2371
+ throw new FlurApiError(resp.status, code, message, raw);
2372
+ }
2373
+ return raw;
2374
+ }
2375
+ const fetchLike = async (input, init2) => {
2376
+ const url = typeof input === "string" ? input : input.toString();
2377
+ const u = new URL(url, baseUrl);
2378
+ const path = `${u.pathname}${u.search}`;
2379
+ const method = (init2?.method ?? "GET").toUpperCase();
2380
+ let bodyStr;
2381
+ if (init2?.body) {
2382
+ bodyStr = typeof init2.body === "string" ? init2.body : init2.body.toString();
2383
+ }
2384
+ const signed = await makeSignedInit(method, path, bodyStr);
2385
+ return fetchImpl(`${baseUrl}${path}`, {
2386
+ ...init2,
2387
+ ...signed,
2388
+ headers: {
2389
+ ...init2?.headers,
2390
+ ...signed.headers
2391
+ }
2392
+ });
2393
+ };
2394
+ return { request, fetch: fetchLike };
2395
+ }
2396
+ function normalizeScopeHeader(scope) {
2397
+ if (!scope || scope.length === 0) return void 0;
2398
+ const unique = Array.from(new Set(scope));
2399
+ for (const item of unique) {
2400
+ if (!PARTNER_SCOPES.includes(item)) {
2401
+ throw new Error(`unsupported partner scope: ${item}`);
2402
+ }
2403
+ }
2404
+ return unique.join(" ");
2405
+ }
2406
+ function createApiCredentialsAdminClient(opts) {
2407
+ const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
2408
+ if (!fetchImpl) {
2409
+ throw new Error(
2410
+ "createApiCredentialsAdminClient: no fetch implementation available"
2411
+ );
2412
+ }
2413
+ const baseUrl = opts.baseUrl.replace(/\/$/, "");
2414
+ async function call(method, path, body, parser) {
2415
+ const init2 = {
2416
+ method,
2417
+ headers: {
2418
+ "content-type": "application/json",
2419
+ accept: "application/json"
2420
+ }
2421
+ };
2422
+ if (body !== void 0) init2.body = JSON.stringify(body);
2423
+ const resp = await fetchImpl(`${baseUrl}${path}`, init2);
2424
+ const text = await resp.text();
2425
+ let raw;
2426
+ if (text) {
2427
+ try {
2428
+ raw = JSON.parse(text);
2429
+ } catch {
2430
+ }
2431
+ }
2432
+ if (!resp.ok) {
2433
+ const code = raw && typeof raw === "object" && "code" in raw && typeof raw.code === "string" ? raw.code : `http_${resp.status}`;
2434
+ const message = raw && typeof raw === "object" && "message" in raw && typeof raw.message === "string" ? raw.message : `request failed with status ${resp.status}`;
2435
+ throw new FlurApiError(resp.status, code, message, raw);
2436
+ }
2437
+ return parser(raw);
2438
+ }
2439
+ const listSchema = import_zod8.z.object({
2440
+ items: import_zod8.z.array(ApiCredentialPublicSchema)
2441
+ });
2442
+ return {
2443
+ list: (accountId) => call(
2444
+ "GET",
2445
+ `/v1/accounts/${accountId}/api-credentials`,
2446
+ void 0,
2447
+ (raw) => listSchema.parse(raw)
2448
+ ),
2449
+ mint: (accountId, input) => call(
2450
+ "POST",
2451
+ `/v1/accounts/${accountId}/api-credentials`,
2452
+ input,
2453
+ (raw) => MintedApiCredentialSchema.parse(raw)
2454
+ ),
2455
+ revoke: (accountId, credentialId) => call(
2456
+ "DELETE",
2457
+ `/v1/accounts/${accountId}/api-credentials/${credentialId}`,
2458
+ void 0,
2459
+ (raw) => ApiCredentialPublicSchema.parse(raw)
2460
+ )
2461
+ };
2462
+ }
2463
+
2464
+ // src/passes/pass.ts
2465
+ var import_zod9 = require("zod");
2466
+ var PASS_KINDS = [
2467
+ "ride-ticket",
2468
+ "transit-pass",
2469
+ "event-ticket",
2470
+ "voucher",
2471
+ "loyalty",
2472
+ "receipt-link"
2473
+ ];
2474
+ var PASS_STATES = [
2475
+ "issued",
2476
+ "active",
2477
+ "redeemed",
2478
+ "expired",
2479
+ "revoked"
2480
+ ];
2481
+ var HexString2 = (length) => import_zod9.z.string().regex(
2482
+ new RegExp(`^[0-9a-fA-F]{${length * 2}}$`),
2483
+ `expected ${length}-byte hex string`
2484
+ );
2485
+ var PassMetadataSchema = import_zod9.z.record(
2486
+ import_zod9.z.union([import_zod9.z.string(), import_zod9.z.number(), import_zod9.z.boolean(), import_zod9.z.null()])
2487
+ );
2488
+ var PassSchema = import_zod9.z.object({
2489
+ passId: import_zod9.z.string().min(1),
2490
+ /** Optional client/template grouping id (server may omit). */
2491
+ templateId: import_zod9.z.string().min(1).optional(),
2492
+ /** Optional human-facing holder identity (server may omit). The cryptographic binding
2493
+ * is `holderDevicePubkey` below. */
2494
+ holderUserId: import_zod9.z.string().min(1).optional(),
2495
+ kind: import_zod9.z.enum(PASS_KINDS),
2496
+ issuerId: import_zod9.z.string().min(1),
2497
+ issuedAtMs: import_zod9.z.number().int().nonnegative(),
2498
+ validFromMs: import_zod9.z.number().int().nonnegative(),
2499
+ validUntilMs: import_zod9.z.number().int().positive(),
2500
+ state: import_zod9.z.enum(PASS_STATES),
2501
+ metadata: PassMetadataSchema,
2502
+ nonce: import_zod9.z.string().min(1),
2503
+ /** Device id this pass is bound to (FK to backend `device_keys`). */
2504
+ holderDeviceId: import_zod9.z.string().min(1),
2505
+ /** 32-byte hex Ed25519 public key of the bound device. The redemption signature
2506
+ * is verified against this key — it is the security-critical binding. */
2507
+ holderDevicePubkey: HexString2(32),
2508
+ /** Optional fixed amount for monetary passes (vouchers, gift cards) in kobo. */
2509
+ amountKobo: import_zod9.z.number().int().nonnegative().optional(),
2510
+ /** ISO-4217-ish currency code; required on the wire. SDK builders default to NGN. */
2511
+ currency: import_zod9.z.string().min(3).max(8),
2512
+ /** Monotonic redemption counter floor. Redemption.counter MUST be > counterSeed. */
2513
+ counterSeed: import_zod9.z.number().int().nonnegative(),
2514
+ /** Optional cumulative spend cap in kobo across all redemptions of this pass. */
2515
+ cumulativeCapKobo: import_zod9.z.number().int().nonnegative().optional(),
2516
+ issuerSig: HexString2(64)
2517
+ }).refine((v) => v.validUntilMs > v.validFromMs, {
2518
+ message: "validUntilMs must be greater than validFromMs"
2519
+ });
2520
+ function buildPass(input) {
2521
+ if (input.validUntilMs <= input.validFromMs) {
2522
+ throw new Error("validUntilMs must be greater than validFromMs");
2523
+ }
2524
+ const out = {
2525
+ passId: input.passId,
2526
+ kind: input.kind,
2527
+ issuerId: input.issuerId,
2528
+ issuedAtMs: input.issuedAtMs,
2529
+ validFromMs: input.validFromMs,
2530
+ validUntilMs: input.validUntilMs,
2531
+ state: input.state,
2532
+ metadata: input.metadata,
2533
+ nonce: input.nonce,
2534
+ holderDeviceId: input.holderDeviceId,
2535
+ holderDevicePubkey: input.holderDevicePubkey,
2536
+ currency: input.currency ?? "NGN",
2537
+ counterSeed: input.counterSeed
2538
+ };
2539
+ if (typeof input.templateId === "string") out.templateId = input.templateId;
2540
+ if (typeof input.holderUserId === "string")
2541
+ out.holderUserId = input.holderUserId;
2542
+ if (typeof input.amountKobo === "number") out.amountKobo = input.amountKobo;
2543
+ if (typeof input.cumulativeCapKobo === "number") {
2544
+ out.cumulativeCapKobo = input.cumulativeCapKobo;
2545
+ }
2546
+ return out;
2547
+ }
2548
+ function signPass(unsigned, issuerPrivateKey) {
2549
+ const issuerSig = bytesToHex(
2550
+ sign(canonicalJSONBytes(unsigned), issuerPrivateKey)
2551
+ );
2552
+ return { ...unsigned, issuerSig };
2553
+ }
2554
+ function verifyPass(pass, issuerPublicKey) {
2555
+ try {
2556
+ const parsed = PassSchema.parse(pass);
2557
+ const { issuerSig, ...unsigned } = parsed;
2558
+ return verify(
2559
+ canonicalJSONBytes(unsigned),
2560
+ hexToBytes(issuerSig),
2561
+ issuerPublicKey
2562
+ );
2563
+ } catch {
2564
+ return false;
2565
+ }
2566
+ }
2567
+ function isPassWithinValidity(pass, nowMs) {
2568
+ return nowMs >= pass.validFromMs && nowMs < pass.validUntilMs;
2569
+ }
2570
+
2571
+ // src/passes/redemption.ts
2572
+ var import_zod10 = require("zod");
2573
+ var HexSig2 = import_zod10.z.string().regex(/^[0-9a-fA-F]{128}$/, "expected 64-byte hex signature");
2574
+ var RedemptionSchema = import_zod10.z.object({
2575
+ pass: PassSchema,
2576
+ redeemerId: import_zod10.z.string().min(1),
2577
+ redeemedAtMs: import_zod10.z.number().int().nonnegative(),
2578
+ /** Strictly monotonic counter scoped to a single pass. Must be > pass.counterSeed
2579
+ * and > the redeemer's lastSeenCounter for this pass. */
2580
+ counter: import_zod10.z.number().int().positive(),
2581
+ /** Amount being redeemed in kobo (0 for non-monetary passes like ride tickets). */
2582
+ amountKobo: import_zod10.z.number().int().nonnegative(),
2583
+ nonce: import_zod10.z.string().min(1),
2584
+ holderSig: HexSig2
2585
+ });
2586
+ var REDEEMABLE_STATES = /* @__PURE__ */ new Set(["issued", "active"]);
2587
+ function buildRedemption(input) {
2588
+ if (!REDEEMABLE_STATES.has(input.pass.state)) {
2589
+ throw new Error(`pass not in redeemable state: ${input.pass.state}`);
2590
+ }
2591
+ if (input.redeemedAtMs < input.pass.validFromMs) {
1963
2592
  throw new Error("redeemedAtMs is before pass validFromMs");
1964
2593
  }
1965
2594
  if (input.redeemedAtMs >= input.pass.validUntilMs) {
@@ -2037,43 +2666,43 @@ function verifyRedemption(r, issuerPublicKey) {
2037
2666
  }
2038
2667
 
2039
2668
  // src/receipts/receipt.ts
2040
- var import_zod9 = require("zod");
2669
+ var import_zod11 = require("zod");
2041
2670
  var RECEIPT_CHANNELS = ["cash", "pass"];
2042
2671
  var RECEIPT_KINDS = RECEIPT_CHANNELS;
2043
- var HexString3 = (length) => import_zod9.z.string().regex(
2672
+ var HexString3 = (length) => import_zod11.z.string().regex(
2044
2673
  new RegExp(`^[0-9a-fA-F]{${length * 2}}$`),
2045
2674
  `expected ${length}-byte hex string`
2046
2675
  );
2047
- var ReceiptPayloadSchema = import_zod9.z.record(
2048
- import_zod9.z.union([import_zod9.z.string(), import_zod9.z.number(), import_zod9.z.boolean(), import_zod9.z.null()])
2676
+ var ReceiptPayloadSchema = import_zod11.z.record(
2677
+ import_zod11.z.union([import_zod11.z.string(), import_zod11.z.number(), import_zod11.z.boolean(), import_zod11.z.null()])
2049
2678
  );
2050
- var ReceiptSchema = import_zod9.z.object({
2051
- receiptId: import_zod9.z.string().min(1),
2052
- channel: import_zod9.z.enum(RECEIPT_CHANNELS),
2679
+ var ReceiptSchema = import_zod11.z.object({
2680
+ receiptId: import_zod11.z.string().min(1),
2681
+ channel: import_zod11.z.enum(RECEIPT_CHANNELS),
2053
2682
  /** Cash-channel: send_intents.id. Required when channel === 'cash'. */
2054
- intentId: import_zod9.z.string().min(1).optional(),
2683
+ intentId: import_zod11.z.string().min(1).optional(),
2055
2684
  /** Pass-channel: pass_redemptions.id. Required when channel === 'pass'. */
2056
- passRedemptionId: import_zod9.z.string().min(1).optional(),
2057
- payerUserId: import_zod9.z.string().min(1),
2058
- payeeUserId: import_zod9.z.string().min(1),
2059
- amountKobo: import_zod9.z.number().int().nonnegative(),
2060
- currency: import_zod9.z.string().min(3).max(8),
2061
- issuedAtMs: import_zod9.z.number().int().nonnegative(),
2062
- issuerId: import_zod9.z.string().min(1),
2685
+ passRedemptionId: import_zod11.z.string().min(1).optional(),
2686
+ payerUserId: import_zod11.z.string().min(1),
2687
+ payeeUserId: import_zod11.z.string().min(1),
2688
+ amountKobo: import_zod11.z.number().int().nonnegative(),
2689
+ currency: import_zod11.z.string().min(3).max(8),
2690
+ issuedAtMs: import_zod11.z.number().int().nonnegative(),
2691
+ issuerId: import_zod11.z.string().min(1),
2063
2692
  payload: ReceiptPayloadSchema,
2064
2693
  issuerSig: HexString3(64)
2065
2694
  }).superRefine((v, ctx) => {
2066
2695
  if (v.channel === "cash") {
2067
2696
  if (!v.intentId) {
2068
2697
  ctx.addIssue({
2069
- code: import_zod9.z.ZodIssueCode.custom,
2698
+ code: import_zod11.z.ZodIssueCode.custom,
2070
2699
  message: "cash receipts require intentId",
2071
2700
  path: ["intentId"]
2072
2701
  });
2073
2702
  }
2074
2703
  if (v.passRedemptionId) {
2075
2704
  ctx.addIssue({
2076
- code: import_zod9.z.ZodIssueCode.custom,
2705
+ code: import_zod11.z.ZodIssueCode.custom,
2077
2706
  message: "cash receipts must not carry passRedemptionId",
2078
2707
  path: ["passRedemptionId"]
2079
2708
  });
@@ -2081,14 +2710,14 @@ var ReceiptSchema = import_zod9.z.object({
2081
2710
  } else if (v.channel === "pass") {
2082
2711
  if (!v.passRedemptionId) {
2083
2712
  ctx.addIssue({
2084
- code: import_zod9.z.ZodIssueCode.custom,
2713
+ code: import_zod11.z.ZodIssueCode.custom,
2085
2714
  message: "pass receipts require passRedemptionId",
2086
2715
  path: ["passRedemptionId"]
2087
2716
  });
2088
2717
  }
2089
2718
  if (v.intentId) {
2090
2719
  ctx.addIssue({
2091
- code: import_zod9.z.ZodIssueCode.custom,
2720
+ code: import_zod11.z.ZodIssueCode.custom,
2092
2721
  message: "pass receipts must not carry intentId",
2093
2722
  path: ["intentId"]
2094
2723
  });
@@ -2327,317 +2956,90 @@ function createReceiptsClient(opts) {
2327
2956
  verifyReceipt: (receipt, issuerPublicKey) => verifyReceipt(receipt, issuerPublicKey)
2328
2957
  };
2329
2958
  }
2330
-
2331
- // src/client/flur.ts
2332
- function generateStaticQR(input) {
2333
- return encodeNQR({ ...input, pointOfInitiation: "static" });
2334
- }
2335
- function generateDynamicQR(input) {
2336
- return encodeNQR({ ...input, pointOfInitiation: "dynamic" });
2337
- }
2338
- function parseQR(payload) {
2339
- return parseNQR(payload);
2340
- }
2341
- function init(opts) {
2342
- const signedFetch = createHmacFetch({
2343
- apiKey: opts.apiKey,
2344
- apiSecret: opts.apiSecret,
2345
- fetchImpl: opts.fetchImpl,
2346
- scope: opts.scope
2347
- });
2348
- const baseUrl = opts.baseUrl.replace(/\/$/, "");
2349
- function subscribeToPayments(s) {
2350
- const controller = new AbortController();
2351
- let cancelled = false;
2352
- (async () => {
2353
- try {
2354
- const url = `${baseUrl}/v1/payments/subscribe?reference=${encodeURIComponent(s.reference)}`;
2355
- const resp = await signedFetch(url, {
2356
- method: "GET",
2357
- headers: { accept: "text/event-stream" },
2358
- signal: controller.signal
2359
- });
2360
- if (!resp.body) return;
2361
- const reader = resp.body.getReader();
2362
- const decoder = new TextDecoder();
2363
- let buffer = "";
2364
- while (!cancelled) {
2365
- const { value, done } = await reader.read();
2366
- if (done) return;
2367
- buffer += decoder.decode(value, { stream: true });
2368
- let idx;
2369
- while ((idx = buffer.indexOf("\n\n")) >= 0) {
2370
- const chunk = buffer.slice(0, idx);
2371
- buffer = buffer.slice(idx + 2);
2372
- for (const line of chunk.split("\n")) {
2373
- if (!line.startsWith("data:")) continue;
2374
- const json = line.slice(5).trim();
2375
- if (!json) continue;
2376
- try {
2377
- s.onEvent(JSON.parse(json));
2378
- } catch (err) {
2379
- s.onError?.(err);
2380
- }
2381
- }
2382
- }
2383
- }
2384
- } catch (err) {
2385
- if (!cancelled) s.onError?.(err);
2386
- }
2387
- })();
2388
- return () => {
2389
- cancelled = true;
2390
- controller.abort();
2391
- };
2392
- }
2393
- const cash = {
2394
- generateStaticQR,
2395
- generateDynamicQR,
2396
- parseQR,
2397
- subscribeToPayments
2398
- };
2399
- const passes = createPassesClient({ baseUrl, fetchImpl: signedFetch });
2400
- const receipts = createReceiptsClient({ baseUrl, fetchImpl: signedFetch });
2401
- return {
2402
- // top-level back-compat surface
2403
- generateStaticQR,
2404
- generateDynamicQR,
2405
- parseQR,
2406
- subscribeToPayments,
2407
- // namespaces
2408
- cash,
2409
- passes,
2410
- receipts
2411
- };
2412
- }
2413
-
2414
- // src/accounts/client.ts
2415
- var import_zod10 = require("zod");
2416
- var ACCOUNT_TYPES = ["personal", "business", "partner"];
2417
- var ACCOUNT_STATUSES = ["active", "suspended", "closed"];
2418
- var MEMBERSHIP_ROLES = ["owner", "admin", "driver", "staff"];
2419
- var AccountSchema = import_zod10.z.object({
2420
- accountId: import_zod10.z.string().uuid(),
2421
- type: import_zod10.z.enum(ACCOUNT_TYPES),
2422
- displayName: import_zod10.z.string().min(1),
2423
- status: import_zod10.z.enum(ACCOUNT_STATUSES),
2424
- ownerUserId: import_zod10.z.string().uuid().nullable(),
2425
- createdAtMs: import_zod10.z.number().int().nonnegative()
2426
- });
2427
- var AccountMembershipSchema = import_zod10.z.object({
2428
- accountId: import_zod10.z.string().uuid(),
2429
- userId: import_zod10.z.string().uuid(),
2430
- role: import_zod10.z.enum(MEMBERSHIP_ROLES),
2431
- createdAtMs: import_zod10.z.number().int().nonnegative()
2432
- });
2433
- function createAccountsClient(opts) {
2434
- const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
2435
- if (!fetchImpl) {
2436
- throw new Error("createAccountsClient: no fetch implementation available");
2437
- }
2438
- const baseUrl = opts.baseUrl.replace(/\/$/, "");
2439
- async function call(method, path, body, parser) {
2440
- const init2 = {
2441
- method,
2442
- headers: {
2443
- "content-type": "application/json",
2444
- accept: "application/json"
2445
- }
2446
- };
2447
- if (body !== void 0) init2.body = JSON.stringify(body);
2448
- const resp = await fetchImpl(`${baseUrl}${path}`, init2);
2449
- const text = await resp.text();
2450
- let raw = void 0;
2451
- if (text) {
2452
- try {
2453
- raw = JSON.parse(text);
2454
- } catch {
2455
- }
2456
- }
2457
- if (!resp.ok) {
2458
- const code = raw && typeof raw === "object" && "code" in raw && typeof raw.code === "string" ? raw.code : `http_${resp.status}`;
2459
- const message = raw && typeof raw === "object" && "message" in raw && typeof raw.message === "string" ? raw.message : `request failed with status ${resp.status}`;
2460
- throw new FlurApiError(resp.status, code, message, raw);
2461
- }
2462
- return parser(raw);
2463
- }
2464
- const itemsSchema = import_zod10.z.object({ items: import_zod10.z.array(AccountSchema) });
2465
- const memberItemsSchema = import_zod10.z.object({
2466
- items: import_zod10.z.array(AccountMembershipSchema)
2467
- });
2468
- return {
2469
- listMyAccounts: () => call(
2470
- "GET",
2471
- "/v1/accounts/me",
2472
- void 0,
2473
- (raw) => itemsSchema.parse(raw)
2474
- ),
2475
- getAccount: (accountId) => call(
2476
- "GET",
2477
- `/v1/accounts/${encodeURIComponent(accountId)}`,
2478
- void 0,
2479
- (raw) => AccountSchema.parse(raw)
2480
- ),
2481
- listMembers: (accountId) => call(
2482
- "GET",
2483
- `/v1/accounts/${encodeURIComponent(accountId)}/members`,
2484
- void 0,
2485
- (raw) => memberItemsSchema.parse(raw)
2486
- ),
2487
- createBusinessAccount: (input) => call("POST", "/v1/accounts", input, (raw) => AccountSchema.parse(raw)),
2488
- addMember: (accountId, input) => call(
2489
- "POST",
2490
- `/v1/accounts/${encodeURIComponent(accountId)}/members`,
2491
- input,
2492
- (raw) => AccountMembershipSchema.parse(raw)
2493
- )
2494
- };
2495
- }
2496
-
2497
- // src/partner/client.ts
2498
- var import_zod11 = require("zod");
2499
- var import_sha2563 = require("@noble/hashes/sha256");
2500
- var import_hmac4 = require("@noble/hashes/hmac");
2501
- var import_utils2 = require("@noble/hashes/utils");
2502
- var PARTNER_SCOPES = [
2503
- "passes:write",
2504
- "passes:read",
2505
- "passes:redeem",
2506
- "receipts:write",
2507
- "receipts:read",
2508
- "offline:issue",
2509
- "offline:settle",
2510
- "offline:read"
2511
- ];
2512
- var ApiCredentialPublicSchema = import_zod11.z.object({
2513
- id: import_zod11.z.string().uuid(),
2514
- accountId: import_zod11.z.string().uuid(),
2515
- keyId: import_zod11.z.string(),
2516
- scopes: import_zod11.z.array(import_zod11.z.enum(PARTNER_SCOPES)),
2517
- label: import_zod11.z.string().nullable(),
2518
- createdAtMs: import_zod11.z.number().int().nonnegative(),
2519
- lastUsedAtMs: import_zod11.z.number().int().nonnegative().nullable(),
2520
- revokedAtMs: import_zod11.z.number().int().nonnegative().nullable()
2521
- });
2522
- var MintedApiCredentialSchema = ApiCredentialPublicSchema.extend({
2523
- secret: import_zod11.z.string().min(1)
2524
- });
2525
- var enc = new TextEncoder();
2526
- async function sha256Hex2(input) {
2527
- const data = typeof input === "string" ? enc.encode(input) : input;
2528
- return (0, import_utils2.bytesToHex)((0, import_sha2563.sha256)(data));
2529
- }
2530
- async function hmacSha256Hex(keyHex, message) {
2531
- return (0, import_utils2.bytesToHex)((0, import_hmac4.hmac)(import_sha2563.sha256, enc.encode(keyHex), enc.encode(message)));
2532
- }
2533
- function defaultNonce2() {
2534
- const c = globalThis.crypto;
2535
- if (c?.randomUUID) return c.randomUUID();
2536
- return `${Date.now().toString(16)}-${Math.random().toString(16).slice(2)}`;
2537
- }
2538
- function canonical(params) {
2539
- return [
2540
- params.method.toUpperCase(),
2541
- params.path,
2542
- params.ts,
2543
- params.nonce,
2544
- params.bodyHash
2545
- ].join("\n");
2546
- }
2547
- async function signPartnerRequest(params) {
2548
- const ts = String(Math.floor((params.nowMs ?? Date.now()) / 1e3));
2549
- const nonce = params.nonce ?? defaultNonce2();
2550
- const bodyData = typeof params.body === "string" ? enc.encode(params.body) : params.body ?? new Uint8Array();
2551
- const bodyHash = await sha256Hex2(bodyData);
2552
- const message = canonical({
2553
- method: params.method,
2554
- path: params.path,
2555
- ts,
2556
- nonce,
2557
- bodyHash
2558
- });
2559
- const signingKey = await sha256Hex2(params.secret);
2560
- const sig = await hmacSha256Hex(signingKey, message);
2561
- return {
2562
- authorization: `Flur-Hmac key=${params.keyId}, ts=${ts}, nonce=${nonce}, sig=${sig}`,
2563
- ts,
2564
- nonce,
2565
- bodyHash
2566
- };
2959
+
2960
+ // src/client/flur.ts
2961
+ function generateStaticQR(input) {
2962
+ return encodeNQR({ ...input, pointOfInitiation: "static" });
2567
2963
  }
2568
- function createFlurPartnerClient(opts) {
2569
- const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
2570
- if (!fetchImpl) {
2571
- throw new Error(
2572
- "createFlurPartnerClient: no fetch implementation available"
2573
- );
2574
- }
2964
+ function generateDynamicQR(input) {
2965
+ return encodeNQR({ ...input, pointOfInitiation: "dynamic" });
2966
+ }
2967
+ function parseQR(payload) {
2968
+ return parseNQR(payload);
2969
+ }
2970
+ function init(opts) {
2971
+ const partner = createFlurPartnerClient({
2972
+ baseUrl: opts.baseUrl,
2973
+ keyId: opts.apiKey,
2974
+ secret: opts.apiSecret,
2975
+ fetchImpl: opts.fetchImpl,
2976
+ scope: opts.scope
2977
+ });
2978
+ const signedFetch = partner.fetch;
2575
2979
  const baseUrl = opts.baseUrl.replace(/\/$/, "");
2576
- async function makeSignedInit(method, path, body) {
2577
- const sig = await signPartnerRequest({
2578
- keyId: opts.keyId,
2579
- secret: opts.secret,
2580
- method,
2581
- path,
2582
- body: body ?? "",
2583
- nowMs: opts.nowMs?.(),
2584
- nonce: opts.nonce?.()
2980
+ function subscribeToPayments(s) {
2981
+ let cancelled = false;
2982
+ queueMicrotask(() => {
2983
+ if (cancelled) return;
2984
+ s.onError?.(
2985
+ new Error(
2986
+ "cash.subscribeToPayments is not available on this backend release; use collections reports or provider webhooks for payment status."
2987
+ )
2988
+ );
2585
2989
  });
2586
- const headers = {
2587
- authorization: sig.authorization,
2588
- accept: "application/json"
2990
+ return () => {
2991
+ cancelled = true;
2589
2992
  };
2590
- if (body !== void 0) headers["content-type"] = "application/json";
2591
- const init2 = { method, headers };
2592
- if (body !== void 0) init2.body = body;
2593
- return init2;
2594
- }
2595
- async function request(opts2) {
2596
- const bodyStr = opts2.body === void 0 ? void 0 : JSON.stringify(opts2.body);
2597
- const init2 = await makeSignedInit(opts2.method, opts2.path, bodyStr);
2598
- const resp = await fetchImpl(`${baseUrl}${opts2.path}`, init2);
2599
- const text = await resp.text();
2600
- let raw;
2601
- if (text) {
2602
- try {
2603
- raw = JSON.parse(text);
2604
- } catch {
2605
- }
2606
- }
2607
- if (!resp.ok) {
2608
- const code = raw && typeof raw === "object" && "code" in raw && typeof raw.code === "string" ? raw.code : `http_${resp.status}`;
2609
- const message = raw && typeof raw === "object" && "message" in raw && typeof raw.message === "string" ? raw.message : `request failed with status ${resp.status}`;
2610
- throw new FlurApiError(resp.status, code, message, raw);
2611
- }
2612
- return raw;
2613
2993
  }
2614
- const fetchLike = async (input, init2) => {
2615
- const url = typeof input === "string" ? input : input.toString();
2616
- const u = new URL(url, baseUrl);
2617
- const path = `${u.pathname}${u.search}`;
2618
- const method = (init2?.method ?? "GET").toUpperCase();
2619
- let bodyStr;
2620
- if (init2?.body) {
2621
- bodyStr = typeof init2.body === "string" ? init2.body : init2.body.toString();
2622
- }
2623
- const signed = await makeSignedInit(method, path, bodyStr);
2624
- return fetchImpl(`${baseUrl}${path}`, {
2625
- ...init2,
2626
- ...signed,
2627
- headers: {
2628
- ...init2?.headers,
2629
- ...signed.headers
2630
- }
2631
- });
2994
+ const cash = {
2995
+ generateStaticQR,
2996
+ generateDynamicQR,
2997
+ parseQR,
2998
+ subscribeToPayments
2999
+ };
3000
+ const passes = createPassesClient({ baseUrl, fetchImpl: signedFetch });
3001
+ const receipts = createReceiptsClient({ baseUrl, fetchImpl: signedFetch });
3002
+ const collections = createPartnerCollectionsClient({
3003
+ baseUrl,
3004
+ fetchImpl: signedFetch
3005
+ });
3006
+ return {
3007
+ // top-level back-compat surface
3008
+ generateStaticQR,
3009
+ generateDynamicQR,
3010
+ parseQR,
3011
+ subscribeToPayments,
3012
+ // namespaces
3013
+ cash,
3014
+ collections,
3015
+ passes,
3016
+ receipts
2632
3017
  };
2633
- return { request, fetch: fetchLike };
2634
3018
  }
2635
- function createApiCredentialsAdminClient(opts) {
3019
+
3020
+ // src/accounts/client.ts
3021
+ var import_zod12 = require("zod");
3022
+ var ACCOUNT_TYPES = ["personal", "business", "partner"];
3023
+ var ACCOUNT_STATUSES = ["active", "suspended", "closed"];
3024
+ var MEMBERSHIP_ROLES = ["owner", "admin", "driver", "staff"];
3025
+ var AccountSchema = import_zod12.z.object({
3026
+ accountId: import_zod12.z.string().uuid(),
3027
+ type: import_zod12.z.enum(ACCOUNT_TYPES),
3028
+ displayName: import_zod12.z.string().min(1),
3029
+ status: import_zod12.z.enum(ACCOUNT_STATUSES),
3030
+ ownerUserId: import_zod12.z.string().uuid().nullable(),
3031
+ createdAtMs: import_zod12.z.number().int().nonnegative()
3032
+ });
3033
+ var AccountMembershipSchema = import_zod12.z.object({
3034
+ accountId: import_zod12.z.string().uuid(),
3035
+ userId: import_zod12.z.string().uuid(),
3036
+ role: import_zod12.z.enum(MEMBERSHIP_ROLES),
3037
+ createdAtMs: import_zod12.z.number().int().nonnegative()
3038
+ });
3039
+ function createAccountsClient(opts) {
2636
3040
  const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
2637
3041
  if (!fetchImpl) {
2638
- throw new Error(
2639
- "createApiCredentialsAdminClient: no fetch implementation available"
2640
- );
3042
+ throw new Error("createAccountsClient: no fetch implementation available");
2641
3043
  }
2642
3044
  const baseUrl = opts.baseUrl.replace(/\/$/, "");
2643
3045
  async function call(method, path, body, parser) {
@@ -2651,7 +3053,7 @@ function createApiCredentialsAdminClient(opts) {
2651
3053
  if (body !== void 0) init2.body = JSON.stringify(body);
2652
3054
  const resp = await fetchImpl(`${baseUrl}${path}`, init2);
2653
3055
  const text = await resp.text();
2654
- let raw;
3056
+ let raw = void 0;
2655
3057
  if (text) {
2656
3058
  try {
2657
3059
  raw = JSON.parse(text);
@@ -2665,70 +3067,78 @@ function createApiCredentialsAdminClient(opts) {
2665
3067
  }
2666
3068
  return parser(raw);
2667
3069
  }
2668
- const listSchema = import_zod11.z.object({
2669
- items: import_zod11.z.array(ApiCredentialPublicSchema)
3070
+ const itemsSchema = import_zod12.z.object({ items: import_zod12.z.array(AccountSchema) });
3071
+ const memberItemsSchema = import_zod12.z.object({
3072
+ items: import_zod12.z.array(AccountMembershipSchema)
2670
3073
  });
2671
3074
  return {
2672
- list: (accountId) => call(
3075
+ listMyAccounts: () => call(
2673
3076
  "GET",
2674
- `/v1/accounts/${accountId}/api-credentials`,
3077
+ "/v1/accounts/me",
2675
3078
  void 0,
2676
- (raw) => listSchema.parse(raw)
3079
+ (raw) => itemsSchema.parse(raw)
2677
3080
  ),
2678
- mint: (accountId, input) => call(
2679
- "POST",
2680
- `/v1/accounts/${accountId}/api-credentials`,
2681
- input,
2682
- (raw) => MintedApiCredentialSchema.parse(raw)
3081
+ getAccount: (accountId) => call(
3082
+ "GET",
3083
+ `/v1/accounts/${encodeURIComponent(accountId)}`,
3084
+ void 0,
3085
+ (raw) => AccountSchema.parse(raw)
2683
3086
  ),
2684
- revoke: (accountId, credentialId) => call(
2685
- "DELETE",
2686
- `/v1/accounts/${accountId}/api-credentials/${credentialId}`,
3087
+ listMembers: (accountId) => call(
3088
+ "GET",
3089
+ `/v1/accounts/${encodeURIComponent(accountId)}/members`,
2687
3090
  void 0,
2688
- (raw) => ApiCredentialPublicSchema.parse(raw)
3091
+ (raw) => memberItemsSchema.parse(raw)
3092
+ ),
3093
+ createBusinessAccount: (input) => call("POST", "/v1/accounts", input, (raw) => AccountSchema.parse(raw)),
3094
+ addMember: (accountId, input) => call(
3095
+ "POST",
3096
+ `/v1/accounts/${encodeURIComponent(accountId)}/members`,
3097
+ input,
3098
+ (raw) => AccountMembershipSchema.parse(raw)
2689
3099
  )
2690
3100
  };
2691
3101
  }
2692
3102
 
2693
3103
  // src/me-offline/client.ts
2694
- var import_zod12 = require("zod");
2695
- var Hex64 = import_zod12.z.string().regex(/^[0-9a-f]{64}$/i);
2696
- var HexAny = import_zod12.z.string().regex(/^[0-9a-f]+$/i);
2697
- var Sha256Hex = import_zod12.z.string().regex(/^[0-9a-f]{64}$/i);
2698
- var RegisterDeviceKeyInputSchema = import_zod12.z.object({
2699
- deviceId: import_zod12.z.string().min(1).max(128),
3104
+ var import_zod13 = require("zod");
3105
+ var Hex64 = import_zod13.z.string().regex(/^[0-9a-f]{64}$/i);
3106
+ var HexAny = import_zod13.z.string().regex(/^[0-9a-f]+$/i);
3107
+ var Sha256Hex = import_zod13.z.string().regex(/^[0-9a-f]{64}$/i);
3108
+ var RegisterDeviceKeyInputSchema = import_zod13.z.object({
3109
+ deviceId: import_zod13.z.string().min(1).max(128),
2700
3110
  publicKeyHex: Hex64
2701
3111
  });
2702
- var DeviceKeyRecordSchema = import_zod12.z.object({
2703
- id: import_zod12.z.string().uuid(),
2704
- userId: import_zod12.z.string().uuid(),
2705
- deviceId: import_zod12.z.string(),
3112
+ var DeviceKeyRecordSchema = import_zod13.z.object({
3113
+ id: import_zod13.z.string().uuid(),
3114
+ userId: import_zod13.z.string().uuid(),
3115
+ deviceId: import_zod13.z.string(),
2706
3116
  publicKeyHex: Hex64,
2707
- createdAtMs: import_zod12.z.number().int().nonnegative(),
2708
- revokedAtMs: import_zod12.z.number().int().nonnegative().nullable()
3117
+ createdAtMs: import_zod13.z.number().int().nonnegative(),
3118
+ revokedAtMs: import_zod13.z.number().int().nonnegative().nullable()
2709
3119
  });
2710
- var ConsumerOACSchema = import_zod12.z.object({
2711
- oacId: import_zod12.z.string().uuid(),
2712
- issuerId: import_zod12.z.string().min(1).max(64),
2713
- userId: import_zod12.z.string().uuid(),
2714
- deviceId: import_zod12.z.string().min(1).max(128),
3120
+ var ConsumerOACSchema = import_zod13.z.object({
3121
+ oacId: import_zod13.z.string().uuid(),
3122
+ issuerId: import_zod13.z.string().min(1).max(64),
3123
+ userId: import_zod13.z.string().uuid(),
3124
+ deviceId: import_zod13.z.string().min(1).max(128),
2715
3125
  devicePubkeyHex: Hex64,
2716
- perTxCapKobo: import_zod12.z.number().int().positive(),
2717
- cumulativeCapKobo: import_zod12.z.number().int().positive(),
2718
- currency: import_zod12.z.string().length(3),
2719
- validFromMs: import_zod12.z.number().int().nonnegative(),
2720
- validUntilMs: import_zod12.z.number().int().nonnegative(),
2721
- counterSeed: import_zod12.z.number().int().nonnegative(),
2722
- issuedAtMs: import_zod12.z.number().int().nonnegative()
2723
- });
2724
- var SignedConsumerOACSchema = import_zod12.z.object({
3126
+ perTxCapKobo: import_zod13.z.number().int().positive(),
3127
+ cumulativeCapKobo: import_zod13.z.number().int().positive(),
3128
+ currency: import_zod13.z.string().length(3),
3129
+ validFromMs: import_zod13.z.number().int().nonnegative(),
3130
+ validUntilMs: import_zod13.z.number().int().nonnegative(),
3131
+ counterSeed: import_zod13.z.number().int().nonnegative(),
3132
+ issuedAtMs: import_zod13.z.number().int().nonnegative()
3133
+ });
3134
+ var SignedConsumerOACSchema = import_zod13.z.object({
2725
3135
  oac: ConsumerOACSchema,
2726
3136
  issuerSig: HexAny,
2727
3137
  issuerPublicKeyHex: Hex64
2728
3138
  });
2729
3139
  var OACRecordSchema = SignedConsumerOACSchema.extend({
2730
- currentOfflineSpentKobo: import_zod12.z.number().int().nonnegative(),
2731
- status: import_zod12.z.enum([
3140
+ currentOfflineSpentKobo: import_zod13.z.number().int().nonnegative(),
3141
+ status: import_zod13.z.enum([
2732
3142
  "active",
2733
3143
  "superseded",
2734
3144
  "expired",
@@ -2737,43 +3147,43 @@ var OACRecordSchema = SignedConsumerOACSchema.extend({
2737
3147
  "draining",
2738
3148
  "closed"
2739
3149
  ]),
2740
- supersededAtMs: import_zod12.z.number().int().nonnegative().nullable(),
2741
- revokedAtMs: import_zod12.z.number().int().nonnegative().nullable(),
2742
- holdId: import_zod12.z.string().uuid().nullable().optional()
2743
- });
2744
- var IssueOACInputSchema = import_zod12.z.object({
2745
- deviceId: import_zod12.z.string().min(1).max(128),
2746
- perTxCapKobo: import_zod12.z.number().int().positive().optional(),
2747
- cumulativeCapKobo: import_zod12.z.number().int().positive().optional(),
2748
- ttlMs: import_zod12.z.number().int().min(6e4).max(1e3 * 60 * 60 * 24 * 7).optional(),
2749
- spendableOnlineKobo: import_zod12.z.number().int().nonnegative().optional()
2750
- });
2751
- var EnableOfflineInputSchema = import_zod12.z.object({
2752
- deviceId: import_zod12.z.string().min(1).max(128),
2753
- amountKobo: import_zod12.z.number().int().positive(),
2754
- perTxCapKobo: import_zod12.z.number().int().positive().optional(),
2755
- ttlMs: import_zod12.z.number().int().min(6e4).max(1e3 * 60 * 60 * 24 * 7).optional(),
2756
- installId: import_zod12.z.string().min(1).max(128),
2757
- partnerId: import_zod12.z.string().min(1).max(64).optional()
2758
- });
2759
- var DisableOfflineInputSchema = import_zod12.z.object({
2760
- deviceId: import_zod12.z.string().min(1).max(128),
2761
- installId: import_zod12.z.string().min(1).max(128).optional(),
2762
- claims: import_zod12.z.array(import_zod12.z.unknown()).max(256).optional()
2763
- });
2764
- var OfflineHoldRecordSchema = import_zod12.z.object({
2765
- holdId: import_zod12.z.string().uuid(),
2766
- userId: import_zod12.z.string().uuid(),
2767
- deviceId: import_zod12.z.string(),
2768
- partnerId: import_zod12.z.string(),
2769
- adapterKind: import_zod12.z.string(),
2770
- externalHoldRef: import_zod12.z.string().nullable(),
2771
- amountKobo: import_zod12.z.number().int().nonnegative(),
2772
- capturedKobo: import_zod12.z.number().int().nonnegative(),
2773
- releasedKobo: import_zod12.z.number().int().nonnegative(),
2774
- remainingKobo: import_zod12.z.number().int().nonnegative(),
2775
- currency: import_zod12.z.string().length(3),
2776
- status: import_zod12.z.enum([
3150
+ supersededAtMs: import_zod13.z.number().int().nonnegative().nullable(),
3151
+ revokedAtMs: import_zod13.z.number().int().nonnegative().nullable(),
3152
+ holdId: import_zod13.z.string().uuid().nullable().optional()
3153
+ });
3154
+ var IssueOACInputSchema = import_zod13.z.object({
3155
+ deviceId: import_zod13.z.string().min(1).max(128),
3156
+ perTxCapKobo: import_zod13.z.number().int().positive().optional(),
3157
+ cumulativeCapKobo: import_zod13.z.number().int().positive().optional(),
3158
+ ttlMs: import_zod13.z.number().int().min(6e4).max(1e3 * 60 * 60 * 24 * 7).optional(),
3159
+ spendableOnlineKobo: import_zod13.z.number().int().nonnegative().optional()
3160
+ });
3161
+ var EnableOfflineInputSchema = import_zod13.z.object({
3162
+ deviceId: import_zod13.z.string().min(1).max(128),
3163
+ amountKobo: import_zod13.z.number().int().positive(),
3164
+ perTxCapKobo: import_zod13.z.number().int().positive().optional(),
3165
+ ttlMs: import_zod13.z.number().int().min(6e4).max(1e3 * 60 * 60 * 24 * 7).optional(),
3166
+ installId: import_zod13.z.string().min(1).max(128),
3167
+ partnerId: import_zod13.z.string().min(1).max(64).optional()
3168
+ });
3169
+ var DisableOfflineInputSchema = import_zod13.z.object({
3170
+ deviceId: import_zod13.z.string().min(1).max(128),
3171
+ installId: import_zod13.z.string().min(1).max(128).optional(),
3172
+ claims: import_zod13.z.array(import_zod13.z.unknown()).max(256).optional()
3173
+ });
3174
+ var OfflineHoldRecordSchema = import_zod13.z.object({
3175
+ holdId: import_zod13.z.string().uuid(),
3176
+ userId: import_zod13.z.string().uuid(),
3177
+ deviceId: import_zod13.z.string(),
3178
+ partnerId: import_zod13.z.string(),
3179
+ adapterKind: import_zod13.z.string(),
3180
+ externalHoldRef: import_zod13.z.string().nullable(),
3181
+ amountKobo: import_zod13.z.number().int().nonnegative(),
3182
+ capturedKobo: import_zod13.z.number().int().nonnegative(),
3183
+ releasedKobo: import_zod13.z.number().int().nonnegative(),
3184
+ remainingKobo: import_zod13.z.number().int().nonnegative(),
3185
+ currency: import_zod13.z.string().length(3),
3186
+ status: import_zod13.z.enum([
2777
3187
  "placing",
2778
3188
  "active",
2779
3189
  "disabling",
@@ -2782,71 +3192,71 @@ var OfflineHoldRecordSchema = import_zod12.z.object({
2782
3192
  "revoked",
2783
3193
  "failed"
2784
3194
  ]),
2785
- installId: import_zod12.z.string().nullable(),
2786
- drainDeadlineMs: import_zod12.z.number().int().nonnegative(),
2787
- disableRequestedAtMs: import_zod12.z.number().int().nonnegative().nullable(),
2788
- createdAtMs: import_zod12.z.number().int().nonnegative(),
2789
- closedAtMs: import_zod12.z.number().int().nonnegative().nullable(),
2790
- isTrusted: import_zod12.z.boolean().optional()
2791
- });
2792
- var EnableOfflineResultSchema = import_zod12.z.object({
3195
+ installId: import_zod13.z.string().nullable(),
3196
+ drainDeadlineMs: import_zod13.z.number().int().nonnegative(),
3197
+ disableRequestedAtMs: import_zod13.z.number().int().nonnegative().nullable(),
3198
+ createdAtMs: import_zod13.z.number().int().nonnegative(),
3199
+ closedAtMs: import_zod13.z.number().int().nonnegative().nullable(),
3200
+ isTrusted: import_zod13.z.boolean().optional()
3201
+ });
3202
+ var EnableOfflineResultSchema = import_zod13.z.object({
2793
3203
  hold: OfflineHoldRecordSchema,
2794
3204
  oac: OACRecordSchema
2795
3205
  });
2796
- var DisableOfflineResultSchema = import_zod12.z.object({
3206
+ var DisableOfflineResultSchema = import_zod13.z.object({
2797
3207
  hold: OfflineHoldRecordSchema,
2798
- trusted: import_zod12.z.boolean(),
2799
- settledClaims: import_zod12.z.number().int().nonnegative()
3208
+ trusted: import_zod13.z.boolean(),
3209
+ settledClaims: import_zod13.z.number().int().nonnegative()
2800
3210
  });
2801
- var OfflineStatusResultSchema = import_zod12.z.object({
3211
+ var OfflineStatusResultSchema = import_zod13.z.object({
2802
3212
  hold: OfflineHoldRecordSchema.nullable(),
2803
3213
  active: OACRecordSchema.nullable()
2804
3214
  });
2805
- var OfflineStateResultSchema = import_zod12.z.object({
3215
+ var OfflineStateResultSchema = import_zod13.z.object({
2806
3216
  active: OACRecordSchema.nullable()
2807
3217
  });
2808
- var ConsumerPaymentClaimSchema = import_zod12.z.object({
2809
- oacId: import_zod12.z.string().uuid(),
3218
+ var ConsumerPaymentClaimSchema = import_zod13.z.object({
3219
+ oacId: import_zod13.z.string().uuid(),
2810
3220
  encounterId: Sha256Hex.optional(),
2811
- payerUserId: import_zod12.z.string().uuid(),
2812
- payeeUserId: import_zod12.z.string().uuid(),
2813
- payerDeviceId: import_zod12.z.string().min(1).max(128),
2814
- payerNonce: import_zod12.z.string().min(8).max(128),
2815
- payeeNonce: import_zod12.z.string().min(8).max(128),
2816
- amountKobo: import_zod12.z.number().int().positive(),
2817
- currency: import_zod12.z.string().length(3).default("NGN"),
2818
- occurredAtMs: import_zod12.z.number().int().nonnegative(),
2819
- completedAtMs: import_zod12.z.number().int().nonnegative().optional(),
2820
- contextId: import_zod12.z.string().max(128).optional(),
3221
+ payerUserId: import_zod13.z.string().uuid(),
3222
+ payeeUserId: import_zod13.z.string().uuid(),
3223
+ payerDeviceId: import_zod13.z.string().min(1).max(128),
3224
+ payerNonce: import_zod13.z.string().min(8).max(128),
3225
+ payeeNonce: import_zod13.z.string().min(8).max(128),
3226
+ amountKobo: import_zod13.z.number().int().positive(),
3227
+ currency: import_zod13.z.string().length(3).default("NGN"),
3228
+ occurredAtMs: import_zod13.z.number().int().nonnegative(),
3229
+ completedAtMs: import_zod13.z.number().int().nonnegative().optional(),
3230
+ contextId: import_zod13.z.string().max(128).optional(),
2821
3231
  payerPubkeyHex: Hex64,
2822
3232
  payerSignature: HexAny,
2823
3233
  payeePubkeyHex: Hex64.optional(),
2824
3234
  payeeSignature: HexAny.optional()
2825
3235
  });
2826
- var ConsumerSettlementSchema = import_zod12.z.object({
2827
- settlementId: import_zod12.z.string().uuid(),
3236
+ var ConsumerSettlementSchema = import_zod13.z.object({
3237
+ settlementId: import_zod13.z.string().uuid(),
2828
3238
  settlementKey: Sha256Hex,
2829
3239
  encounterId: Sha256Hex,
2830
- oacId: import_zod12.z.string().uuid(),
2831
- payerUserId: import_zod12.z.string().uuid(),
2832
- payeeUserId: import_zod12.z.string().uuid(),
2833
- amountKobo: import_zod12.z.number().int().positive(),
2834
- currency: import_zod12.z.string().length(3),
2835
- status: import_zod12.z.enum(["SETTLED", "REVIEW"]),
2836
- reviewReason: import_zod12.z.string().nullable(),
2837
- ledgerRef: import_zod12.z.string().nullable(),
3240
+ oacId: import_zod13.z.string().uuid(),
3241
+ payerUserId: import_zod13.z.string().uuid(),
3242
+ payeeUserId: import_zod13.z.string().uuid(),
3243
+ amountKobo: import_zod13.z.number().int().positive(),
3244
+ currency: import_zod13.z.string().length(3),
3245
+ status: import_zod13.z.enum(["SETTLED", "REVIEW"]),
3246
+ reviewReason: import_zod13.z.string().nullable(),
3247
+ ledgerRef: import_zod13.z.string().nullable(),
2838
3248
  issuerSig: HexAny,
2839
- createdAtMs: import_zod12.z.number().int().nonnegative()
3249
+ createdAtMs: import_zod13.z.number().int().nonnegative()
2840
3250
  });
2841
- var ConsumerSettleResultSchema = import_zod12.z.object({
3251
+ var ConsumerSettleResultSchema = import_zod13.z.object({
2842
3252
  settlement: ConsumerSettlementSchema,
2843
3253
  encounterId: Sha256Hex,
2844
- replayed: import_zod12.z.boolean()
3254
+ replayed: import_zod13.z.boolean()
2845
3255
  });
2846
- var RevokeDeviceKeyInputSchema = import_zod12.z.object({
2847
- deviceId: import_zod12.z.string().min(1).max(128),
3256
+ var RevokeDeviceKeyInputSchema = import_zod13.z.object({
3257
+ deviceId: import_zod13.z.string().min(1).max(128),
2848
3258
  /** Step-up token from /api/v1/auth/send/verify with purpose='offline_revoke'. */
2849
- sendAuthToken: import_zod12.z.string().min(16)
3259
+ sendAuthToken: import_zod13.z.string().min(16)
2850
3260
  });
2851
3261
  function createMeOfflineClient(opts) {
2852
3262
  const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
@@ -2879,7 +3289,7 @@ function createMeOfflineClient(opts) {
2879
3289
  }
2880
3290
  return parser(raw);
2881
3291
  }
2882
- const deviceKeyItems = import_zod12.z.object({ items: import_zod12.z.array(DeviceKeyRecordSchema) });
3292
+ const deviceKeyItems = import_zod13.z.object({ items: import_zod13.z.array(DeviceKeyRecordSchema) });
2883
3293
  return {
2884
3294
  registerDeviceKey: (input) => call(
2885
3295
  "POST",
@@ -2943,6 +3353,320 @@ function createMeOfflineClient(opts) {
2943
3353
  )
2944
3354
  };
2945
3355
  }
3356
+
3357
+ // src/partner-funding/client.ts
3358
+ var import_zod14 = require("zod");
3359
+ var MinorString = import_zod14.z.string().regex(/^-?\d+$/);
3360
+ var PositiveMinor = import_zod14.z.union([
3361
+ import_zod14.z.number().int().positive(),
3362
+ import_zod14.z.string().regex(/^[1-9]\d{0,18}$/)
3363
+ ]);
3364
+ var Currency = import_zod14.z.string().trim().length(3).transform((v) => v.toUpperCase());
3365
+ var Metadata = import_zod14.z.record(import_zod14.z.unknown());
3366
+ var PARTNER_KINDS = ["bank", "merchant"];
3367
+ var CUSTODIAL_MODES = ["agent_of_bank", "flur_virtual_pool"];
3368
+ var PARTNER_PROFILE_STATUSES = [
3369
+ "active",
3370
+ "suspended",
3371
+ "closed"
3372
+ ];
3373
+ var PARTNER_FUNDING_DIRECTIONS = ["credit", "debit"];
3374
+ var PARTNER_FUNDING_STATUSES = [
3375
+ "pending",
3376
+ "posted",
3377
+ "failed"
3378
+ ];
3379
+ var PAYOUT_DESTINATION_STATUSES = [
3380
+ "pending",
3381
+ "verified",
3382
+ "disabled"
3383
+ ];
3384
+ var WITHDRAWAL_STATES = [
3385
+ "requested",
3386
+ "submitted",
3387
+ "processing",
3388
+ "paid",
3389
+ "failed",
3390
+ "reversed"
3391
+ ];
3392
+ var PartnerProfileSchema = import_zod14.z.object({
3393
+ partnerAccountId: import_zod14.z.string().uuid(),
3394
+ kind: import_zod14.z.enum(PARTNER_KINDS),
3395
+ custodialMode: import_zod14.z.enum(CUSTODIAL_MODES),
3396
+ displayName: import_zod14.z.string(),
3397
+ bankCode: import_zod14.z.string().nullable(),
3398
+ poolAccountNumber: import_zod14.z.string().nullable(),
3399
+ status: import_zod14.z.enum(PARTNER_PROFILE_STATUSES),
3400
+ metadata: Metadata,
3401
+ createdAtMs: import_zod14.z.number().int().nonnegative(),
3402
+ updatedAtMs: import_zod14.z.number().int().nonnegative()
3403
+ });
3404
+ var UpsertPartnerProfileInputSchema = import_zod14.z.object({
3405
+ kind: import_zod14.z.enum(PARTNER_KINDS),
3406
+ custodialMode: import_zod14.z.enum(CUSTODIAL_MODES),
3407
+ displayName: import_zod14.z.string().trim().min(1).max(200),
3408
+ bankCode: import_zod14.z.string().trim().min(1).max(64).optional(),
3409
+ poolAccountNumber: import_zod14.z.string().trim().min(1).max(64).optional(),
3410
+ metadata: Metadata.optional()
3411
+ });
3412
+ var PartnerFundingEventInputSchema = import_zod14.z.object({
3413
+ externalRef: import_zod14.z.string().trim().min(8).max(128),
3414
+ direction: import_zod14.z.enum(PARTNER_FUNDING_DIRECTIONS).optional(),
3415
+ userId: import_zod14.z.string().uuid().optional(),
3416
+ accountId: import_zod14.z.string().uuid().optional(),
3417
+ amountMinor: PositiveMinor,
3418
+ currency: Currency,
3419
+ fundingSource: import_zod14.z.string().trim().min(1).max(64).optional(),
3420
+ providerMetadata: Metadata.optional()
3421
+ });
3422
+ var PartnerFundingSchema = import_zod14.z.object({
3423
+ fundingId: import_zod14.z.string().uuid(),
3424
+ partnerId: import_zod14.z.string().uuid(),
3425
+ accountId: import_zod14.z.string().uuid(),
3426
+ userId: import_zod14.z.string().uuid().nullable(),
3427
+ direction: import_zod14.z.enum(PARTNER_FUNDING_DIRECTIONS),
3428
+ currency: import_zod14.z.string(),
3429
+ amountMinor: MinorString,
3430
+ externalRef: import_zod14.z.string(),
3431
+ status: import_zod14.z.enum(PARTNER_FUNDING_STATUSES),
3432
+ fundingSource: import_zod14.z.string(),
3433
+ ledgerRef: import_zod14.z.string(),
3434
+ providerMetadata: Metadata,
3435
+ createdAtMs: import_zod14.z.number().int().nonnegative(),
3436
+ updatedAtMs: import_zod14.z.number().int().nonnegative()
3437
+ });
3438
+ var IngestFundingResultSchema = import_zod14.z.object({
3439
+ funding: PartnerFundingSchema,
3440
+ replayed: import_zod14.z.boolean()
3441
+ });
3442
+ var PayoutDestinationSchema = import_zod14.z.object({
3443
+ destinationId: import_zod14.z.string().uuid(),
3444
+ accountId: import_zod14.z.string().uuid(),
3445
+ partnerId: import_zod14.z.string().uuid(),
3446
+ bankCode: import_zod14.z.string(),
3447
+ accountNumber: import_zod14.z.string(),
3448
+ accountName: import_zod14.z.string(),
3449
+ status: import_zod14.z.enum(PAYOUT_DESTINATION_STATUSES),
3450
+ verifiedAtMs: import_zod14.z.number().int().nonnegative().nullable(),
3451
+ metadata: Metadata,
3452
+ createdAtMs: import_zod14.z.number().int().nonnegative(),
3453
+ updatedAtMs: import_zod14.z.number().int().nonnegative()
3454
+ });
3455
+ var CreatePayoutDestinationInputSchema = import_zod14.z.object({
3456
+ partnerId: import_zod14.z.string().uuid(),
3457
+ bankCode: import_zod14.z.string().trim().min(1).max(32),
3458
+ accountNumber: import_zod14.z.string().trim().min(4).max(64),
3459
+ accountName: import_zod14.z.string().trim().min(1).max(200),
3460
+ metadata: Metadata.optional()
3461
+ });
3462
+ var ListPayoutDestinationsResultSchema = import_zod14.z.object({
3463
+ items: import_zod14.z.array(PayoutDestinationSchema)
3464
+ });
3465
+ var WithdrawalSchema = import_zod14.z.object({
3466
+ withdrawalId: import_zod14.z.string().uuid(),
3467
+ accountId: import_zod14.z.string().uuid(),
3468
+ userId: import_zod14.z.string().uuid(),
3469
+ partnerId: import_zod14.z.string().uuid(),
3470
+ destinationId: import_zod14.z.string().uuid(),
3471
+ currency: import_zod14.z.string(),
3472
+ amountMinor: MinorString,
3473
+ state: import_zod14.z.enum(WITHDRAWAL_STATES),
3474
+ idempotencyKey: import_zod14.z.string(),
3475
+ providerRef: import_zod14.z.string().nullable(),
3476
+ lastError: import_zod14.z.string().nullable(),
3477
+ ledgerRef: import_zod14.z.string(),
3478
+ reverseLedgerRef: import_zod14.z.string().nullable(),
3479
+ metadata: Metadata,
3480
+ createdAtMs: import_zod14.z.number().int().nonnegative(),
3481
+ updatedAtMs: import_zod14.z.number().int().nonnegative()
3482
+ });
3483
+ var CreateWithdrawalInputSchema = import_zod14.z.object({
3484
+ destinationId: import_zod14.z.string().uuid(),
3485
+ amountMinor: PositiveMinor,
3486
+ currency: Currency,
3487
+ idempotencyKey: import_zod14.z.string().trim().min(8).max(128),
3488
+ metadata: Metadata.optional()
3489
+ });
3490
+ var CreateWithdrawalResultSchema = import_zod14.z.object({
3491
+ withdrawal: WithdrawalSchema,
3492
+ replayed: import_zod14.z.boolean()
3493
+ });
3494
+ var PayoutEventInputSchema = import_zod14.z.object({
3495
+ externalRef: import_zod14.z.string().trim().min(8).max(128),
3496
+ withdrawalId: import_zod14.z.string().uuid().optional(),
3497
+ state: import_zod14.z.enum(["submitted", "processing", "paid", "failed"]),
3498
+ providerRef: import_zod14.z.string().trim().min(1).max(128).optional(),
3499
+ failureCode: import_zod14.z.string().trim().max(64).optional(),
3500
+ failureMessage: import_zod14.z.string().trim().max(512).optional(),
3501
+ providerMetadata: Metadata.optional()
3502
+ });
3503
+ var RecordPayoutEventResultSchema = import_zod14.z.object({
3504
+ withdrawal: WithdrawalSchema,
3505
+ replayed: import_zod14.z.boolean()
3506
+ });
3507
+ var ReconciliationReportSchema = import_zod14.z.object({
3508
+ partnerId: import_zod14.z.string().uuid(),
3509
+ currency: import_zod14.z.string(),
3510
+ fromMs: import_zod14.z.number().int().nonnegative(),
3511
+ toMs: import_zod14.z.number().int().nonnegative(),
3512
+ fundingsCreditMinor: MinorString,
3513
+ fundingsDebitMinor: MinorString,
3514
+ withdrawalsPaidMinor: MinorString,
3515
+ withdrawalsReversedMinor: MinorString,
3516
+ withdrawalsInFlightMinor: MinorString,
3517
+ expectedReserveBalanceMinor: MinorString,
3518
+ actualReserveBalanceMinor: MinorString,
3519
+ imbalanceMinor: MinorString,
3520
+ generatedAtMs: import_zod14.z.number().int().nonnegative()
3521
+ });
3522
+ function createPartnerFundingClient(partner) {
3523
+ return {
3524
+ ingestFunding: async (input) => {
3525
+ const body = PartnerFundingEventInputSchema.parse(input);
3526
+ const raw = await partner.request({
3527
+ method: "POST",
3528
+ path: "/v1/partners/fundings",
3529
+ body
3530
+ });
3531
+ return IngestFundingResultSchema.parse(raw);
3532
+ },
3533
+ recordPayoutEvent: async (input) => {
3534
+ const body = PayoutEventInputSchema.parse(input);
3535
+ const raw = await partner.request({
3536
+ method: "POST",
3537
+ path: "/v1/partners/payouts/events",
3538
+ body
3539
+ });
3540
+ return RecordPayoutEventResultSchema.parse(raw);
3541
+ },
3542
+ reconciliation: async (input) => {
3543
+ const qs = new URLSearchParams({
3544
+ currency: input.currency
3545
+ });
3546
+ if (typeof input.fromMs === "number")
3547
+ qs.set("fromMs", String(input.fromMs));
3548
+ if (typeof input.toMs === "number") qs.set("toMs", String(input.toMs));
3549
+ const raw = await partner.request({
3550
+ method: "GET",
3551
+ path: `/v1/partners/reconciliation/daily?${qs.toString()}`
3552
+ });
3553
+ return ReconciliationReportSchema.parse(raw);
3554
+ }
3555
+ };
3556
+ }
3557
+ function createConsumerWithdrawalsClient(opts) {
3558
+ const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
3559
+ if (!fetchImpl) {
3560
+ throw new Error(
3561
+ "createConsumerWithdrawalsClient: no fetch implementation available"
3562
+ );
3563
+ }
3564
+ const baseUrl = opts.baseUrl.replace(/\/$/, "");
3565
+ async function call(method, path, body, parser) {
3566
+ const init2 = {
3567
+ method,
3568
+ headers: { accept: "application/json" }
3569
+ };
3570
+ if (body !== void 0) {
3571
+ init2.body = JSON.stringify(body);
3572
+ init2.headers = { ...init2.headers, "content-type": "application/json" };
3573
+ }
3574
+ const resp = await fetchImpl(`${baseUrl}${path}`, init2);
3575
+ const text = await resp.text();
3576
+ let raw;
3577
+ if (text) {
3578
+ try {
3579
+ raw = JSON.parse(text);
3580
+ } catch {
3581
+ raw = text;
3582
+ }
3583
+ }
3584
+ if (!resp.ok) {
3585
+ const code = raw && typeof raw === "object" && "code" in raw && typeof raw.code === "string" ? raw.code : `http_${resp.status}`;
3586
+ const message = raw && typeof raw === "object" && "message" in raw && typeof raw.message === "string" ? raw.message : `request failed with status ${resp.status}`;
3587
+ throw new FlurApiError(resp.status, code, message, raw);
3588
+ }
3589
+ return parser(raw);
3590
+ }
3591
+ return {
3592
+ listDestinations: () => call(
3593
+ "GET",
3594
+ "/v1/me/payout-destinations",
3595
+ void 0,
3596
+ (raw) => ListPayoutDestinationsResultSchema.parse(raw)
3597
+ ),
3598
+ createDestination: (input) => call(
3599
+ "POST",
3600
+ "/v1/me/payout-destinations",
3601
+ CreatePayoutDestinationInputSchema.parse(input),
3602
+ (raw) => PayoutDestinationSchema.parse(raw)
3603
+ ),
3604
+ verifyDestination: (destinationId) => call(
3605
+ "POST",
3606
+ `/v1/me/payout-destinations/${encodeURIComponent(destinationId)}/verify`,
3607
+ {},
3608
+ (raw) => PayoutDestinationSchema.parse(raw)
3609
+ ),
3610
+ disableDestination: (destinationId) => call(
3611
+ "POST",
3612
+ `/v1/me/payout-destinations/${encodeURIComponent(destinationId)}/disable`,
3613
+ {},
3614
+ (raw) => PayoutDestinationSchema.parse(raw)
3615
+ ),
3616
+ createWithdrawal: (input) => call(
3617
+ "POST",
3618
+ "/v1/me/withdrawals",
3619
+ CreateWithdrawalInputSchema.parse(input),
3620
+ (raw) => CreateWithdrawalResultSchema.parse(raw)
3621
+ ),
3622
+ getWithdrawal: (withdrawalId) => call(
3623
+ "GET",
3624
+ `/v1/me/withdrawals/${encodeURIComponent(withdrawalId)}`,
3625
+ void 0,
3626
+ (raw) => WithdrawalSchema.parse(raw)
3627
+ )
3628
+ };
3629
+ }
3630
+ function createPartnerProfileAdminClient(opts) {
3631
+ const fetchImpl = opts.fetchImpl ?? globalThis.fetch;
3632
+ if (!fetchImpl) {
3633
+ throw new Error(
3634
+ "createPartnerProfileAdminClient: no fetch implementation available"
3635
+ );
3636
+ }
3637
+ const baseUrl = opts.baseUrl.replace(/\/$/, "");
3638
+ return {
3639
+ upsertProfile: async (partnerAccountId, input) => {
3640
+ const body = {
3641
+ partnerAccountId,
3642
+ ...UpsertPartnerProfileInputSchema.parse(input)
3643
+ };
3644
+ const resp = await fetchImpl(`${baseUrl}/v1/partners/profile`, {
3645
+ method: "POST",
3646
+ headers: {
3647
+ "content-type": "application/json",
3648
+ accept: "application/json"
3649
+ },
3650
+ body: JSON.stringify(body)
3651
+ });
3652
+ const text = await resp.text();
3653
+ let raw;
3654
+ if (text) {
3655
+ try {
3656
+ raw = JSON.parse(text);
3657
+ } catch {
3658
+ raw = text;
3659
+ }
3660
+ }
3661
+ if (!resp.ok) {
3662
+ const code = raw && typeof raw === "object" && "code" in raw && typeof raw.code === "string" ? raw.code : `http_${resp.status}`;
3663
+ const message = raw && typeof raw === "object" && "message" in raw && typeof raw.message === "string" ? raw.message : `request failed with status ${resp.status}`;
3664
+ throw new FlurApiError(resp.status, code, message, raw);
3665
+ }
3666
+ return PartnerProfileSchema.parse(raw);
3667
+ }
3668
+ };
3669
+ }
2946
3670
  // Annotate the CommonJS export names for ESM import in node:
2947
3671
  0 && (module.exports = {
2948
3672
  ACCOUNT_STATUSES,
@@ -2951,11 +3675,24 @@ function createMeOfflineClient(opts) {
2951
3675
  AccountMembershipSchema,
2952
3676
  AccountSchema,
2953
3677
  ApiCredentialPublicSchema,
3678
+ COLLECTION_INTENT_STATUSES,
3679
+ COLLECTION_PAYMENT_STATUSES,
3680
+ CUSTODIAL_MODES,
3681
+ CollectionIntentSchema,
3682
+ CollectionPaymentResultSchema,
3683
+ CollectionPaymentSchema,
3684
+ CollectionReportSummarySchema,
3685
+ CollectionStatementSchema,
2954
3686
  ConsumerOACRecordSchema,
2955
3687
  ConsumerOACSchema,
2956
3688
  ConsumerPaymentClaimSchema,
2957
3689
  ConsumerSettleResultSchema,
2958
3690
  ConsumerSettlementSchema,
3691
+ CreateCollectionIntentInputSchema,
3692
+ CreatePayoutDestinationInputSchema,
3693
+ CreatePayoutInputSchema,
3694
+ CreateWithdrawalInputSchema,
3695
+ CreateWithdrawalResultSchema,
2959
3696
  DeviceKeyRecordSchema,
2960
3697
  DisableOfflineInputSchema,
2961
3698
  DisableOfflineResultSchema,
@@ -2968,8 +3705,14 @@ function createMeOfflineClient(opts) {
2968
3705
  FlurError,
2969
3706
  FlurExpiredError,
2970
3707
  FlurReplayError,
3708
+ IngestFundingResultSchema,
2971
3709
  IssueOACInputSchema,
3710
+ ListPayoutDestinationsResultSchema,
2972
3711
  MEMBERSHIP_ROLES,
3712
+ MERCHANT_PAYOUT_STATUSES,
3713
+ MERCHANT_PROFILE_STATUSES,
3714
+ MerchantPayoutSchema,
3715
+ MerchantProfileSchema,
2973
3716
  MintedApiCredentialSchema,
2974
3717
  NGN_CURRENCY_CODE,
2975
3718
  NG_COUNTRY_CODE,
@@ -2984,25 +3727,46 @@ function createMeOfflineClient(opts) {
2984
3727
  OfflineStateResultSchema,
2985
3728
  OfflineStatusResultSchema,
2986
3729
  OfflineTokenSchema,
3730
+ PARTNER_FUNDING_DIRECTIONS,
3731
+ PARTNER_FUNDING_STATUSES,
3732
+ PARTNER_KINDS,
3733
+ PARTNER_PROFILE_STATUSES,
2987
3734
  PARTNER_SCOPES,
2988
3735
  PASS_KINDS,
2989
3736
  PASS_STATES,
2990
3737
  PAYLOAD_FORMAT_INDICATOR_VALUE,
3738
+ PAYOUT_DESTINATION_STATUSES,
2991
3739
  POINT_OF_INITIATION,
3740
+ PartnerFundingEventInputSchema,
3741
+ PartnerFundingSchema,
3742
+ PartnerProfileSchema,
2992
3743
  PassMetadataSchema,
2993
3744
  PassSchema,
3745
+ PayCollectionInputSchema,
2994
3746
  PaymentClaimSchema,
3747
+ PayoutDestinationSchema,
3748
+ PayoutEventInputSchema,
3749
+ ProviderEventInputSchema,
3750
+ ProviderEventRecordSchema,
3751
+ PublicCollectionIntentSchema,
2995
3752
  RECEIPT_CHANNELS,
2996
3753
  RECEIPT_KINDS,
2997
3754
  REPLAY_WINDOW_MS,
2998
3755
  ReceiptPayloadSchema,
2999
3756
  ReceiptSchema,
3757
+ ReconciliationReportSchema,
3758
+ RecordPayoutEventResultSchema,
3000
3759
  RedemptionSchema,
3001
3760
  RegisterDeviceKeyInputSchema,
3002
3761
  RevokeDeviceKeyInputSchema,
3762
+ SETTLEMENT_SCHEDULES,
3003
3763
  SettleResponseSchema,
3004
3764
  SettlementSchema,
3005
3765
  SignedConsumerOACSchema,
3766
+ UpsertMerchantProfileInputSchema,
3767
+ UpsertPartnerProfileInputSchema,
3768
+ WITHDRAWAL_STATES,
3769
+ WithdrawalSchema,
3006
3770
  bodySha256Hex,
3007
3771
  buildAuthorization,
3008
3772
  buildOAC,
@@ -3019,10 +3783,16 @@ function createMeOfflineClient(opts) {
3019
3783
  crc16ccittHex,
3020
3784
  createAccountsClient,
3021
3785
  createApiCredentialsAdminClient,
3786
+ createCollectionsClient,
3787
+ createConsumerCollectionsClient,
3788
+ createConsumerWithdrawalsClient,
3022
3789
  createFlurPartnerClient,
3023
3790
  createHmacFetch,
3024
3791
  createMeOfflineClient,
3025
3792
  createOfflineSettlementsClient,
3793
+ createPartnerCollectionsClient,
3794
+ createPartnerFundingClient,
3795
+ createPartnerProfileAdminClient,
3026
3796
  createPassesClient,
3027
3797
  createReceiptsClient,
3028
3798
  decodeAuthorizationQR,