@feelflow/ffid-sdk 5.10.0 → 5.13.0
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/{chunk-IZSL6DI7.cjs → chunk-JFFRO2Q5.cjs} +308 -11
- package/dist/{chunk-OJ3OJTIE.js → chunk-RATTQIKM.js} +304 -12
- package/dist/components/index.cjs +8 -8
- package/dist/components/index.d.cts +1 -1
- package/dist/components/index.d.ts +1 -1
- package/dist/components/index.js +1 -1
- package/dist/{ffid-client-DRjzfAaS.d.cts → ffid-client-BG0Qr86U.d.ts} +228 -71
- package/dist/{ffid-client-gboJROw0.d.ts → ffid-client-C3K3sAqq.d.cts} +228 -71
- package/dist/{index-DSvX4q8E.d.cts → index-C6dnexXf.d.cts} +24 -43
- package/dist/{index-DSvX4q8E.d.ts → index-C6dnexXf.d.ts} +24 -43
- package/dist/index.cjs +56 -36
- package/dist/index.d.cts +266 -4
- package/dist/index.d.ts +266 -4
- package/dist/index.js +2 -2
- package/dist/server/index.cjs +144 -5
- package/dist/server/index.d.cts +3 -3
- package/dist/server/index.d.ts +3 -3
- package/dist/server/index.js +144 -5
- package/dist/server/test/index.d.cts +2 -2
- package/dist/server/test/index.d.ts +2 -2
- package/dist/{types-BYdtyO_2.d.cts → types-BeVl-z12.d.cts} +10 -1
- package/dist/{types-BYdtyO_2.d.ts → types-BeVl-z12.d.ts} +10 -1
- package/dist/webhooks/index.cjs +5 -2
- package/dist/webhooks/index.d.cts +1 -1
- package/dist/webhooks/index.d.ts +1 -1
- package/dist/webhooks/index.js +5 -2
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { F as FFIDSubscriptionStatus, a as FFIDConfig, b as FFIDApiResponse, c as FFIDSessionResponse, d as FFIDRedirectResult, e as FFIDError, f as FFIDSubscriptionCheckResponse, g as FFIDCheckServiceAccessParams, h as FFIDServiceAccessDecision, i as FFIDProfileCallOptions, j as FFIDUserProfile, k as FFIDUpdateUserProfileRequest, l as FFIDAnalyticsConfig, m as
|
|
2
|
-
export {
|
|
1
|
+
import { F as FFIDSubscriptionStatus, a as FFIDConfig, b as FFIDApiResponse, c as FFIDSessionResponse, d as FFIDRedirectResult, e as FFIDError, f as FFIDSubscriptionCheckResponse, g as FFIDCheckServiceAccessParams, h as FFIDServiceAccessDecision, i as FFIDProfileCallOptions, j as FFIDUserProfile, k as FFIDUpdateUserProfileRequest, l as FFIDAnalyticsConfig, m as FFIDVerifyAccessTokenOptions, n as FFIDOAuthUserInfo, o as FFIDInquiryCreateParams, p as FFIDInquiryCreateResponse, q as FFIDAuthMode, r as FFIDLogger, s as FFIDCacheAdapter, t as FFIDUser, u as FFIDOrganization, v as FFIDSubscription, w as FFIDSubscriptionContextValue, E as EffectiveSubscriptionStatus, x as FFIDOAuthUserInfoSubscription, y as FFIDAnnouncementsClientConfig, L as ListAnnouncementsOptions, z as FFIDAnnouncementsApiResponse, A as AnnouncementListResponse, B as FFIDAnnouncementsLogger } from './index-C6dnexXf.js';
|
|
2
|
+
export { C as Announcement, D as AnnouncementStatus, G as AnnouncementType, H as EFFECTIVE_SUBSCRIPTION_STATUSES, I as FFIDAnnouncementBadge, J as FFIDAnnouncementList, K as FFIDAnnouncementsError, M as FFIDAnnouncementsErrorCode, N as FFIDAnnouncementsServerResponse, O as FFIDCacheConfig, P as FFIDContextValue, Q as FFIDInquiryCategory, R as FFIDInquiryCategorySite2026, S as FFIDInquiryForm, T as FFIDInquiryFormCategoryItem, U as FFIDInquiryFormClassNames, V as FFIDInquiryFormLegalLayout, W as FFIDInquiryFormOrganization, X as FFIDInquiryFormPlaceholderContext, Y as FFIDInquiryFormPrefill, Z as FFIDInquiryFormProps, _ as FFIDInquiryFormSubmitData, $ as FFIDInquiryFormSubmitResult, a0 as FFIDJwtClaims, a1 as FFIDLoginButton, a2 as FFIDOAuthTokenResponse, a3 as FFIDOAuthUserInfoMemberRole, a4 as FFIDOrganizationSwitcher, a5 as FFIDRedirectErrorCode, a6 as FFIDSeatModel, a7 as FFIDServiceAccessDenialReason, a8 as FFIDServiceAccessFailPolicy, a9 as FFIDSubscriptionBadge, aa as FFIDTokenIntrospectionResponse, ab as FFIDUserMenu, ac as FFID_INQUIRY_CATEGORIES, ad as FFID_INQUIRY_CATEGORIES_SITE_2026, ae as UseFFIDAnnouncementsOptions, af as UseFFIDAnnouncementsReturn, ag as isFFIDInquiryCategorySite2026, ah as useFFIDAnnouncements } from './index-C6dnexXf.js';
|
|
3
3
|
export { A as ALL_DENIED_EXCEPT_NECESSARY, i as CONSENT_COOKIE_NAME, j as CONSENT_DISMISSAL_TIMESTAMP_KEY, l as COOKIE_VERSION, D as DEFAULT_CONSENT_ERROR_MESSAGES, o as FFIDAnalyticsProvider, p as FFIDAnalyticsProviderProps, c as FFIDConsentCategories, r as FFIDConsentCategoryCode, e as FFIDConsentCategoryMetadata, w as FFIDConsentError, x as FFIDConsentErrorCode, y as FFIDConsentMergeStrategy, B as FFIDConsentMergeWarning, E as FFIDConsentMergeWarningEvent, F as FFIDConsentResult, I as FFIDConsentSource, a as FFIDConsentState, d as FFIDConsentSyncResult, M as FFIDCookieBanner, N as FFIDCookieBannerClassNames, O as FFIDCookieBannerProps, Q as FFIDCookieLink, R as FFIDCookieLinkProps, f as FFIDCookiePolicy, T as FFIDCookieSettings, U as FFIDCookieSettingsClassNames, V as FFIDCookieSettingsProps, _ as FFID_CONSENT_ERROR_CODES, ae as UseFFIDConsentPreferencesReturn, af as UseFFIDConsentReturn, ag as clearConsentDismissalTimestamp, aj as decodeConsentCookie, al as encodeConsentCookie, an as readConsentCookie, ao as readConsentDismissalTimestamp, aq as useFFIDConsent, ar as useFFIDConsentPreferences, as as writeConsentCookie, at as writeConsentDismissalTimestamp } from './FFIDCookieLink-D1WwE_ZO.js';
|
|
4
4
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
5
5
|
import { ReactNode, ComponentType, FC } from 'react';
|
|
@@ -122,6 +122,81 @@ declare function storeCodeVerifier(verifier: string, logger?: PKCELogger): boole
|
|
|
122
122
|
*/
|
|
123
123
|
declare function retrieveCodeVerifier(logger?: PKCELogger): string | null;
|
|
124
124
|
|
|
125
|
+
/** Logger interface matching FFIDLogger for optional warning output */
|
|
126
|
+
interface StateLogger {
|
|
127
|
+
warn: (...args: unknown[]) => void;
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* Store the OAuth `state` for later retrieval.
|
|
131
|
+
*
|
|
132
|
+
* Writes to both sessionStorage (primary) and localStorage (fallback for iOS
|
|
133
|
+
* WebKit sessionStorage eviction during external OAuth bounces). Returns true
|
|
134
|
+
* if at least one write succeeded.
|
|
135
|
+
*
|
|
136
|
+
* @param state - The OAuth state value to store
|
|
137
|
+
* @param logger - Optional logger for warning on storage failure
|
|
138
|
+
* @returns true if stored in at least one storage, false otherwise
|
|
139
|
+
*/
|
|
140
|
+
declare function storeState(state: string, logger?: StateLogger): boolean;
|
|
141
|
+
/**
|
|
142
|
+
* Retrieve and remove the OAuth `state`.
|
|
143
|
+
*
|
|
144
|
+
* Reads from sessionStorage first, falls back to localStorage (with 5-minute TTL).
|
|
145
|
+
* Removes from all storages after retrieval (one-time use). Returns null if no
|
|
146
|
+
* state is stored, the fallback is stale (>5 min), or storage is unavailable.
|
|
147
|
+
*
|
|
148
|
+
* @param logger - Optional logger for warning on storage failure
|
|
149
|
+
*/
|
|
150
|
+
declare function retrieveState(logger?: StateLogger): string | null;
|
|
151
|
+
|
|
152
|
+
declare function cleanupStateStorage(logger?: StateLogger): void;
|
|
153
|
+
|
|
154
|
+
/**
|
|
155
|
+
* Billing checkout / portal session types.
|
|
156
|
+
*
|
|
157
|
+
* types/index.ts のサイズ上限対応で切り出し(中身は逐語移設、#3787 Phase A)。
|
|
158
|
+
*/
|
|
159
|
+
/**
|
|
160
|
+
* Checkout session response from billing checkout endpoint
|
|
161
|
+
*/
|
|
162
|
+
interface FFIDCheckoutSessionResponse {
|
|
163
|
+
/** Stripe Checkout session ID */
|
|
164
|
+
sessionId: string;
|
|
165
|
+
/** Stripe Checkout session URL (null if session creation had issues) */
|
|
166
|
+
url: string | null;
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Portal session response from billing portal endpoint
|
|
170
|
+
*/
|
|
171
|
+
interface FFIDPortalSessionResponse {
|
|
172
|
+
/** Stripe Billing Portal URL */
|
|
173
|
+
url: string;
|
|
174
|
+
}
|
|
175
|
+
/**
|
|
176
|
+
* Parameters for creating a checkout session
|
|
177
|
+
*/
|
|
178
|
+
interface FFIDCreateCheckoutParams {
|
|
179
|
+
/** Organization ID (UUID) */
|
|
180
|
+
organizationId: string;
|
|
181
|
+
/** Subscription ID (UUID) */
|
|
182
|
+
subscriptionId: string;
|
|
183
|
+
/** URL to redirect after successful checkout */
|
|
184
|
+
successUrl: string;
|
|
185
|
+
/** URL to redirect after cancelled checkout */
|
|
186
|
+
cancelUrl: string;
|
|
187
|
+
/** Optional plan ID for upgrade or resubscription */
|
|
188
|
+
planId?: string;
|
|
189
|
+
}
|
|
190
|
+
/**
|
|
191
|
+
* Parameters for creating a billing portal session
|
|
192
|
+
*/
|
|
193
|
+
interface FFIDCreatePortalParams {
|
|
194
|
+
/** Organization ID (UUID) */
|
|
195
|
+
organizationId: string;
|
|
196
|
+
/** URL to redirect when user exits the portal */
|
|
197
|
+
returnUrl: string;
|
|
198
|
+
}
|
|
199
|
+
|
|
125
200
|
/** Billing interval for subscriptions */
|
|
126
201
|
type FFIDBillingInterval = 'monthly' | 'yearly';
|
|
127
202
|
/**
|
|
@@ -489,6 +564,122 @@ interface FFIDRemoveMemberResponse {
|
|
|
489
564
|
message: string;
|
|
490
565
|
}
|
|
491
566
|
|
|
567
|
+
/**
|
|
568
|
+
* Contract resource types (#3787 Phase A)
|
|
569
|
+
*
|
|
570
|
+
* シート割り当て・請求書・支払い再試行の ext API 型。
|
|
571
|
+
* サーバー側の sanitize 済みレスポンス(Stripe 内部 ID を含まない)と対になる。
|
|
572
|
+
*/
|
|
573
|
+
/** シート割り当て 1 件(ユーザー情報付き、一覧用) */
|
|
574
|
+
interface FFIDSeatAssignmentWithUser {
|
|
575
|
+
userId: string;
|
|
576
|
+
email: string;
|
|
577
|
+
name: string | null;
|
|
578
|
+
role: string;
|
|
579
|
+
assignedAt: string;
|
|
580
|
+
assignedBy: string | null;
|
|
581
|
+
}
|
|
582
|
+
/** シート割り当てレコード(割り当て直後のレスポンス用) */
|
|
583
|
+
interface FFIDSeatAssignmentRecord {
|
|
584
|
+
id: string;
|
|
585
|
+
subscriptionId: string;
|
|
586
|
+
userId: string;
|
|
587
|
+
assignedBy: string | null;
|
|
588
|
+
assignedAt: string;
|
|
589
|
+
createdAt: string;
|
|
590
|
+
updatedAt: string;
|
|
591
|
+
}
|
|
592
|
+
/** GET /api/v1/subscriptions/ext/{id}/seats/assignments のレスポンス */
|
|
593
|
+
interface FFIDListSeatAssignmentsResponse {
|
|
594
|
+
assignments: FFIDSeatAssignmentWithUser[];
|
|
595
|
+
totalSeats: number;
|
|
596
|
+
assignedSeats: number;
|
|
597
|
+
availableSeats: number;
|
|
598
|
+
}
|
|
599
|
+
/** listSeatAssignments のパラメータ */
|
|
600
|
+
interface FFIDListSeatAssignmentsParams {
|
|
601
|
+
subscriptionId: string;
|
|
602
|
+
}
|
|
603
|
+
/** assignSeats のパラメータ */
|
|
604
|
+
interface FFIDAssignSeatsParams {
|
|
605
|
+
subscriptionId: string;
|
|
606
|
+
userIds: string[];
|
|
607
|
+
}
|
|
608
|
+
/** POST /api/v1/subscriptions/ext/{id}/seats/assignments のレスポンス */
|
|
609
|
+
interface FFIDAssignSeatsResponse {
|
|
610
|
+
message: string;
|
|
611
|
+
assignments: FFIDSeatAssignmentRecord[];
|
|
612
|
+
}
|
|
613
|
+
/** unassignSeat のパラメータ */
|
|
614
|
+
interface FFIDUnassignSeatParams {
|
|
615
|
+
subscriptionId: string;
|
|
616
|
+
userId: string;
|
|
617
|
+
}
|
|
618
|
+
/** DELETE /api/v1/subscriptions/ext/{id}/seats/assignments/{userId} のレスポンス */
|
|
619
|
+
interface FFIDUnassignSeatResponse {
|
|
620
|
+
message: string;
|
|
621
|
+
}
|
|
622
|
+
/** 請求書サマリー(一覧用) */
|
|
623
|
+
interface FFIDInvoiceSummary {
|
|
624
|
+
id: string;
|
|
625
|
+
organizationId: string;
|
|
626
|
+
subscriptionId: string | null;
|
|
627
|
+
invoiceNumber: string;
|
|
628
|
+
description: string | null;
|
|
629
|
+
subtotal: number;
|
|
630
|
+
taxRate: number;
|
|
631
|
+
taxAmount: number;
|
|
632
|
+
totalAmount: number;
|
|
633
|
+
currency: string;
|
|
634
|
+
status: string;
|
|
635
|
+
issuedAt: string | null;
|
|
636
|
+
dueDate: string | null;
|
|
637
|
+
paidAt: string | null;
|
|
638
|
+
pdfUrl: string | null;
|
|
639
|
+
createdAt: string;
|
|
640
|
+
}
|
|
641
|
+
/** 請求書詳細(請求先情報・備考を含む) */
|
|
642
|
+
interface FFIDInvoiceDetail extends FFIDInvoiceSummary {
|
|
643
|
+
billingName: string | null;
|
|
644
|
+
billingEmail: string | null;
|
|
645
|
+
notes: string | null;
|
|
646
|
+
}
|
|
647
|
+
/** listInvoices のパラメータ */
|
|
648
|
+
interface FFIDListInvoicesParams {
|
|
649
|
+
organizationId: string;
|
|
650
|
+
}
|
|
651
|
+
/** GET /api/v1/billing/ext/invoices のレスポンス */
|
|
652
|
+
interface FFIDListInvoicesResponse {
|
|
653
|
+
invoices: FFIDInvoiceSummary[];
|
|
654
|
+
count: number;
|
|
655
|
+
}
|
|
656
|
+
/** getInvoice のパラメータ */
|
|
657
|
+
interface FFIDGetInvoiceParams {
|
|
658
|
+
invoiceId: string;
|
|
659
|
+
}
|
|
660
|
+
/** GET /api/v1/billing/ext/invoices/{id} のレスポンス */
|
|
661
|
+
interface FFIDGetInvoiceResponse {
|
|
662
|
+
invoice: FFIDInvoiceDetail;
|
|
663
|
+
}
|
|
664
|
+
/** retryPayment のパラメータ */
|
|
665
|
+
interface FFIDRetryPaymentParams {
|
|
666
|
+
organizationId: string;
|
|
667
|
+
}
|
|
668
|
+
/** 再試行に失敗した契約の詳細 */
|
|
669
|
+
interface FFIDRetryPaymentFailure {
|
|
670
|
+
subscriptionId: string;
|
|
671
|
+
reason: string;
|
|
672
|
+
stripeCode?: string;
|
|
673
|
+
}
|
|
674
|
+
/** POST /api/v1/billing/ext/retry-payment のレスポンス */
|
|
675
|
+
interface FFIDRetryPaymentSummary {
|
|
676
|
+
totalAttempted: number;
|
|
677
|
+
succeeded: number;
|
|
678
|
+
failed: number;
|
|
679
|
+
noOpenInvoice: number;
|
|
680
|
+
failures: FFIDRetryPaymentFailure[];
|
|
681
|
+
}
|
|
682
|
+
|
|
492
683
|
/** OTP / magic link methods - sendOtp / verifyOtp */
|
|
493
684
|
|
|
494
685
|
/** Response from sendOtp */
|
|
@@ -554,6 +745,25 @@ interface ContractWizardSubscriptionOptions {
|
|
|
554
745
|
organizationId?: string;
|
|
555
746
|
}
|
|
556
747
|
|
|
748
|
+
/** OAuth token operations - exchangeCodeForTokens / refreshAccessToken / signOutToken */
|
|
749
|
+
|
|
750
|
+
/**
|
|
751
|
+
* Optional OAuth `state` validation for {@link exchangeCodeForTokens}.
|
|
752
|
+
*
|
|
753
|
+
* If a `state` is supplied on EITHER side — `expectedState` (the value persisted
|
|
754
|
+
* at `redirectToAuthorize`) or `actualState` (the value returned on the callback
|
|
755
|
+
* URL) — both must be present and equal before any token exchange. A mismatch
|
|
756
|
+
* OR an omitted counterpart fails closed (no exchange) to defend against CSRF
|
|
757
|
+
* (RFC 6749 §10.12 / #3841). Validation is skipped only when BOTH are omitted
|
|
758
|
+
* (backward compatible — callers that don't opt in are unaffected).
|
|
759
|
+
*/
|
|
760
|
+
interface ExchangeCodeForTokensOptions {
|
|
761
|
+
/** Stored state from `redirectToAuthorize` (e.g. `retrieveState()`) */
|
|
762
|
+
expectedState?: string;
|
|
763
|
+
/** State returned on the OAuth callback URL */
|
|
764
|
+
actualState?: string;
|
|
765
|
+
}
|
|
766
|
+
|
|
557
767
|
/** Redirect and URL generation - redirectToLogin / redirectToAuthorize / redirectToLogout / getLoginUrl / getSignupUrl / getLogoutUrl */
|
|
558
768
|
|
|
559
769
|
/**
|
|
@@ -593,7 +803,7 @@ declare function createFFIDClient(config: FFIDConfig): {
|
|
|
593
803
|
getLogoutUrl: (postLogoutRedirectUri?: string) => string;
|
|
594
804
|
getSignupUrl: (redirectUrl?: string) => string;
|
|
595
805
|
createError: (code: string, message: string) => FFIDError;
|
|
596
|
-
exchangeCodeForTokens: (code: string, codeVerifier?: string) => Promise<FFIDApiResponse<void>>;
|
|
806
|
+
exchangeCodeForTokens: (code: string, codeVerifier?: string, opts?: ExchangeCodeForTokensOptions) => Promise<FFIDApiResponse<void>>;
|
|
597
807
|
refreshAccessToken: () => Promise<FFIDApiResponse<void>>;
|
|
598
808
|
checkSubscription: (params: {
|
|
599
809
|
userId?: string;
|
|
@@ -622,6 +832,12 @@ declare function createFFIDClient(config: FFIDConfig): {
|
|
|
622
832
|
getAnalyticsConfig: (serviceCode: string, options?: FFIDProfileCallOptions) => Promise<FFIDApiResponse<FFIDAnalyticsConfig>>;
|
|
623
833
|
createCheckoutSession: (params: FFIDCreateCheckoutParams) => Promise<FFIDApiResponse<FFIDCheckoutSessionResponse>>;
|
|
624
834
|
createPortalSession: (params: FFIDCreatePortalParams) => Promise<FFIDApiResponse<FFIDPortalSessionResponse>>;
|
|
835
|
+
listInvoices: (params: FFIDListInvoicesParams) => Promise<FFIDApiResponse<FFIDListInvoicesResponse>>;
|
|
836
|
+
getInvoice: (params: FFIDGetInvoiceParams) => Promise<FFIDApiResponse<FFIDGetInvoiceResponse>>;
|
|
837
|
+
retryPayment: (params: FFIDRetryPaymentParams) => Promise<FFIDApiResponse<FFIDRetryPaymentSummary>>;
|
|
838
|
+
listSeatAssignments: (params: FFIDListSeatAssignmentsParams) => Promise<FFIDApiResponse<FFIDListSeatAssignmentsResponse>>;
|
|
839
|
+
assignSeats: (params: FFIDAssignSeatsParams) => Promise<FFIDApiResponse<FFIDAssignSeatsResponse>>;
|
|
840
|
+
unassignSeat: (params: FFIDUnassignSeatParams) => Promise<FFIDApiResponse<FFIDUnassignSeatResponse>>;
|
|
625
841
|
listPlans: () => Promise<FFIDApiResponse<FFIDListPlansResponse>>;
|
|
626
842
|
getSubscription: (subscriptionId: string) => Promise<FFIDApiResponse<FFIDSubscriptionDetail>>;
|
|
627
843
|
subscribe: (params: FFIDSubscribeParams) => Promise<FFIDApiResponse<FFIDSubscribeResponse>>;
|
|
@@ -689,6 +905,52 @@ declare class FFIDSDKError extends Error {
|
|
|
689
905
|
constructor(code: string, message: string);
|
|
690
906
|
}
|
|
691
907
|
|
|
908
|
+
/**
|
|
909
|
+
* OAuth redirect callback handler
|
|
910
|
+
*
|
|
911
|
+
* `handleRedirectCallback` is the convenience counterpart to
|
|
912
|
+
* `redirectToAuthorize`: it reads `code` + `state` from the callback URL,
|
|
913
|
+
* validates the OAuth `state` against the value persisted at authorize time
|
|
914
|
+
* (CSRF protection, RFC 6749 §10.12), retrieves the PKCE verifier, exchanges
|
|
915
|
+
* the code for tokens, and cleans the params out of the URL on success.
|
|
916
|
+
*/
|
|
917
|
+
|
|
918
|
+
/**
|
|
919
|
+
* Minimal client surface required by {@link handleRedirectCallback}.
|
|
920
|
+
* A full {@link FFIDClient} satisfies this structurally.
|
|
921
|
+
*/
|
|
922
|
+
type HandleRedirectCallbackClient = Pick<FFIDClient, 'exchangeCodeForTokens' | 'createError' | 'logger'>;
|
|
923
|
+
/** Options for {@link handleRedirectCallback} */
|
|
924
|
+
interface HandleRedirectCallbackOptions {
|
|
925
|
+
/**
|
|
926
|
+
* Callback URL (or query string) to read `code` / `state` from. Accepts an
|
|
927
|
+
* absolute URL, a relative URL, or a bare query string. Defaults to
|
|
928
|
+
* `window.location.search` in the browser.
|
|
929
|
+
*/
|
|
930
|
+
url?: string;
|
|
931
|
+
}
|
|
932
|
+
/**
|
|
933
|
+
* Complete an OAuth authorization-code redirect.
|
|
934
|
+
*
|
|
935
|
+
* Behavior:
|
|
936
|
+
* 1. Reads `code` + `state` from `options.url ?? window.location.search`.
|
|
937
|
+
* 2. CSRF guard: if a `state` exists on EITHER side (a stored state from
|
|
938
|
+
* authorize OR a `state` on the callback URL), the two MUST match — mismatch,
|
|
939
|
+
* a missing stored state, or an **omitted** callback `state` all **fail closed**
|
|
940
|
+
* (returns an error, performs no exchange). Validation is skipped ONLY when
|
|
941
|
+
* neither side has any state (a genuine no-state flow). Omitting the callback
|
|
942
|
+
* `state` does NOT bypass the check (#3841).
|
|
943
|
+
* 3. Retrieves the PKCE verifier and exchanges the code for tokens.
|
|
944
|
+
* 4. On success, removes `code` + `state` from the browser URL.
|
|
945
|
+
*
|
|
946
|
+
* SSR-safe: when there is no `window` and no `options.url`, no exchange is
|
|
947
|
+
* attempted and an error result is returned.
|
|
948
|
+
*
|
|
949
|
+
* @param client - FFID client (or any object exposing exchangeCodeForTokens / createError / logger)
|
|
950
|
+
* @param options - Optional callback URL override
|
|
951
|
+
*/
|
|
952
|
+
declare function handleRedirectCallback(client: HandleRedirectCallbackClient, options?: HandleRedirectCallbackOptions): Promise<FFIDApiResponse<void>>;
|
|
953
|
+
|
|
692
954
|
/**
|
|
693
955
|
* Redirect URI normalization (SDK copy)
|
|
694
956
|
*
|
|
@@ -1397,4 +1659,4 @@ declare function createInquiryMethods(deps: InquiryMethodsDeps): {
|
|
|
1397
1659
|
};
|
|
1398
1660
|
type FFIDInquiryClient = ReturnType<typeof createInquiryMethods>;
|
|
1399
1661
|
|
|
1400
|
-
export { ACCESS_GRANTING_EFFECTIVE_STATUSES, AnnouncementListResponse, BLOCKING_EFFECTIVE_STATUSES, type ComputeEffectiveStatusInput, type ContractWizardFlowType, type ContractWizardResubscribeOptions, type ContractWizardSubscribeOptions, type ContractWizardSubscriptionOptions, DEFAULT_API_BASE_URL, DEFAULT_OAUTH_SCOPES, EffectiveSubscriptionStatus, type FFIDAddMemberParams, type FFIDAddMemberRequest, type FFIDAddMemberResponse, FFIDAnnouncementsApiResponse, type FFIDAnnouncementsClient, FFIDAnnouncementsClientConfig, FFIDAnnouncementsLogger, FFIDApiResponse, type FFIDAssignableMemberRole, type FFIDBillingInterval, FFIDCacheAdapter, type FFIDCancelPendingDowngradeResponse, type FFIDCancelSubscriptionParams, type FFIDCancelSubscriptionResponse, type FFIDChangePlanParams, type FFIDChangePlanResponse, FFIDCheckServiceAccessParams, FFIDCheckoutSessionResponse, type FFIDClient, FFIDConfig, FFIDCreateCheckoutParams, FFIDCreatePortalParams, FFIDError, type FFIDInquiryClient, FFIDInquiryCreateParams, FFIDInquiryCreateResponse, type FFIDListMembersResponse, type FFIDListPlansResponse, FFIDLogger, type FFIDMemberRole, type FFIDMemberStatus, type FFIDNewsletterBodySource, type FFIDNewsletterCampaignStatus, type FFIDNewsletterClient, type FFIDNewsletterConfirmParams, type FFIDNewsletterConfirmResponse, type FFIDNewsletterDispatchParams, type FFIDNewsletterDispatchResponse, type FFIDNewsletterSegment, type FFIDNewsletterSubscribeParams, type FFIDNewsletterSubscribeResponse, type FFIDNewsletterType, type FFIDNewsletterUnsubscribeParams, type FFIDNewsletterUnsubscribeResponse, FFIDOAuthUserInfo, FFIDOAuthUserInfoSubscription, FFIDOrganization, type FFIDOrganizationMember, type FFIDOtpSendResponse, type FFIDOtpVerifyResponse, type FFIDPasswordResetConfirmResponse, type FFIDPasswordResetResponse, type FFIDPasswordResetVerifyResponse, type FFIDPlanChangeLineItem, type FFIDPlanChangePreview, type FFIDPlanChangePreviewResponse, type FFIDPlanInfo, FFIDPortalSessionResponse, type FFIDPreviewPlanChangeParams, type FFIDPreviewSeatChangeParams, FFIDProfileCallOptions, FFIDProvider, type FFIDProviderProps, FFIDRedirectResult, type FFIDRemoveMemberResponse, type FFIDResetSessionResponse, FFIDSDKError, type FFIDSeatChangeLineItem, type FFIDSeatChangePreview, type FFIDSeatChangePreviewResponse, FFIDServiceAccessDecision, type FFIDServiceInfo, FFIDSessionResponse, type FFIDSubscribeParams, type FFIDSubscribeResponse, FFIDSubscription, FFIDSubscriptionCheckResponse, FFIDSubscriptionContextValue, type FFIDSubscriptionDetail, FFIDSubscriptionStatus, type FFIDSubscriptionSummary, type FFIDSupportedCurrency, type FFIDUpdateMemberRoleResponse, FFIDUpdateUserProfileRequest, FFIDUser, FFIDUserProfile, FFIDVerifyAccessTokenOptions, FFID_ANNOUNCEMENTS_ERROR_CODES, FFID_NEWSLETTER_DISPATCH_MAX_RECIPIENTS, FFID_NEWSLETTER_TYPES, type KVNamespaceLike, ListAnnouncementsOptions, type NormalizeRedirectUriResult, type RedirectToAuthorizeOptions, type TokenData, type TokenStore, type UseFFIDReturn, type UseRequireActiveSubscriptionOptions, type UseRequireActiveSubscriptionReturn, type WithFFIDAuthOptions, type WithSubscriptionOptions, computeEffectiveStatusFromSession, createFFIDAnnouncementsClient, createFFIDClient, createKVCacheAdapter, createMemoryCacheAdapter, createTokenStore, generateCodeChallenge, generateCodeVerifier, hasAccessFromUserinfo, isBlockedFromUserinfo, normalizeRedirectUri, retrieveCodeVerifier, storeCodeVerifier, useFFID, useRequireActiveSubscription, useSubscription, withFFIDAuth, withSubscription };
|
|
1662
|
+
export { ACCESS_GRANTING_EFFECTIVE_STATUSES, AnnouncementListResponse, BLOCKING_EFFECTIVE_STATUSES, type ComputeEffectiveStatusInput, type ContractWizardFlowType, type ContractWizardResubscribeOptions, type ContractWizardSubscribeOptions, type ContractWizardSubscriptionOptions, DEFAULT_API_BASE_URL, DEFAULT_OAUTH_SCOPES, EffectiveSubscriptionStatus, type ExchangeCodeForTokensOptions, type FFIDAddMemberParams, type FFIDAddMemberRequest, type FFIDAddMemberResponse, FFIDAnnouncementsApiResponse, type FFIDAnnouncementsClient, FFIDAnnouncementsClientConfig, FFIDAnnouncementsLogger, FFIDApiResponse, type FFIDAssignableMemberRole, type FFIDBillingInterval, FFIDCacheAdapter, type FFIDCancelPendingDowngradeResponse, type FFIDCancelSubscriptionParams, type FFIDCancelSubscriptionResponse, type FFIDChangePlanParams, type FFIDChangePlanResponse, FFIDCheckServiceAccessParams, type FFIDCheckoutSessionResponse, type FFIDClient, FFIDConfig, type FFIDCreateCheckoutParams, type FFIDCreatePortalParams, FFIDError, type FFIDInquiryClient, FFIDInquiryCreateParams, FFIDInquiryCreateResponse, type FFIDListMembersResponse, type FFIDListPlansResponse, FFIDLogger, type FFIDMemberRole, type FFIDMemberStatus, type FFIDNewsletterBodySource, type FFIDNewsletterCampaignStatus, type FFIDNewsletterClient, type FFIDNewsletterConfirmParams, type FFIDNewsletterConfirmResponse, type FFIDNewsletterDispatchParams, type FFIDNewsletterDispatchResponse, type FFIDNewsletterSegment, type FFIDNewsletterSubscribeParams, type FFIDNewsletterSubscribeResponse, type FFIDNewsletterType, type FFIDNewsletterUnsubscribeParams, type FFIDNewsletterUnsubscribeResponse, FFIDOAuthUserInfo, FFIDOAuthUserInfoSubscription, FFIDOrganization, type FFIDOrganizationMember, type FFIDOtpSendResponse, type FFIDOtpVerifyResponse, type FFIDPasswordResetConfirmResponse, type FFIDPasswordResetResponse, type FFIDPasswordResetVerifyResponse, type FFIDPlanChangeLineItem, type FFIDPlanChangePreview, type FFIDPlanChangePreviewResponse, type FFIDPlanInfo, type FFIDPortalSessionResponse, type FFIDPreviewPlanChangeParams, type FFIDPreviewSeatChangeParams, FFIDProfileCallOptions, FFIDProvider, type FFIDProviderProps, FFIDRedirectResult, type FFIDRemoveMemberResponse, type FFIDResetSessionResponse, FFIDSDKError, type FFIDSeatChangeLineItem, type FFIDSeatChangePreview, type FFIDSeatChangePreviewResponse, FFIDServiceAccessDecision, type FFIDServiceInfo, FFIDSessionResponse, type FFIDSubscribeParams, type FFIDSubscribeResponse, FFIDSubscription, FFIDSubscriptionCheckResponse, FFIDSubscriptionContextValue, type FFIDSubscriptionDetail, FFIDSubscriptionStatus, type FFIDSubscriptionSummary, type FFIDSupportedCurrency, type FFIDUpdateMemberRoleResponse, FFIDUpdateUserProfileRequest, FFIDUser, FFIDUserProfile, FFIDVerifyAccessTokenOptions, FFID_ANNOUNCEMENTS_ERROR_CODES, FFID_NEWSLETTER_DISPATCH_MAX_RECIPIENTS, FFID_NEWSLETTER_TYPES, type HandleRedirectCallbackClient, type HandleRedirectCallbackOptions, type KVNamespaceLike, ListAnnouncementsOptions, type NormalizeRedirectUriResult, type RedirectToAuthorizeOptions, type TokenData, type TokenStore, type UseFFIDReturn, type UseRequireActiveSubscriptionOptions, type UseRequireActiveSubscriptionReturn, type WithFFIDAuthOptions, type WithSubscriptionOptions, cleanupStateStorage as clearState, computeEffectiveStatusFromSession, createFFIDAnnouncementsClient, createFFIDClient, createKVCacheAdapter, createMemoryCacheAdapter, createTokenStore, generateCodeChallenge, generateCodeVerifier, handleRedirectCallback, hasAccessFromUserinfo, isBlockedFromUserinfo, normalizeRedirectUri, retrieveCodeVerifier, retrieveState, storeCodeVerifier, storeState, useFFID, useRequireActiveSubscription, useSubscription, withFFIDAuth, withSubscription };
|
package/dist/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { useFFIDContext, useSubscription } from './chunk-
|
|
2
|
-
export { ACCESS_GRANTING_EFFECTIVE_STATUSES, BLOCKING_EFFECTIVE_STATUSES, DEFAULT_API_BASE_URL, DEFAULT_OAUTH_SCOPES, FFIDAnnouncementBadge, FFIDAnnouncementList, FFIDInquiryForm, FFIDLoginButton, FFIDOrganizationSwitcher, FFIDProvider, FFIDSDKError, FFIDSubscriptionBadge, FFIDUserMenu, FFID_ANNOUNCEMENTS_ERROR_CODES, FFID_INQUIRY_CATEGORIES, FFID_INQUIRY_CATEGORIES_SITE_2026, computeEffectiveStatusFromSession, createFFIDAnnouncementsClient, createFFIDClient, createTokenStore, generateCodeChallenge, generateCodeVerifier, hasAccessFromUserinfo, isBlockedFromUserinfo, isFFIDInquiryCategorySite2026, normalizeRedirectUri, retrieveCodeVerifier, storeCodeVerifier, useFFID, useFFIDAnnouncements, useSubscription, withSubscription } from './chunk-
|
|
1
|
+
import { useFFIDContext, useSubscription } from './chunk-RATTQIKM.js';
|
|
2
|
+
export { ACCESS_GRANTING_EFFECTIVE_STATUSES, BLOCKING_EFFECTIVE_STATUSES, DEFAULT_API_BASE_URL, DEFAULT_OAUTH_SCOPES, EFFECTIVE_SUBSCRIPTION_STATUSES, FFIDAnnouncementBadge, FFIDAnnouncementList, FFIDInquiryForm, FFIDLoginButton, FFIDOrganizationSwitcher, FFIDProvider, FFIDSDKError, FFIDSubscriptionBadge, FFIDUserMenu, FFID_ANNOUNCEMENTS_ERROR_CODES, FFID_INQUIRY_CATEGORIES, FFID_INQUIRY_CATEGORIES_SITE_2026, cleanupStateStorage as clearState, computeEffectiveStatusFromSession, createFFIDAnnouncementsClient, createFFIDClient, createTokenStore, generateCodeChallenge, generateCodeVerifier, handleRedirectCallback, hasAccessFromUserinfo, isBlockedFromUserinfo, isFFIDInquiryCategorySite2026, normalizeRedirectUri, retrieveCodeVerifier, retrieveState, storeCodeVerifier, storeState, useFFID, useFFIDAnnouncements, useSubscription, withSubscription } from './chunk-RATTQIKM.js';
|
|
3
3
|
export { ALL_DENIED_EXCEPT_NECESSARY, CONSENT_COOKIE_NAME, CONSENT_DISMISSAL_TIMESTAMP_KEY, COOKIE_VERSION, DEFAULT_CONSENT_ERROR_MESSAGES, FFIDAnalyticsProvider, FFIDConsentError, FFIDCookieBanner, FFIDCookieLink, FFIDCookieSettings, FFID_CONSENT_ERROR_CODES, clearConsentDismissalTimestamp, decodeConsentCookie, encodeConsentCookie, readConsentCookie, readConsentDismissalTimestamp, useFFIDConsent, useFFIDConsentPreferences, writeConsentCookie, writeConsentDismissalTimestamp } from './chunk-M4N2PUX6.js';
|
|
4
4
|
import { useEffect, useRef } from 'react';
|
|
5
5
|
import { jsx, Fragment } from 'react/jsx-runtime';
|
package/dist/server/index.cjs
CHANGED
|
@@ -119,6 +119,9 @@ function normalizeUserinfo(raw) {
|
|
|
119
119
|
return {
|
|
120
120
|
sub: raw.sub,
|
|
121
121
|
email: raw.email,
|
|
122
|
+
// #3791: undefined → undefined を保つ(false に丸めない)。古い FFID は wire に
|
|
123
|
+
// 含めないため、consumer は undefined を「未確認」ではなく「不明」として扱える。
|
|
124
|
+
emailVerified: raw.email_verified,
|
|
122
125
|
name: raw.name,
|
|
123
126
|
picture: raw.picture,
|
|
124
127
|
companyName: raw.company_name ?? null,
|
|
@@ -374,6 +377,9 @@ function createVerifyAccessToken(deps) {
|
|
|
374
377
|
const base = {
|
|
375
378
|
sub: introspectResponse.sub,
|
|
376
379
|
email: introspectResponse.email ?? null,
|
|
380
|
+
// #3791: preserve undefined (do NOT coerce to false) so introspect-strategy
|
|
381
|
+
// callers can distinguish "verified" / "not verified" / "older server".
|
|
382
|
+
email_verified: introspectResponse.email_verified,
|
|
377
383
|
name: introspectResponse.name ?? null,
|
|
378
384
|
picture: introspectResponse.picture ?? null,
|
|
379
385
|
company_name: introspectResponse.company_name ?? null,
|
|
@@ -431,6 +437,8 @@ function createVerifyAccessToken(deps) {
|
|
|
431
437
|
// src/client/billing-methods.ts
|
|
432
438
|
var BILLING_CHECKOUT_ENDPOINT = "/api/v1/billing/checkout";
|
|
433
439
|
var BILLING_PORTAL_ENDPOINT = "/api/v1/billing/portal";
|
|
440
|
+
var EXT_INVOICES_ENDPOINT = "/api/v1/billing/ext/invoices";
|
|
441
|
+
var EXT_RETRY_PAYMENT_ENDPOINT = "/api/v1/billing/ext/retry-payment";
|
|
434
442
|
function createBillingMethods(deps) {
|
|
435
443
|
const { fetchWithAuth, createError } = deps;
|
|
436
444
|
async function createCheckoutSession(params) {
|
|
@@ -472,7 +480,31 @@ function createBillingMethods(deps) {
|
|
|
472
480
|
`${BILLING_PORTAL_ENDPOINT}?${query.toString()}`
|
|
473
481
|
);
|
|
474
482
|
}
|
|
475
|
-
|
|
483
|
+
async function listInvoices(params) {
|
|
484
|
+
if (!params.organizationId) {
|
|
485
|
+
return { error: createError("VALIDATION_ERROR", "organizationId \u306F\u5FC5\u9808\u3067\u3059") };
|
|
486
|
+
}
|
|
487
|
+
const query = new URLSearchParams({ organizationId: params.organizationId });
|
|
488
|
+
return fetchWithAuth(`${EXT_INVOICES_ENDPOINT}?${query.toString()}`);
|
|
489
|
+
}
|
|
490
|
+
async function getInvoice(params) {
|
|
491
|
+
if (!params.invoiceId) {
|
|
492
|
+
return { error: createError("VALIDATION_ERROR", "invoiceId \u306F\u5FC5\u9808\u3067\u3059") };
|
|
493
|
+
}
|
|
494
|
+
return fetchWithAuth(
|
|
495
|
+
`${EXT_INVOICES_ENDPOINT}/${encodeURIComponent(params.invoiceId)}`
|
|
496
|
+
);
|
|
497
|
+
}
|
|
498
|
+
async function retryPayment(params) {
|
|
499
|
+
if (!params.organizationId) {
|
|
500
|
+
return { error: createError("VALIDATION_ERROR", "organizationId \u306F\u5FC5\u9808\u3067\u3059") };
|
|
501
|
+
}
|
|
502
|
+
return fetchWithAuth(EXT_RETRY_PAYMENT_ENDPOINT, {
|
|
503
|
+
method: "POST",
|
|
504
|
+
body: JSON.stringify({ organizationId: params.organizationId })
|
|
505
|
+
});
|
|
506
|
+
}
|
|
507
|
+
return { createCheckoutSession, createPortalSession, listInvoices, getInvoice, retryPayment };
|
|
476
508
|
}
|
|
477
509
|
|
|
478
510
|
// src/client/subscription-methods.ts
|
|
@@ -814,6 +846,45 @@ function createMembersMethods(deps) {
|
|
|
814
846
|
return { listMembers, addMember, updateMemberRole, removeMember };
|
|
815
847
|
}
|
|
816
848
|
|
|
849
|
+
// src/client/seat-methods.ts
|
|
850
|
+
function seatsEndpoint(subscriptionId) {
|
|
851
|
+
return `/api/v1/subscriptions/ext/${encodeURIComponent(subscriptionId)}/seats/assignments`;
|
|
852
|
+
}
|
|
853
|
+
function createSeatMethods(deps) {
|
|
854
|
+
const { fetchWithAuth, createError } = deps;
|
|
855
|
+
async function listSeatAssignments(params) {
|
|
856
|
+
if (!params.subscriptionId) {
|
|
857
|
+
return { error: createError("VALIDATION_ERROR", "subscriptionId \u306F\u5FC5\u9808\u3067\u3059") };
|
|
858
|
+
}
|
|
859
|
+
return fetchWithAuth(seatsEndpoint(params.subscriptionId));
|
|
860
|
+
}
|
|
861
|
+
async function assignSeats(params) {
|
|
862
|
+
if (!params.subscriptionId) {
|
|
863
|
+
return { error: createError("VALIDATION_ERROR", "subscriptionId \u306F\u5FC5\u9808\u3067\u3059") };
|
|
864
|
+
}
|
|
865
|
+
if (!Array.isArray(params.userIds) || params.userIds.length === 0) {
|
|
866
|
+
return { error: createError("VALIDATION_ERROR", "userIds \u306F 1 \u4EF6\u4EE5\u4E0A\u6307\u5B9A\u3057\u3066\u304F\u3060\u3055\u3044") };
|
|
867
|
+
}
|
|
868
|
+
return fetchWithAuth(seatsEndpoint(params.subscriptionId), {
|
|
869
|
+
method: "POST",
|
|
870
|
+
body: JSON.stringify({ userIds: params.userIds })
|
|
871
|
+
});
|
|
872
|
+
}
|
|
873
|
+
async function unassignSeat(params) {
|
|
874
|
+
if (!params.subscriptionId) {
|
|
875
|
+
return { error: createError("VALIDATION_ERROR", "subscriptionId \u306F\u5FC5\u9808\u3067\u3059") };
|
|
876
|
+
}
|
|
877
|
+
if (!params.userId) {
|
|
878
|
+
return { error: createError("VALIDATION_ERROR", "userId \u306F\u5FC5\u9808\u3067\u3059") };
|
|
879
|
+
}
|
|
880
|
+
return fetchWithAuth(
|
|
881
|
+
`${seatsEndpoint(params.subscriptionId)}/${encodeURIComponent(params.userId)}`,
|
|
882
|
+
{ method: "DELETE" }
|
|
883
|
+
);
|
|
884
|
+
}
|
|
885
|
+
return { listSeatAssignments, assignSeats, unassignSeat };
|
|
886
|
+
}
|
|
887
|
+
|
|
817
888
|
// src/client/profile-methods.ts
|
|
818
889
|
var EXT_PROFILE_ENDPOINT = "/api/v1/users/ext/me";
|
|
819
890
|
function resolveAuthOverride(options, createError) {
|
|
@@ -864,7 +935,7 @@ function createProfileMethods(deps) {
|
|
|
864
935
|
}
|
|
865
936
|
|
|
866
937
|
// src/client/version-check.ts
|
|
867
|
-
var SDK_VERSION = "5.
|
|
938
|
+
var SDK_VERSION = "5.13.0";
|
|
868
939
|
var SDK_USER_AGENT = `FFID-SDK/${SDK_VERSION} (TypeScript)`;
|
|
869
940
|
var SDK_VERSION_HEADER = "X-FFID-SDK-Version";
|
|
870
941
|
function sdkHeaders() {
|
|
@@ -936,9 +1007,20 @@ function createOAuthTokenMethods(deps) {
|
|
|
936
1007
|
logger,
|
|
937
1008
|
errorCodes
|
|
938
1009
|
} = deps;
|
|
939
|
-
async function exchangeCodeForTokens(code, codeVerifier) {
|
|
1010
|
+
async function exchangeCodeForTokens(code, codeVerifier, opts) {
|
|
940
1011
|
const url = `${baseUrl}${OAUTH_TOKEN_ENDPOINT}`;
|
|
941
1012
|
logger.debug("Exchanging code for tokens:", url);
|
|
1013
|
+
if (opts?.expectedState !== void 0 || opts?.actualState !== void 0) {
|
|
1014
|
+
if (opts?.expectedState !== opts?.actualState) {
|
|
1015
|
+
logger.error("Token exchange aborted: OAuth state mismatch or omitted (possible CSRF)");
|
|
1016
|
+
return {
|
|
1017
|
+
error: {
|
|
1018
|
+
code: errorCodes.STATE_MISMATCH_ERROR,
|
|
1019
|
+
message: "OAuth state \u304C\u4E00\u81F4\u3057\u307E\u305B\u3093\u3002CSRF \u306E\u53EF\u80FD\u6027\u304C\u3042\u308B\u305F\u3081\u8A8D\u8A3C\u3092\u4E2D\u6B62\u3057\u307E\u3057\u305F"
|
|
1020
|
+
}
|
|
1021
|
+
};
|
|
1022
|
+
}
|
|
1023
|
+
}
|
|
942
1024
|
const effectiveRedirectUri = resolvedRedirectUri ?? (typeof window !== "undefined" ? window.location.origin + window.location.pathname : null);
|
|
943
1025
|
if (!effectiveRedirectUri) {
|
|
944
1026
|
logger.error("redirectUri is required for token exchange in SSR environments. Set config.redirectUri explicitly.");
|
|
@@ -1383,6 +1465,46 @@ function base64UrlEncode(buffer) {
|
|
|
1383
1465
|
return btoa(binary).replace(/\+/g, "-").replace(/\//g, "_").replace(/=+$/, "");
|
|
1384
1466
|
}
|
|
1385
1467
|
|
|
1468
|
+
// src/auth/state.ts
|
|
1469
|
+
var STATE_STORAGE_KEY = "ffid_oauth_state";
|
|
1470
|
+
var STATE_FALLBACK_STORAGE_KEY = "ffid_oauth_state_fb";
|
|
1471
|
+
var STATE_FALLBACK_TIMESTAMP_KEY = "ffid_oauth_state_fb_ts";
|
|
1472
|
+
function storeState(state, logger) {
|
|
1473
|
+
if (typeof window === "undefined") {
|
|
1474
|
+
logger?.warn("storeState: storage is not available in SSR context");
|
|
1475
|
+
return false;
|
|
1476
|
+
}
|
|
1477
|
+
let sessionStored = false;
|
|
1478
|
+
try {
|
|
1479
|
+
window.sessionStorage.setItem(STATE_STORAGE_KEY, state);
|
|
1480
|
+
sessionStored = true;
|
|
1481
|
+
} catch (error) {
|
|
1482
|
+
logger?.warn("storeState: sessionStorage \u3078\u306E\u4FDD\u5B58\u306B\u5931\u6557\u3057\u307E\u3057\u305F:", error);
|
|
1483
|
+
}
|
|
1484
|
+
let localStored = false;
|
|
1485
|
+
try {
|
|
1486
|
+
window.localStorage.setItem(STATE_FALLBACK_STORAGE_KEY, state);
|
|
1487
|
+
window.localStorage.setItem(STATE_FALLBACK_TIMESTAMP_KEY, String(Date.now()));
|
|
1488
|
+
localStored = true;
|
|
1489
|
+
} catch (error) {
|
|
1490
|
+
logger?.warn("storeState: localStorage fallback \u3078\u306E\u4FDD\u5B58\u306B\u5931\u6557\u3057\u307E\u3057\u305F:", error);
|
|
1491
|
+
}
|
|
1492
|
+
return sessionStored || localStored;
|
|
1493
|
+
}
|
|
1494
|
+
function cleanupStateStorage(logger) {
|
|
1495
|
+
try {
|
|
1496
|
+
window.sessionStorage.removeItem(STATE_STORAGE_KEY);
|
|
1497
|
+
} catch (error) {
|
|
1498
|
+
logger?.warn("retrieveState: sessionStorage \u306E\u30AF\u30EA\u30FC\u30F3\u30A2\u30C3\u30D7\u306B\u5931\u6557\u3057\u307E\u3057\u305F:", error);
|
|
1499
|
+
}
|
|
1500
|
+
try {
|
|
1501
|
+
window.localStorage.removeItem(STATE_FALLBACK_STORAGE_KEY);
|
|
1502
|
+
window.localStorage.removeItem(STATE_FALLBACK_TIMESTAMP_KEY);
|
|
1503
|
+
} catch (error) {
|
|
1504
|
+
logger?.warn("retrieveState: localStorage \u306E\u30AF\u30EA\u30FC\u30F3\u30A2\u30C3\u30D7\u306B\u5931\u6557\u3057\u307E\u3057\u305F:", error);
|
|
1505
|
+
}
|
|
1506
|
+
}
|
|
1507
|
+
|
|
1386
1508
|
// src/client/redirect.ts
|
|
1387
1509
|
var OAUTH_AUTHORIZE_ENDPOINT = "/api/v1/oauth/authorize";
|
|
1388
1510
|
var AUTH_LOGOUT_ENDPOINT = "/api/v1/auth/logout";
|
|
@@ -1514,6 +1636,7 @@ function createRedirectMethods(deps) {
|
|
|
1514
1636
|
const recentCount = getRecentRedirectCount(authorizeKey, now, logger);
|
|
1515
1637
|
if (recentCount >= REDIRECT_LOOP_THRESHOLD) {
|
|
1516
1638
|
cleanupVerifierStorage(logger);
|
|
1639
|
+
cleanupStateStorage(logger);
|
|
1517
1640
|
logger.warn("[FFID SDK] redirect loop detected \u2014 \u81EA\u52D5\u30EA\u30C0\u30A4\u30EC\u30AF\u30C8\u3092\u505C\u6B62\u3057\u307E\u3057\u305F", {
|
|
1518
1641
|
authorizeKey,
|
|
1519
1642
|
recentCount,
|
|
@@ -1537,6 +1660,11 @@ function createRedirectMethods(deps) {
|
|
|
1537
1660
|
return { success: false, error: errorMessage };
|
|
1538
1661
|
}
|
|
1539
1662
|
const state = generateRandomState();
|
|
1663
|
+
if (!storeState(state, logger)) {
|
|
1664
|
+
logger.error(
|
|
1665
|
+
"redirectToAuthorize: OAuth state \u3092\u4FDD\u5B58\u3067\u304D\u307E\u305B\u3093\u3067\u3057\u305F\uFF08storage \u5229\u7528\u4E0D\u53EF\uFF09\u3002\u30B3\u30FC\u30EB\u30D0\u30C3\u30AF\u3067\u306E CSRF \u691C\u8A3C\u304C\u5931\u6557\u3057\u307E\u3059"
|
|
1666
|
+
);
|
|
1667
|
+
}
|
|
1540
1668
|
const redirectUri = resolvedRedirectUri ?? window.location.origin + window.location.pathname;
|
|
1541
1669
|
const params = new URLSearchParams({
|
|
1542
1670
|
response_type: "code",
|
|
@@ -2251,7 +2379,8 @@ var FFID_ERROR_CODES = {
|
|
|
2251
2379
|
TOKEN_EXCHANGE_ERROR: "TOKEN_EXCHANGE_ERROR",
|
|
2252
2380
|
TOKEN_REFRESH_ERROR: "TOKEN_REFRESH_ERROR",
|
|
2253
2381
|
NO_TOKENS: "NO_TOKENS",
|
|
2254
|
-
TOKEN_VERIFICATION_ERROR: "TOKEN_VERIFICATION_ERROR"
|
|
2382
|
+
TOKEN_VERIFICATION_ERROR: "TOKEN_VERIFICATION_ERROR",
|
|
2383
|
+
STATE_MISMATCH_ERROR: "STATE_MISMATCH_ERROR"
|
|
2255
2384
|
};
|
|
2256
2385
|
var EXT_CHECK_ENDPOINT = "/api/v1/subscriptions/ext/check";
|
|
2257
2386
|
var DEFAULT_ALLOW_GRACE = true;
|
|
@@ -2609,7 +2738,11 @@ function createFFIDClient(config) {
|
|
|
2609
2738
|
}
|
|
2610
2739
|
return result;
|
|
2611
2740
|
}
|
|
2612
|
-
const { createCheckoutSession, createPortalSession } = createBillingMethods({
|
|
2741
|
+
const { createCheckoutSession, createPortalSession, listInvoices, getInvoice, retryPayment } = createBillingMethods({
|
|
2742
|
+
fetchWithAuth,
|
|
2743
|
+
createError
|
|
2744
|
+
});
|
|
2745
|
+
const { listSeatAssignments, assignSeats, unassignSeat } = createSeatMethods({
|
|
2613
2746
|
fetchWithAuth,
|
|
2614
2747
|
createError
|
|
2615
2748
|
});
|
|
@@ -2718,6 +2851,12 @@ function createFFIDClient(config) {
|
|
|
2718
2851
|
getAnalyticsConfig,
|
|
2719
2852
|
createCheckoutSession,
|
|
2720
2853
|
createPortalSession,
|
|
2854
|
+
listInvoices,
|
|
2855
|
+
getInvoice,
|
|
2856
|
+
retryPayment,
|
|
2857
|
+
listSeatAssignments,
|
|
2858
|
+
assignSeats,
|
|
2859
|
+
unassignSeat,
|
|
2721
2860
|
listPlans,
|
|
2722
2861
|
getSubscription,
|
|
2723
2862
|
subscribe,
|
package/dist/server/index.d.cts
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { F as FFIDLogger, a as FFIDError, b as FFIDCacheAdapter, c as FFIDVerifyAccessTokenOptions, d as FFIDApiResponse, e as FFIDOAuthUserInfo } from '../ffid-client-
|
|
2
|
-
export { f as FFIDAddMemberParams, g as FFIDAddMemberRequest, h as FFIDAddMemberResponse, i as FFIDAssignableMemberRole, j as FFIDCacheConfig, k as FFIDClient, l as FFIDConfig, m as FFIDListMembersResponse, n as FFIDMemberRole, o as FFIDOrganization, p as FFIDOrganizationMember, q as FFIDOtpSendResponse, r as FFIDOtpVerifyResponse, s as FFIDPasswordResetConfirmResponse, t as FFIDPasswordResetResponse, u as FFIDPasswordResetVerifyResponse, v as FFIDProfileCallOptions, w as FFIDRemoveMemberResponse, x as FFIDResetSessionResponse, y as FFIDSubscription, z as FFIDUpdateMemberRoleResponse, A as FFIDUpdateUserProfileRequest, B as FFIDUser, C as FFIDUserProfile, T as TokenData, D as TokenStore, E as createFFIDClient, G as createTokenStore } from '../ffid-client-
|
|
1
|
+
import { F as FFIDLogger, a as FFIDError, b as FFIDCacheAdapter, c as FFIDVerifyAccessTokenOptions, d as FFIDApiResponse, e as FFIDOAuthUserInfo } from '../ffid-client-C3K3sAqq.cjs';
|
|
2
|
+
export { f as FFIDAddMemberParams, g as FFIDAddMemberRequest, h as FFIDAddMemberResponse, i as FFIDAssignableMemberRole, j as FFIDCacheConfig, k as FFIDClient, l as FFIDConfig, m as FFIDListMembersResponse, n as FFIDMemberRole, o as FFIDOrganization, p as FFIDOrganizationMember, q as FFIDOtpSendResponse, r as FFIDOtpVerifyResponse, s as FFIDPasswordResetConfirmResponse, t as FFIDPasswordResetResponse, u as FFIDPasswordResetVerifyResponse, v as FFIDProfileCallOptions, w as FFIDRemoveMemberResponse, x as FFIDResetSessionResponse, y as FFIDSubscription, z as FFIDUpdateMemberRoleResponse, A as FFIDUpdateUserProfileRequest, B as FFIDUser, C as FFIDUserProfile, T as TokenData, D as TokenStore, E as createFFIDClient, G as createTokenStore } from '../ffid-client-C3K3sAqq.cjs';
|
|
3
3
|
export { D as DEFAULT_API_BASE_URL, a as DEFAULT_OAUTH_SCOPES } from '../constants-D61jqRIO.cjs';
|
|
4
4
|
import { z } from 'zod';
|
|
5
|
-
import '../types-
|
|
5
|
+
import '../types-BeVl-z12.cjs';
|
|
6
6
|
|
|
7
7
|
/** Token verification - verifyAccessToken() implementation */
|
|
8
8
|
|
package/dist/server/index.d.ts
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import { F as FFIDLogger, a as FFIDError, b as FFIDCacheAdapter, c as FFIDVerifyAccessTokenOptions, d as FFIDApiResponse, e as FFIDOAuthUserInfo } from '../ffid-client-
|
|
2
|
-
export { f as FFIDAddMemberParams, g as FFIDAddMemberRequest, h as FFIDAddMemberResponse, i as FFIDAssignableMemberRole, j as FFIDCacheConfig, k as FFIDClient, l as FFIDConfig, m as FFIDListMembersResponse, n as FFIDMemberRole, o as FFIDOrganization, p as FFIDOrganizationMember, q as FFIDOtpSendResponse, r as FFIDOtpVerifyResponse, s as FFIDPasswordResetConfirmResponse, t as FFIDPasswordResetResponse, u as FFIDPasswordResetVerifyResponse, v as FFIDProfileCallOptions, w as FFIDRemoveMemberResponse, x as FFIDResetSessionResponse, y as FFIDSubscription, z as FFIDUpdateMemberRoleResponse, A as FFIDUpdateUserProfileRequest, B as FFIDUser, C as FFIDUserProfile, T as TokenData, D as TokenStore, E as createFFIDClient, G as createTokenStore } from '../ffid-client-
|
|
1
|
+
import { F as FFIDLogger, a as FFIDError, b as FFIDCacheAdapter, c as FFIDVerifyAccessTokenOptions, d as FFIDApiResponse, e as FFIDOAuthUserInfo } from '../ffid-client-BG0Qr86U.js';
|
|
2
|
+
export { f as FFIDAddMemberParams, g as FFIDAddMemberRequest, h as FFIDAddMemberResponse, i as FFIDAssignableMemberRole, j as FFIDCacheConfig, k as FFIDClient, l as FFIDConfig, m as FFIDListMembersResponse, n as FFIDMemberRole, o as FFIDOrganization, p as FFIDOrganizationMember, q as FFIDOtpSendResponse, r as FFIDOtpVerifyResponse, s as FFIDPasswordResetConfirmResponse, t as FFIDPasswordResetResponse, u as FFIDPasswordResetVerifyResponse, v as FFIDProfileCallOptions, w as FFIDRemoveMemberResponse, x as FFIDResetSessionResponse, y as FFIDSubscription, z as FFIDUpdateMemberRoleResponse, A as FFIDUpdateUserProfileRequest, B as FFIDUser, C as FFIDUserProfile, T as TokenData, D as TokenStore, E as createFFIDClient, G as createTokenStore } from '../ffid-client-BG0Qr86U.js';
|
|
3
3
|
export { D as DEFAULT_API_BASE_URL, a as DEFAULT_OAUTH_SCOPES } from '../constants-D61jqRIO.js';
|
|
4
4
|
import { z } from 'zod';
|
|
5
|
-
import '../types-
|
|
5
|
+
import '../types-BeVl-z12.js';
|
|
6
6
|
|
|
7
7
|
/** Token verification - verifyAccessToken() implementation */
|
|
8
8
|
|