@opexa/portal-components 0.0.175 → 0.0.177

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.
@@ -0,0 +1,3 @@
1
+ import type { Mutation } from '../../types';
2
+ import { type UpdateSessionInput } from '../services/updateSession';
3
+ export declare const useUpdateSessionMutation: Mutation<boolean, UpdateSessionInput>;
@@ -0,0 +1,26 @@
1
+ import { useMutation } from '@tanstack/react-query';
2
+ import { getQueryClient } from '../../utils/getQueryClient.js';
3
+ import { getUpdateSessionMutationKey } from '../../utils/mutationKeys.js';
4
+ import { getSessionQueryKey } from '../../utils/queryKeys.js';
5
+ import { updateSession, } from '../services/updateSession.js';
6
+ export const useUpdateSessionMutation = (config) => {
7
+ const queryClient = getQueryClient();
8
+ return useMutation({
9
+ ...config,
10
+ mutationKey: getUpdateSessionMutationKey(),
11
+ mutationFn: async (input) => {
12
+ const ok = await updateSession(input);
13
+ queryClient.setQueryData(getSessionQueryKey(), (prev) => {
14
+ if (!prev)
15
+ return prev;
16
+ if (!input.domain)
17
+ return prev;
18
+ return {
19
+ ...prev,
20
+ ...input,
21
+ };
22
+ });
23
+ return ok;
24
+ },
25
+ });
26
+ };
@@ -0,0 +1,5 @@
1
+ import { type HttpRequestOptions } from '../../services/httpRequest';
2
+ export interface UpdateSessionInput {
3
+ domain?: string;
4
+ }
5
+ export declare const updateSession: (input: UpdateSessionInput, options?: HttpRequestOptions) => Promise<boolean>;
@@ -0,0 +1,10 @@
1
+ import { cache } from 'react';
2
+ import { httpRequest, } from '../../services/httpRequest.js';
3
+ export const updateSession = cache(async (input, options) => {
4
+ const { ok } = await httpRequest.json('/api/sessions', {
5
+ ...options,
6
+ method: 'PATCH',
7
+ body: JSON.stringify(input),
8
+ });
9
+ return ok;
10
+ });
@@ -8,7 +8,9 @@ import { z } from 'zod';
8
8
  import { useShallow } from 'zustand/shallow';
9
9
  import { useAvailablePromosQuery } from '../../../../client/hooks/useAvailablePromosQuery.js';
10
10
  import { useCreateGCashDepositMutation } from '../../../../client/hooks/useCreateGCashDepositMutation.js';
11
+ import { useDepositQuery } from '../../../../client/hooks/useDepositQuery.js';
11
12
  import { useDepositsCountQuery } from '../../../../client/hooks/useDepositsCountQuery.js';
13
+ import { useDisclosure } from '../../../../client/hooks/useDisclosure.js';
12
14
  import { useGlobalStore } from '../../../../client/hooks/useGlobalStore.js';
13
15
  import { usePaymentSettingsQuery } from '../../../../client/hooks/usePaymentSettingsQuery.js';
14
16
  import { AlertCircleIcon } from '../../../../icons/AlertCircleIcon.js';
@@ -27,24 +29,49 @@ import { useDepositWithdrawalPropsContext } from '../../DepositWithdrawalContext
27
29
  import { AvailablePromos } from '../AvailablePromos.js';
28
30
  export function GCashDeposit() {
29
31
  const depositWithdrawalProps = useDepositWithdrawalPropsContext();
32
+ const disclosure = useDisclosure();
30
33
  const globalStore = useGlobalStore(useShallow((ctx) => ({
31
34
  depositWithdrawal: ctx.depositWithdrawal,
32
35
  })));
33
36
  const [status, setStatus] = useState('waiting');
34
37
  const createDepositMutation = useCreateGCashDepositMutation({
35
38
  onMutate() {
39
+ disclosure.setOpen(true);
36
40
  setStatus('processing');
37
41
  },
38
42
  onSuccess(data) {
39
43
  invariant(data.checkoutUrl);
40
44
  window.open(data.checkoutUrl, '_blank', 'noopener,noreferrer');
41
45
  form.reset();
42
- setStatus('success');
46
+ disclosure.setOpen(false);
43
47
  },
44
48
  onError() {
49
+ disclosure.setOpen(true);
45
50
  setStatus('failed');
46
51
  },
47
52
  });
53
+ const depositQuery = useDepositQuery(createDepositMutation.data?.id, {
54
+ enabled: createDepositMutation.data != null,
55
+ refetchInterval(ctx) {
56
+ if (ctx.state.data?.status === 'CANCELLED' ||
57
+ ctx.state.data?.status === 'CONFIRMED') {
58
+ return false;
59
+ }
60
+ else {
61
+ return 2500;
62
+ }
63
+ },
64
+ });
65
+ useEffect(() => {
66
+ if (depositQuery.data?.status === 'CANCELLED') {
67
+ disclosure.setOpen(true);
68
+ setStatus('failed');
69
+ }
70
+ else if (depositQuery.data?.status === 'CONFIRMED') {
71
+ disclosure.setOpen(true);
72
+ setStatus('success');
73
+ }
74
+ }, [depositQuery.data?.status, disclosure]);
48
75
  const depositsCountQuery = useDepositsCountQuery();
49
76
  const depositsCount = depositsCountQuery.data ?? 0;
50
77
  const paymentSettingsQuery = usePaymentSettingsQuery();
@@ -117,13 +144,13 @@ export function GCashDeposit() {
117
144
  });
118
145
  }
119
146
  }, [form, minimumAmount]);
120
- const handleSubmit = form.handleSubmit(async (data) => {
121
- createDepositMutation.mutate({
122
- amount: data.amount.toString(),
123
- promo: data.promo ?? undefined,
124
- });
125
- });
126
- return (_jsxs("form", { onSubmit: handleSubmit, noValidate: true, children: [_jsx(Controller, { control: form.control, name: "amount", render: (o) => (_jsxs(Field.Root, { invalid: !!form.formState.errors.amount, children: [_jsxs(NumberInput.Root, { min: 0, step: 1, value: o.field.value, onValueChange: (details) => {
147
+ return (_jsxs("form", { onSubmit: form.handleSubmit(async (data) => {
148
+ createDepositMutation.reset();
149
+ createDepositMutation.mutate({
150
+ amount: data.amount.toString(),
151
+ promo: data.promo ?? undefined,
152
+ });
153
+ }), noValidate: true, children: [_jsx(Controller, { control: form.control, name: "amount", render: (o) => (_jsxs(Field.Root, { invalid: !!form.formState.errors.amount, children: [_jsxs(NumberInput.Root, { min: 0, step: 1, value: o.field.value, onValueChange: (details) => {
127
154
  o.field.onChange(details.value);
128
155
  }, formatOptions: {
129
156
  maximumFractionDigits: 2,
@@ -137,11 +164,9 @@ export function GCashDeposit() {
137
164
  }, min: minimumAmount, max: maximumAmount, className: "mt-lg" }), _jsx(Controller, { control: form.control, name: "promo", render: (o) => (_jsx(AvailablePromos, { value: o.field.value, onChange: (value) => {
138
165
  o.field.onChange(value);
139
166
  globalStore.depositWithdrawal.setPromo(null);
140
- }, className: "mt-3xl" })) }), _jsx(Button, { type: "submit", className: "mt-3xl", disabled: createDepositMutation.isPending, children: "Deposit" }), _jsxs("p", { className: "text-text-tertiary-600 mt-lg text-xs", children: ["By depositing, you agree to our", ' ', _jsx(Link, { href: depositWithdrawalProps.termsOfUseUrl ?? '/terms-of-use', onClick: () => globalStore.depositWithdrawal.setOpen(false), className: "text-text-warning-primary-600 underline underline-offset-2", children: "Terms of Use" }), ' ', "and", ' ', _jsx(Link, { href: depositWithdrawalProps.privacyPolicyUrl ?? '/privacy-policy', onClick: () => globalStore.depositWithdrawal.setOpen(false), className: "text-text-warning-primary-600 underline underline-offset-2", children: "Privacy Policy" }), "."] }), _jsx(AlertDialog.Root, { open: status !== 'waiting', onOpenChange: (details) => {
141
- if (!details.open) {
142
- setStatus('waiting');
143
- }
144
- }, lazyMount: true, unmountOnExit: true, children: _jsxs(Portal, { children: [_jsx(AlertDialog.Backdrop, { className: "!z-[calc(var(--z-dialog)+2)]" }), _jsx(AlertDialog.Positioner, { className: "!z-[calc(var(--z-dialog)+3)]", children: _jsxs(AlertDialog.Content, { children: [_jsx(AlertDialog.CloseTrigger, { disabled: status === 'processing', children: _jsx(XIcon, {}) }), _jsxs(AlertDialog.Header, { children: [status === 'processing' && (_jsx(SpinnerIcon, { className: "text-text-brand-primary-600 size-12" })), status === 'success' && (_jsx("div", { className: "bg-bg-success-secondary text-text-featured-icon-light-success flex size-12 items-center justify-center rounded-full", children: _jsx(AlertCircleIcon, {}) })), status === 'failed' && (_jsx("div", { className: "bg-bg-error-secondary text-text-featured-icon-light-error flex size-12 items-center justify-center rounded-full", children: _jsx(AlertCircleIcon, {}) }))] }), _jsxs(AlertDialog.Body, { children: [_jsxs(AlertDialog.Title, { children: [status === 'processing' && 'Processing Deposit', status === 'success' && 'Deposit Successful', status === 'failed' && 'Deposit Failed'] }), _jsxs(AlertDialog.Description, { children: [status === 'processing' &&
167
+ }, className: "mt-3xl" })) }), _jsx(Button, { type: "submit", className: "mt-3xl", disabled: createDepositMutation.isPending, children: "Deposit" }), _jsxs("p", { className: "text-text-tertiary-600 mt-lg text-xs", children: ["By depositing, you agree to our", ' ', _jsx(Link, { href: depositWithdrawalProps.termsOfUseUrl ?? '/terms-of-use', onClick: () => globalStore.depositWithdrawal.setOpen(false), className: "text-text-warning-primary-600 underline underline-offset-2", children: "Terms of Use" }), ' ', "and", ' ', _jsx(Link, { href: depositWithdrawalProps.privacyPolicyUrl ?? '/privacy-policy', onClick: () => globalStore.depositWithdrawal.setOpen(false), className: "text-text-warning-primary-600 underline underline-offset-2", children: "Privacy Policy" }), "."] }), _jsx(AlertDialog.Root, { open: disclosure.open, onOpenChange: (details) => {
168
+ disclosure.setOpen(details.open);
169
+ }, lazyMount: true, unmountOnExit: true, children: _jsxs(Portal, { children: [_jsx(AlertDialog.Backdrop, { className: "!z-[calc(var(--z-dialog)+2)]" }), _jsx(AlertDialog.Positioner, { className: "!z-[calc(var(--z-dialog)+3)]", children: _jsxs(AlertDialog.Content, { children: [_jsx(AlertDialog.CloseTrigger, { children: _jsx(XIcon, {}) }), _jsxs(AlertDialog.Header, { children: [status === 'processing' && (_jsx(SpinnerIcon, { className: "text-text-brand-primary-600 size-12" })), status === 'success' && (_jsx("div", { className: "bg-bg-success-secondary text-text-featured-icon-light-success flex size-12 items-center justify-center rounded-full", children: _jsx(AlertCircleIcon, {}) })), status === 'failed' && (_jsx("div", { className: "bg-bg-error-secondary text-text-featured-icon-light-error flex size-12 items-center justify-center rounded-full", children: _jsx(AlertCircleIcon, {}) }))] }), _jsxs(AlertDialog.Body, { children: [_jsxs(AlertDialog.Title, { children: [status === 'processing' && 'Processing Deposit', status === 'success' && 'Deposit Successful', status === 'failed' && 'Deposit Failed'] }), _jsxs(AlertDialog.Description, { children: [status === 'processing' &&
145
170
  "We're verifying your account and amount. Please hold a moment.", status === 'success' &&
146
171
  'Your deposit has been successfully processed.', status === 'failed' &&
147
172
  'Something went wrong while processing your deposit. Please try again or contact support.'] })] }), (status === 'failed' || status === 'success') && (_jsx(AlertDialog.Footer, { children: _jsx(AlertDialog.Context, { children: (api) => (_jsx(Button, { onClick: () => {
@@ -8,7 +8,9 @@ import { z } from 'zod';
8
8
  import { useShallow } from 'zustand/shallow';
9
9
  import { useAvailablePromosQuery } from '../../../../client/hooks/useAvailablePromosQuery.js';
10
10
  import { useCreateMayaDepositMutation } from '../../../../client/hooks/useCreateMayaDepositMutation.js';
11
+ import { useDepositQuery } from '../../../../client/hooks/useDepositQuery.js';
11
12
  import { useDepositsCountQuery } from '../../../../client/hooks/useDepositsCountQuery.js';
13
+ import { useDisclosure } from '../../../../client/hooks/useDisclosure.js';
12
14
  import { useGlobalStore } from '../../../../client/hooks/useGlobalStore.js';
13
15
  import { usePaymentSettingsQuery } from '../../../../client/hooks/usePaymentSettingsQuery.js';
14
16
  import { AlertCircleIcon } from '../../../../icons/AlertCircleIcon.js';
@@ -27,24 +29,49 @@ import { useDepositWithdrawalPropsContext } from '../../DepositWithdrawalContext
27
29
  import { AvailablePromos } from '../AvailablePromos.js';
28
30
  export function MayaDeposit() {
29
31
  const depositWithdrawalProps = useDepositWithdrawalPropsContext();
32
+ const disclosure = useDisclosure();
30
33
  const globalStore = useGlobalStore(useShallow((ctx) => ({
31
34
  depositWithdrawal: ctx.depositWithdrawal,
32
35
  })));
33
36
  const [status, setStatus] = useState('waiting');
34
37
  const createDepositMutation = useCreateMayaDepositMutation({
35
38
  onMutate() {
39
+ disclosure.setOpen(true);
36
40
  setStatus('processing');
37
41
  },
38
42
  onSuccess(data) {
39
43
  invariant(data.checkoutUrl);
40
44
  window.open(data.checkoutUrl, '_blank', 'noopener,noreferrer');
41
45
  form.reset();
42
- setStatus('success');
46
+ disclosure.setOpen(false);
43
47
  },
44
48
  onError() {
49
+ disclosure.setOpen(true);
45
50
  setStatus('failed');
46
51
  },
47
52
  });
53
+ const depositQuery = useDepositQuery(createDepositMutation.data?.id, {
54
+ enabled: createDepositMutation.data != null,
55
+ refetchInterval(ctx) {
56
+ if (ctx.state.data?.status === 'CANCELLED' ||
57
+ ctx.state.data?.status === 'CONFIRMED') {
58
+ return false;
59
+ }
60
+ else {
61
+ return 2500;
62
+ }
63
+ },
64
+ });
65
+ useEffect(() => {
66
+ if (depositQuery.data?.status === 'CANCELLED') {
67
+ disclosure.setOpen(true);
68
+ setStatus('failed');
69
+ }
70
+ else if (depositQuery.data?.status === 'CONFIRMED') {
71
+ disclosure.setOpen(true);
72
+ setStatus('success');
73
+ }
74
+ }, [depositQuery.data?.status, disclosure]);
48
75
  const depositsCountQuery = useDepositsCountQuery();
49
76
  const depositsCount = depositsCountQuery.data ?? 0;
50
77
  const paymentSettingsQuery = usePaymentSettingsQuery();
@@ -117,13 +144,13 @@ export function MayaDeposit() {
117
144
  });
118
145
  }
119
146
  }, [form, minimumAmount]);
120
- const handleSubmit = form.handleSubmit(async (data) => {
121
- createDepositMutation.mutate({
122
- amount: data.amount.toString(),
123
- promo: data.promo ?? undefined,
124
- });
125
- });
126
- return (_jsxs("form", { onSubmit: handleSubmit, noValidate: true, children: [_jsx(Controller, { control: form.control, name: "amount", render: (o) => (_jsxs(Field.Root, { invalid: !!form.formState.errors.amount, children: [_jsxs(NumberInput.Root, { min: 0, step: 1, value: o.field.value, onValueChange: (details) => {
147
+ return (_jsxs("form", { onSubmit: form.handleSubmit(async (data) => {
148
+ createDepositMutation.reset();
149
+ createDepositMutation.mutate({
150
+ amount: data.amount.toString(),
151
+ promo: data.promo ?? undefined,
152
+ });
153
+ }), noValidate: true, children: [_jsx(Controller, { control: form.control, name: "amount", render: (o) => (_jsxs(Field.Root, { invalid: !!form.formState.errors.amount, children: [_jsxs(NumberInput.Root, { min: 0, step: 1, value: o.field.value, onValueChange: (details) => {
127
154
  o.field.onChange(details.value);
128
155
  }, formatOptions: {
129
156
  maximumFractionDigits: 2,
@@ -137,11 +164,9 @@ export function MayaDeposit() {
137
164
  }, min: minimumAmount, max: maximumAmount, className: "mt-lg" }), _jsx(Controller, { control: form.control, name: "promo", render: (o) => (_jsx(AvailablePromos, { value: o.field.value, onChange: (value) => {
138
165
  o.field.onChange(value);
139
166
  globalStore.depositWithdrawal.setPromo(null);
140
- }, className: "mt-3xl" })) }), _jsx(Button, { type: "submit", className: "mt-3xl", disabled: createDepositMutation.isPending, children: "Deposit" }), _jsxs("p", { className: "text-text-tertiary-600 mt-lg text-xs", children: ["By depositing, you agree to our", ' ', _jsx(Link, { href: depositWithdrawalProps.termsOfUseUrl ?? '/terms-of-use', onClick: () => globalStore.depositWithdrawal.setOpen(false), className: "text-text-warning-primary-600 underline underline-offset-2", children: "Terms of Use" }), ' ', "and", ' ', _jsx(Link, { href: depositWithdrawalProps.privacyPolicyUrl ?? '/privacy-policy', onClick: () => globalStore.depositWithdrawal.setOpen(false), className: "text-text-warning-primary-600 underline underline-offset-2", children: "Privacy Policy" }), "."] }), _jsx(AlertDialog.Root, { open: status !== 'waiting', onOpenChange: (details) => {
141
- if (!details.open) {
142
- setStatus('waiting');
143
- }
144
- }, lazyMount: true, unmountOnExit: true, children: _jsxs(Portal, { children: [_jsx(AlertDialog.Backdrop, { className: "!z-[calc(var(--z-dialog)+2)]" }), _jsx(AlertDialog.Positioner, { className: "!z-[calc(var(--z-dialog)+3)]", children: _jsxs(AlertDialog.Content, { children: [_jsx(AlertDialog.CloseTrigger, { disabled: status === 'processing', children: _jsx(XIcon, {}) }), _jsxs(AlertDialog.Header, { children: [status === 'processing' && (_jsx(SpinnerIcon, { className: "text-text-brand-primary-600 size-12" })), status === 'success' && (_jsx("div", { className: "bg-bg-success-secondary text-text-featured-icon-light-success flex size-12 items-center justify-center rounded-full", children: _jsx(AlertCircleIcon, {}) })), status === 'failed' && (_jsx("div", { className: "bg-bg-error-secondary text-text-featured-icon-light-error flex size-12 items-center justify-center rounded-full", children: _jsx(AlertCircleIcon, {}) }))] }), _jsxs(AlertDialog.Body, { children: [_jsxs(AlertDialog.Title, { children: [status === 'processing' && 'Processing Deposit', status === 'success' && 'Deposit Successful', status === 'failed' && 'Deposit Failed'] }), _jsxs(AlertDialog.Description, { children: [status === 'processing' &&
167
+ }, className: "mt-3xl" })) }), _jsx(Button, { type: "submit", className: "mt-3xl", disabled: createDepositMutation.isPending, children: "Deposit" }), _jsxs("p", { className: "text-text-tertiary-600 mt-lg text-xs", children: ["By depositing, you agree to our", ' ', _jsx(Link, { href: depositWithdrawalProps.termsOfUseUrl ?? '/terms-of-use', onClick: () => globalStore.depositWithdrawal.setOpen(false), className: "text-text-warning-primary-600 underline underline-offset-2", children: "Terms of Use" }), ' ', "and", ' ', _jsx(Link, { href: depositWithdrawalProps.privacyPolicyUrl ?? '/privacy-policy', onClick: () => globalStore.depositWithdrawal.setOpen(false), className: "text-text-warning-primary-600 underline underline-offset-2", children: "Privacy Policy" }), "."] }), _jsx(AlertDialog.Root, { open: disclosure.open, onOpenChange: (details) => {
168
+ disclosure.setOpen(details.open);
169
+ }, lazyMount: true, unmountOnExit: true, children: _jsxs(Portal, { children: [_jsx(AlertDialog.Backdrop, { className: "!z-[calc(var(--z-dialog)+2)]" }), _jsx(AlertDialog.Positioner, { className: "!z-[calc(var(--z-dialog)+3)]", children: _jsxs(AlertDialog.Content, { children: [_jsx(AlertDialog.CloseTrigger, { children: _jsx(XIcon, {}) }), _jsxs(AlertDialog.Header, { children: [status === 'processing' && (_jsx(SpinnerIcon, { className: "text-text-brand-primary-600 size-12" })), status === 'success' && (_jsx("div", { className: "bg-bg-success-secondary text-text-featured-icon-light-success flex size-12 items-center justify-center rounded-full", children: _jsx(AlertCircleIcon, {}) })), status === 'failed' && (_jsx("div", { className: "bg-bg-error-secondary text-text-featured-icon-light-error flex size-12 items-center justify-center rounded-full", children: _jsx(AlertCircleIcon, {}) }))] }), _jsxs(AlertDialog.Body, { children: [_jsxs(AlertDialog.Title, { children: [status === 'processing' && 'Processing Deposit', status === 'success' && 'Deposit Successful', status === 'failed' && 'Deposit Failed'] }), _jsxs(AlertDialog.Description, { children: [status === 'processing' &&
145
170
  "We're verifying your account and amount. Please hold a moment.", status === 'success' &&
146
171
  'Your deposit has been successfully processed.', status === 'failed' &&
147
172
  'Something went wrong while processing your deposit. Please try again or contact support.'] })] }), (status === 'failed' || status === 'success') && (_jsx(AlertDialog.Footer, { children: _jsx(AlertDialog.Context, { children: (api) => (_jsx(Button, { onClick: () => {
@@ -1,4 +1,4 @@
1
- import type { ReactNode } from 'react';
1
+ import { type ReactNode } from 'react';
2
2
  export interface PortalProviderProps {
3
3
  googleAnalyticsId?: string;
4
4
  googleTagManagerId?: string;
@@ -1,6 +1,7 @@
1
- import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
1
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
2
  import { GoogleAnalytics, GoogleTagManager } from '@next/third-parties/google';
3
3
  import { dehydrate, HydrationBoundary } from '@tanstack/react-query';
4
+ import { Suspense } from 'react';
4
5
  import { prefetchAccountQuery } from '../../server/utils/prefetchAccountQuery.js';
5
6
  import { prefetchPlatformQuery } from '../../server/utils/prefetchPlatformQuery.js';
6
7
  import { prefetchSessionQuery } from '../../server/utils/prefetchSessionQuery.js';
@@ -8,6 +9,7 @@ import { prefetchWalletQuery } from '../../server/utils/prefetchWalletQuery.js';
8
9
  import { FacebookPixel, GoogleRecaptcha } from '../../third-parties/index.js';
9
10
  import { getQueryClient } from '../../utils/getQueryClient.js';
10
11
  import { Providers } from './Providers.js';
12
+ import { SetupDomain } from './SetupDomain.js';
11
13
  import { Snackbar } from './Snackbar.js';
12
14
  import { WebVitals } from './WebVitals.js';
13
15
  export async function PortalProvider({ children, facebookPixelId, googleAnalyticsId, googleTagManagerId, googleRecaptchaSiteKey, }) {
@@ -18,5 +20,5 @@ export async function PortalProvider({ children, facebookPixelId, googleAnalytic
18
20
  prefetchAccountQuery(),
19
21
  prefetchWalletQuery(),
20
22
  ]);
21
- return (_jsxs(_Fragment, { children: [_jsx(WebVitals, {}), _jsx(Providers, { children: _jsx(HydrationBoundary, { state: dehydrate(queryClient), children: children }) }), _jsx(Snackbar, {}), facebookPixelId && _jsx(FacebookPixel, { fbId: facebookPixelId }), googleAnalyticsId && _jsx(GoogleAnalytics, { gaId: googleAnalyticsId }), googleTagManagerId && _jsx(GoogleTagManager, { gtmId: googleTagManagerId }), googleRecaptchaSiteKey && (_jsx(GoogleRecaptcha, { siteKey: googleRecaptchaSiteKey }))] }));
23
+ return (_jsxs(_Fragment, { children: [_jsx(WebVitals, {}), _jsx(Providers, { children: _jsxs(HydrationBoundary, { state: dehydrate(queryClient), children: [children, _jsx(Suspense, { fallback: null, children: _jsx(SetupDomain, {}) })] }) }), _jsx(Snackbar, {}), facebookPixelId && _jsx(FacebookPixel, { fbId: facebookPixelId }), googleAnalyticsId && _jsx(GoogleAnalytics, { gaId: googleAnalyticsId }), googleTagManagerId && _jsx(GoogleTagManager, { gtmId: googleTagManagerId }), googleRecaptchaSiteKey && (_jsx(GoogleRecaptcha, { siteKey: googleRecaptchaSiteKey }))] }));
22
24
  }
@@ -0,0 +1 @@
1
+ export declare function SetupDomain(): null;
@@ -0,0 +1,18 @@
1
+ 'use client';
2
+ import { useSearchParams } from 'next/navigation';
3
+ import { useTimeout } from 'usehooks-ts';
4
+ import { useSessionQuery } from '../../client/hooks/useSessionQuery.js';
5
+ import { useUpdateSessionMutation } from '../../client/hooks/useUpdateSessionMutation.js';
6
+ export function SetupDomain() {
7
+ const searchParams = useSearchParams();
8
+ const sessionQuery = useSessionQuery();
9
+ const updateSessionMutation = useUpdateSessionMutation();
10
+ useTimeout(() => {
11
+ const market = searchParams.get('m');
12
+ const domain = `${window.location.host}/${market}`;
13
+ if (domain === sessionQuery.data?.domain)
14
+ return;
15
+ updateSessionMutation.mutate({ domain });
16
+ }, sessionQuery.isPending ? null : searchParams.has('m') ? 1000 : null);
17
+ return null;
18
+ }
@@ -36,3 +36,8 @@ export declare const POST: (request: NextRequest, { params }: {
36
36
  auth: string[];
37
37
  }>;
38
38
  }) => Promise<NextResponse>;
39
+ export declare const PATCH: (request: NextRequest, { params }: {
40
+ params: Promise<{
41
+ auth: string[];
42
+ }>;
43
+ }) => Promise<NextResponse>;
package/dist/handlers.js CHANGED
@@ -62,7 +62,7 @@ export const GET = async (request, { params }) => {
62
62
  if (path === 'sessions') {
63
63
  const accessToken = request.cookies.get(ACCESS_TOKEN_COOKIE_NAME)?.value;
64
64
  const refreshToken = request.cookies.get(REFRESH_TOKEN_COOKIE_NAME)?.value;
65
- const domain = request.cookies.get(DOMAIN_COOKIE_NAME)?.value ?? request.nextUrl.origin;
65
+ const domain = request.cookies.get(DOMAIN_COOKIE_NAME)?.value ?? request.nextUrl.host;
66
66
  if (!refreshToken) {
67
67
  const response = NextResponse.json({
68
68
  ok: true,
@@ -260,3 +260,38 @@ export const POST = async (request, { params }) => {
260
260
  message: 'Not found',
261
261
  }, { status: 404 });
262
262
  };
263
+ const UpdateSessionDefinition = z.object({
264
+ domain: z.string().optional().nullable(),
265
+ });
266
+ export const PATCH = async (request, { params }) => {
267
+ const { auth } = await params;
268
+ const path = auth[0];
269
+ /*
270
+ *
271
+ * PATCH -> /api/sessions
272
+ *
273
+ */
274
+ if (path === 'sessions') {
275
+ const body = await request.json();
276
+ const parsed = UpdateSessionDefinition.safeParse(body);
277
+ if (!parsed.success) {
278
+ return NextResponse.json({
279
+ ok: false,
280
+ message: parsed.error.issues[0].message,
281
+ }, { status: 400 });
282
+ }
283
+ const response = NextResponse.json({ ok: true });
284
+ if (parsed.data.domain) {
285
+ response.cookies.set(DOMAIN_COOKIE_NAME, parsed.data.domain, {
286
+ expires: addDays(new Date(), 30),
287
+ httpOnly: true,
288
+ sameSite: 'strict',
289
+ });
290
+ }
291
+ return response;
292
+ }
293
+ return NextResponse.json({
294
+ ok: false,
295
+ message: 'Not found',
296
+ }, { status: 404 });
297
+ };
@@ -1,25 +1,11 @@
1
- import { addDays, addMinutes } from 'date-fns';
1
+ import { addMinutes } from 'date-fns';
2
2
  import { NextFetchEvent, NextResponse, } from 'next/server';
3
- import { ACCESS_TOKEN_COOKIE_NAME, DOMAIN_COOKIE_NAME, REFRESH_TOKEN_COOKIE_NAME, } from './constants/index.js';
3
+ import { ACCESS_TOKEN_COOKIE_NAME, REFRESH_TOKEN_COOKIE_NAME, } from './constants/index.js';
4
4
  import { refreshSession } from './services/auth.js';
5
5
  export const middleware = async (req) => {
6
6
  const accessToken = req.cookies.get(ACCESS_TOKEN_COOKIE_NAME)?.value;
7
7
  const refreshToken = req.cookies.get(REFRESH_TOKEN_COOKIE_NAME)?.value;
8
8
  const res = NextResponse.next();
9
- if (req.nextUrl.searchParams.has('m')) {
10
- res.cookies.set(DOMAIN_COOKIE_NAME, `${req.nextUrl.hostname}/${req.nextUrl.searchParams.get('m')}`, {
11
- expires: addDays(new Date(), 30),
12
- httpOnly: true,
13
- sameSite: 'strict',
14
- });
15
- }
16
- if (!res.cookies.has(DOMAIN_COOKIE_NAME)) {
17
- res.cookies.set(DOMAIN_COOKIE_NAME, req.nextUrl.origin, {
18
- expires: addDays(new Date(), 30),
19
- httpOnly: true,
20
- sameSite: 'strict',
21
- });
22
- }
23
9
  if (!accessToken && refreshToken) {
24
10
  try {
25
11
  const data = await refreshSession({
@@ -5,9 +5,10 @@ export const getSession = cache(async () => {
5
5
  const Cookies = await cookies();
6
6
  const Headers = await headers();
7
7
  const token = Cookies.get(ACCESS_TOKEN_COOKIE_NAME)?.value;
8
- const headerProto = Headers.get('x-forwarded-proto') ?? 'http';
9
- const headerHost = Headers.get('x-forwarded-host') ?? 'localhost';
10
- const domain = Cookies.get(DOMAIN_COOKIE_NAME)?.value ?? `${headerProto}://${headerHost}`;
8
+ const domain = Cookies.get(DOMAIN_COOKIE_NAME)?.value ??
9
+ Headers.get('host') ??
10
+ Headers.get('x-forwarded-host') ??
11
+ 'localhost';
11
12
  return token
12
13
  ? {
13
14
  status: 'authenticated',
@@ -30,3 +30,4 @@ export declare const getCompleteOnboardingMutationKey: () => MutationKey;
30
30
  export declare const getSkipOnboardingMutationKey: () => MutationKey;
31
31
  export declare const getUploadImageFileMutationKey: () => MutationKey;
32
32
  export declare const getResetPasswordMutationKey: () => MutationKey;
33
+ export declare const getUpdateSessionMutationKey: () => MutationKey;
@@ -114,3 +114,7 @@ export const getResetPasswordMutationKey = () => [
114
114
  PARENT_KEY,
115
115
  'resetPassword',
116
116
  ];
117
+ export const getUpdateSessionMutationKey = () => [
118
+ PARENT_KEY,
119
+ 'updateSession',
120
+ ];
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@opexa/portal-components",
3
- "version": "0.0.175",
3
+ "version": "0.0.177",
4
4
  "exports": {
5
5
  "./ui/*": {
6
6
  "types": "./dist/ui/*/index.d.ts",