feat: add success and fail payment pages, fix payment system
This commit is contained in:
parent
237dec5681
commit
1fc35e973d
BIN
public/ExclamationIcon.png
Normal file
BIN
public/ExclamationIcon.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 3.7 KiB |
BIN
public/SuccessIcon.png
Normal file
BIN
public/SuccessIcon.png
Normal file
Binary file not shown.
|
After Width: | Height: | Size: 1.7 KiB |
@ -1,85 +1,121 @@
|
||||
import routes from "@/routes"
|
||||
import { AuthPayload } from "../types"
|
||||
import { getAuthHeaders } from "../utils"
|
||||
import routes from "@/routes";
|
||||
import { AuthPayload } from "../types";
|
||||
import { getAuthHeaders } from "../utils";
|
||||
|
||||
export interface GetPayload extends AuthPayload {
|
||||
id: string
|
||||
id: string;
|
||||
}
|
||||
|
||||
export interface ChargebeeReceiptPayload extends AuthPayload {
|
||||
itemPriceId: string
|
||||
gwToken: string
|
||||
referenceId?: string
|
||||
itemPriceId: string;
|
||||
gwToken: string;
|
||||
referenceId?: string;
|
||||
}
|
||||
|
||||
export interface AppleReceiptPayload extends AuthPayload {
|
||||
receiptData: string
|
||||
autorenewable?: boolean
|
||||
sandbox?: boolean
|
||||
receiptData: string;
|
||||
autorenewable?: boolean;
|
||||
sandbox?: boolean;
|
||||
}
|
||||
|
||||
export type Payload = ChargebeeReceiptPayload | AppleReceiptPayload
|
||||
export interface StripeReceiptPayload extends AuthPayload {
|
||||
itemInterval: "week" | "month" | "year";
|
||||
}
|
||||
|
||||
export type Payload =
|
||||
| ChargebeeReceiptPayload
|
||||
| AppleReceiptPayload
|
||||
| StripeReceiptPayload;
|
||||
|
||||
export interface Response {
|
||||
subscription_receipt: SubscriptionReceipt
|
||||
subscription_receipt: SubscriptionReceipt;
|
||||
}
|
||||
|
||||
export interface SubscriptionReceipt {
|
||||
id: string
|
||||
user_id: number
|
||||
status: number
|
||||
expires_at: null | string
|
||||
requested_at: string
|
||||
created_at: string
|
||||
id: string;
|
||||
user_id: number;
|
||||
status: number;
|
||||
expires_at: null | string;
|
||||
requested_at: string;
|
||||
created_at: string;
|
||||
data: {
|
||||
input: {
|
||||
subscription_items: [
|
||||
{
|
||||
item_price_id: string
|
||||
item_price_id: string;
|
||||
}
|
||||
],
|
||||
];
|
||||
payment_intent: {
|
||||
gw_token: string
|
||||
gateway_account_id: string
|
||||
}
|
||||
},
|
||||
app_bundle_id: string
|
||||
autorenewable: boolean
|
||||
error: string
|
||||
}
|
||||
gw_token: string;
|
||||
gateway_account_id: string;
|
||||
};
|
||||
};
|
||||
client_secret: string;
|
||||
app_bundle_id: string;
|
||||
autorenewable: boolean;
|
||||
error: string;
|
||||
};
|
||||
}
|
||||
|
||||
function createRequest({ token, itemPriceId, gwToken, referenceId }: ChargebeeReceiptPayload): Request
|
||||
function createRequest({ token, receiptData, autorenewable = true, sandbox = true }: AppleReceiptPayload): Request
|
||||
function createRequest(payload: Payload): Request
|
||||
function createRequest({
|
||||
token,
|
||||
itemPriceId,
|
||||
gwToken,
|
||||
referenceId,
|
||||
}: ChargebeeReceiptPayload): Request;
|
||||
function createRequest({
|
||||
token,
|
||||
receiptData,
|
||||
autorenewable = true,
|
||||
sandbox = true,
|
||||
}: AppleReceiptPayload): Request;
|
||||
function createRequest({ token, itemInterval }: StripeReceiptPayload): Request;
|
||||
function createRequest(payload: Payload): Request;
|
||||
function createRequest(payload: Payload): Request {
|
||||
const url = new URL(routes.server.subscriptionReceipts())
|
||||
const data = isChargebeeReceipt(payload) ? {
|
||||
way: 'chargebee',
|
||||
subscription_receipt: {
|
||||
item_price_id: payload.itemPriceId,
|
||||
gw_token: payload.gwToken,
|
||||
reference_id: payload.referenceId,
|
||||
}
|
||||
} : {
|
||||
way: 'apple',
|
||||
subscription_receipt: {
|
||||
receipt_data: payload.receiptData,
|
||||
autorenewable: payload.autorenewable,
|
||||
sandbox: payload.sandbox,
|
||||
}
|
||||
}
|
||||
const body = JSON.stringify(data)
|
||||
return new Request(url, { method: 'POST', headers: getAuthHeaders(payload.token), body })
|
||||
const url = new URL(routes.server.subscriptionReceipts());
|
||||
const data = getDataPayload(payload);
|
||||
const body = JSON.stringify(data);
|
||||
return new Request(url, {
|
||||
method: "POST",
|
||||
headers: getAuthHeaders(payload.token),
|
||||
body,
|
||||
});
|
||||
}
|
||||
|
||||
function isChargebeeReceipt(payload: Payload ): payload is ChargebeeReceiptPayload {
|
||||
return 'itemPriceId' in payload && 'gwToken' in payload
|
||||
function getDataPayload(payload: Payload) {
|
||||
if ("itemPriceId" in payload && "gwToken" in payload) {
|
||||
return {
|
||||
way: "chargebee",
|
||||
subscription_receipt: {
|
||||
item_price_id: payload.itemPriceId,
|
||||
gw_token: payload.gwToken,
|
||||
reference_id: payload.referenceId,
|
||||
},
|
||||
};
|
||||
}
|
||||
if ("receiptData" in payload) {
|
||||
return {
|
||||
way: "apple",
|
||||
subscription_receipt: {
|
||||
receipt_data: payload.receiptData,
|
||||
autorenewable: payload.autorenewable,
|
||||
sandbox: payload.sandbox,
|
||||
},
|
||||
};
|
||||
}
|
||||
if ("itemInterval" in payload) {
|
||||
return {
|
||||
way: "stripe",
|
||||
subscription_receipt: {
|
||||
item_interval: payload.itemInterval,
|
||||
},
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
function createGetRequest({ id, token }: GetPayload): Request {
|
||||
const url = new URL(routes.server.subscriptionReceipt(id))
|
||||
return new Request(url, { method: 'GET', headers: getAuthHeaders(token) })
|
||||
const url = new URL(routes.server.subscriptionReceipt(id));
|
||||
return new Request(url, { method: "GET", headers: getAuthHeaders(token) });
|
||||
}
|
||||
|
||||
export { createRequest, createGetRequest }
|
||||
export { createRequest, createGetRequest };
|
||||
|
||||
@ -45,12 +45,16 @@ import { EPathsFromHome } from "@/store/siteConfig";
|
||||
import parseAPNG, { APNG } from "apng-js";
|
||||
import { useApi, useApiCall } from "@/api";
|
||||
import { Asset } from "@/api/resources/Assets";
|
||||
import PaymentResultPage from "../PaymentPage/results";
|
||||
import PaymentSuccessPage from "../PaymentPage/results/SuccessPage";
|
||||
import PaymentFailPage from "../PaymentPage/results/ErrorPage";
|
||||
|
||||
function App(): JSX.Element {
|
||||
const [isSpecialOfferOpen, setIsSpecialOfferOpen] = useState<boolean>(false);
|
||||
const [leoApng, setLeoApng] = useState<Error | APNG>(Error);
|
||||
const navigate = useNavigate();
|
||||
const api = useApi();
|
||||
const dispatch = useDispatch();
|
||||
|
||||
const closeSpecialOfferAttention = () => {
|
||||
setIsSpecialOfferOpen(false);
|
||||
@ -66,6 +70,15 @@ function App(): JSX.Element {
|
||||
|
||||
const { data } = useApiCall<Asset[]>(assetsData);
|
||||
|
||||
useEffect(() => {
|
||||
// TODO: remove later
|
||||
dispatch(
|
||||
actions.token.update(
|
||||
"eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOjQwNjEyLCJpYXQiOjE2OTc5MjY0MTksImV4cCI6MTcwNjU2NjQxOSwianRpIjoiZTg0NWE0ZmUtYmVmNy00ODNmLWIwMzgtYjlkYzBlZjk1MjNmIiwiZW1haWwiOiJvdGhlcjJAZXhhbXBsZS5jb20iLCJzdGF0ZSI6InByb3ZlbiIsImxvYyI6ImVuIiwidHoiOjAsInR5cGUiOiJlbWFpbCIsImlzcyI6ImNvbS5saWZlLmF1cmEifQ.ijaHDiNRLUIKdkziVB-zt8DA8WNH7RNwvYkp2EGDxTM"
|
||||
)
|
||||
);
|
||||
}, [dispatch]);
|
||||
|
||||
useEffect(() => {
|
||||
async function getApng() {
|
||||
if (!data) return;
|
||||
@ -125,6 +138,9 @@ function App(): JSX.Element {
|
||||
element={<SubscriptionPage />}
|
||||
/>
|
||||
<Route path={routes.client.paymentMethod()} element={<PaymentPage />} />
|
||||
<Route path={routes.client.paymentResult()} element={<PaymentResultPage />} />
|
||||
<Route path={routes.client.paymentSuccess()} element={<PaymentSuccessPage />} />
|
||||
<Route path={routes.client.paymentFail()} element={<PaymentFailPage />} />
|
||||
<Route
|
||||
path={routes.client.wallpaper()}
|
||||
element={<ProtectWallpaperPage />}
|
||||
|
||||
@ -67,8 +67,8 @@ function BreathPage({ leoApng }: BreathPageProps): JSX.Element {
|
||||
setIsOpenModal(false);
|
||||
};
|
||||
|
||||
const token =
|
||||
"eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOjIzNjEyLCJpYXQiOjE2OTM0MTg5MTAsImV4cCI6MTcwMjA1ODkxMCwianRpIjoiNzg5MjkwYWItODg0YS00MGUyLTkyNjEtOWI2OGEyNjkwNmE0IiwiZW1haWwiOiJvdGhlckBleGFtcGxlLmNvbSIsInN0YXRlIjoicHJvdmVuIiwibG9jIjoiZW4iLCJ0eiI6LTI4ODAwLCJ0eXBlIjoiZW1haWwiLCJpc3MiOiJjb20ubGlmZS5hdXJhIn0.J2ocWIv5jKzuKMcwMgWMiNMyGg5qLlMAeln-bQm_9lw";
|
||||
|
||||
const token = useSelector(selectors.selectToken)
|
||||
const createCallback = useCallback(async () => {
|
||||
const data: UserCallbacks.PayloadPost = {
|
||||
data: {
|
||||
@ -100,7 +100,7 @@ function BreathPage({ leoApng }: BreathPageProps): JSX.Element {
|
||||
}
|
||||
|
||||
return createCallbackRequest.user_callback;
|
||||
}, [api, dispatch]);
|
||||
}, [api, dispatch, token]);
|
||||
|
||||
useApiCall<UserCallbacks.IUserCallbacks>(createCallback);
|
||||
|
||||
|
||||
@ -12,8 +12,7 @@ import FullScreenModal from "../FullScreenModal";
|
||||
import CompatibilityLoading from "../CompatibilityLoading";
|
||||
|
||||
function CompatResultPage(): JSX.Element {
|
||||
const token =
|
||||
"eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOjIzNjEyLCJpYXQiOjE2OTM0MTg5MTAsImV4cCI6MTcwMjA1ODkxMCwianRpIjoiNzg5MjkwYWItODg0YS00MGUyLTkyNjEtOWI2OGEyNjkwNmE0IiwiZW1haWwiOiJvdGhlckBleGFtcGxlLmNvbSIsInN0YXRlIjoicHJvdmVuIiwibG9jIjoiZW4iLCJ0eiI6LTI4ODAwLCJ0eXBlIjoiZW1haWwiLCJpc3MiOiJjb20ubGlmZS5hdXJhIn0.J2ocWIv5jKzuKMcwMgWMiNMyGg5qLlMAeln-bQm_9lw";
|
||||
const token = useSelector(selectors.selectToken)
|
||||
const { t } = useTranslation();
|
||||
const navigate = useNavigate();
|
||||
const api = useApi();
|
||||
@ -82,7 +81,7 @@ function CompatResultPage(): JSX.Element {
|
||||
setText(aICompat?.compat?.body || "Loading...");
|
||||
|
||||
return aICompat.compat;
|
||||
}, [api, rightUser, categoryId, birthdate]);
|
||||
}, [api, rightUser, categoryId, birthdate, token]);
|
||||
|
||||
useApiCall<AICompats.ICompat | AIRequests.IAiRequest>(loadData);
|
||||
|
||||
|
||||
@ -34,8 +34,7 @@ const buttonTextFormatter = (text: string): JSX.Element => {
|
||||
};
|
||||
|
||||
function HomePage(): JSX.Element {
|
||||
const token =
|
||||
"eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOjIzNjEyLCJpYXQiOjE2OTM0MTg5MTAsImV4cCI6MTcwMjA1ODkxMCwianRpIjoiNzg5MjkwYWItODg0YS00MGUyLTkyNjEtOWI2OGEyNjkwNmE0IiwiZW1haWwiOiJvdGhlckBleGFtcGxlLmNvbSIsInN0YXRlIjoicHJvdmVuIiwibG9jIjoiZW4iLCJ0eiI6LTI4ODAwLCJ0eXBlIjoiZW1haWwiLCJpc3MiOiJjb20ubGlmZS5hdXJhIn0.J2ocWIv5jKzuKMcwMgWMiNMyGg5qLlMAeln-bQm_9lw";
|
||||
const token = useSelector(selectors.selectToken)
|
||||
const { t } = useTranslation();
|
||||
const navigate = useNavigate();
|
||||
const dispatch = useDispatch();
|
||||
|
||||
@ -23,20 +23,15 @@ export default function CheckoutForm() {
|
||||
|
||||
setIsProcessing(true);
|
||||
|
||||
const { error, paymentIntent } = await stripe.confirmPayment({
|
||||
const { error } = await stripe.confirmPayment({
|
||||
elements,
|
||||
confirmParams: {
|
||||
return_url: window.location.href,
|
||||
},
|
||||
redirect: "if_required",
|
||||
return_url: `https://${window.location.host}/payment/result`,
|
||||
}
|
||||
});
|
||||
|
||||
if (error) {
|
||||
setMessage(error?.message || "Oops! Something went wrong.");
|
||||
} else if (paymentIntent && paymentIntent.status === "succeeded") {
|
||||
setMessage("Payment succeeded!");
|
||||
} else {
|
||||
setMessage("Unexpected state");
|
||||
}
|
||||
|
||||
setIsProcessing(false);
|
||||
|
||||
@ -5,6 +5,7 @@ import { useEffect, useState } from "react";
|
||||
import { Stripe, loadStripe } from "@stripe/stripe-js";
|
||||
import { Elements } from "@stripe/react-stripe-js";
|
||||
import CheckoutForm from "./CheckoutForm";
|
||||
import { useAuth } from "@/auth";
|
||||
|
||||
interface StripeModalProps {
|
||||
open: boolean;
|
||||
@ -16,14 +17,15 @@ interface StripeModalProps {
|
||||
export function StripeModal({
|
||||
open,
|
||||
onClose,
|
||||
// onSuccess,
|
||||
}: // onSuccess,
|
||||
// onError,
|
||||
}: StripeModalProps): JSX.Element {
|
||||
StripeModalProps): JSX.Element {
|
||||
const api = useApi();
|
||||
const { token } = useAuth();
|
||||
const [stripePromise, setStripePromise] =
|
||||
useState<Promise<Stripe | null> | null>(null);
|
||||
const [clientSecret, setClientSecret] = useState<string>("");
|
||||
const isLoading = false;
|
||||
const [isLoading, setIsLoading ] = useState(true);
|
||||
|
||||
useEffect(() => {
|
||||
(async () => {
|
||||
@ -33,25 +35,18 @@ export function StripeModal({
|
||||
}, [api]);
|
||||
|
||||
useEffect(() => {
|
||||
fetch("https://aura.wit.life/api/v1/user/subscription_receipts.json", {
|
||||
method: "POST",
|
||||
headers: {
|
||||
Authorization:
|
||||
"Bearer eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOjIzNjEyLCJpYXQiOjE2OTM0MTg5MTAsImV4cCI6MTcwMjA1ODkxMCwianRpIjoiNzg5MjkwYWItODg0YS00MGUyLTkyNjEtOWI2OGEyNjkwNmE0IiwiZW1haWwiOiJvdGhlckBleGFtcGxlLmNvbSIsInN0YXRlIjoicHJvdmVuIiwibG9jIjoiZW4iLCJ0eiI6LTI4ODAwLCJ0eXBlIjoiZW1haWwiLCJpc3MiOiJjb20ubGlmZS5hdXJhIn0.J2ocWIv5jKzuKMcwMgWMiNMyGg5qLlMAeln-bQm_9lw",
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
body: JSON.stringify({
|
||||
way: "stripe",
|
||||
subscription_receipt: {
|
||||
item_interval: "year",
|
||||
},
|
||||
}),
|
||||
}).then(async (res) => {
|
||||
const { subscription_receipt } = await res.json();
|
||||
if (!open) return;
|
||||
(async () => {
|
||||
|
||||
const { subscription_receipt } = await api.createSubscriptionReceipt({
|
||||
token,
|
||||
itemInterval: "year",
|
||||
});
|
||||
const { client_secret } = subscription_receipt.data;
|
||||
setClientSecret(client_secret);
|
||||
});
|
||||
}, []);
|
||||
setIsLoading(false);
|
||||
})();
|
||||
}, [api, token, open]);
|
||||
|
||||
const handleClose = () => {
|
||||
onClose();
|
||||
|
||||
30
src/components/PaymentPage/results/ErrorPage/index.tsx
Normal file
30
src/components/PaymentPage/results/ErrorPage/index.tsx
Normal file
@ -0,0 +1,30 @@
|
||||
import { useNavigate } from "react-router-dom";
|
||||
import { useTranslation } from "react-i18next";
|
||||
import routes from "@/routes";
|
||||
import styles from "./styles.module.css";
|
||||
import Title from "@/components/Title";
|
||||
import MainButton from "@/components/MainButton";
|
||||
|
||||
function PaymentFailPage(): JSX.Element {
|
||||
const { t } = useTranslation();
|
||||
const navigate = useNavigate();
|
||||
const handleNext = () => navigate(routes.client.paymentMethod());
|
||||
|
||||
return (
|
||||
<section className={`${styles.page} page`}>
|
||||
<img src="/ExclamationIcon.png" alt="Exclamation Icon" />
|
||||
<div className={styles.text}>
|
||||
<Title variant="h1">{t("auweb.pay_bad.title")}</Title>
|
||||
<p className={styles.list}>{t("auweb.pay_bad.text1")}</p>
|
||||
</div>
|
||||
<div className={styles.bottom}>
|
||||
<p className={styles.description}>{t("auweb.pay_bad.text2")}</p>
|
||||
<MainButton className={styles.button} onClick={handleNext}>
|
||||
{t("auweb.pay_bad.button")}
|
||||
</MainButton>
|
||||
</div>
|
||||
</section>
|
||||
);
|
||||
}
|
||||
|
||||
export default PaymentFailPage;
|
||||
@ -0,0 +1,38 @@
|
||||
.page {
|
||||
position: relative;
|
||||
height: calc(100vh - 50px);
|
||||
/* max-height: -webkit-fill-available; */
|
||||
overflow-y: scroll;
|
||||
justify-content: center;
|
||||
gap: 80px;
|
||||
}
|
||||
|
||||
.text {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.list {
|
||||
font-weight: 500;
|
||||
white-space: pre-wrap;
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
.description {
|
||||
font-weight: 500;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.button {
|
||||
width: 100%;
|
||||
max-width: 260px;
|
||||
border-radius: 50px;
|
||||
background-color: #fe2b57;
|
||||
}
|
||||
|
||||
.bottom {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
align-items: center;
|
||||
gap: 16px;
|
||||
}
|
||||
25
src/components/PaymentPage/results/SuccessPage/index.tsx
Normal file
25
src/components/PaymentPage/results/SuccessPage/index.tsx
Normal file
@ -0,0 +1,25 @@
|
||||
import { useNavigate } from 'react-router-dom'
|
||||
import { useTranslation } from "react-i18next";
|
||||
import routes from '@/routes'
|
||||
import styles from "./styles.module.css";
|
||||
import Title from "@/components/Title";
|
||||
import MainButton from "@/components/MainButton";
|
||||
|
||||
function PaymentSuccessPage(): JSX.Element {
|
||||
const { t } = useTranslation();
|
||||
const navigate = useNavigate()
|
||||
const handleNext = () => navigate(routes.client.home())
|
||||
|
||||
return (
|
||||
<section className={`${styles.page} page`}>
|
||||
<img src="/SuccessIcon.png" alt="Success Icon" />
|
||||
<div className={styles.text}>
|
||||
<Title variant="h1">{t("auweb.pay_good.title")}</Title>
|
||||
<p>{t("auweb.pay_good.text1")}</p>
|
||||
</div>
|
||||
<MainButton className={styles.button} onClick={handleNext}>{t("auweb.pay_good.button")}</MainButton>
|
||||
</section>
|
||||
);
|
||||
}
|
||||
|
||||
export default PaymentSuccessPage;
|
||||
@ -0,0 +1,25 @@
|
||||
.page {
|
||||
position: relative;
|
||||
flex: auto;
|
||||
height: calc(100vh - 50px);
|
||||
max-height: -webkit-fill-available;
|
||||
justify-content: center;
|
||||
gap: 80px;
|
||||
}
|
||||
|
||||
.text {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.text > p {
|
||||
text-align: center;
|
||||
font-weight: 500;
|
||||
}
|
||||
|
||||
.button {
|
||||
width: 100%;
|
||||
max-width: 260px;
|
||||
border-radius: 50px;
|
||||
background-color: #FE2B57;
|
||||
}
|
||||
21
src/components/PaymentPage/results/index.tsx
Normal file
21
src/components/PaymentPage/results/index.tsx
Normal file
@ -0,0 +1,21 @@
|
||||
import { useNavigate } from "react-router-dom";
|
||||
import routes from "@/routes";
|
||||
import { useEffect } from "react";
|
||||
import { useSearchParams } from "react-router-dom";
|
||||
|
||||
function PaymentResultPage(): JSX.Element {
|
||||
const navigate = useNavigate();
|
||||
const [searchParams] = useSearchParams();
|
||||
const status = searchParams.get("redirect_status");
|
||||
|
||||
useEffect(() => {
|
||||
if (status === "succeeded") {
|
||||
return navigate(routes.client.paymentSuccess());
|
||||
}
|
||||
return navigate(routes.client.paymentFail());
|
||||
}, [navigate, status]);
|
||||
|
||||
return <></>;
|
||||
}
|
||||
|
||||
export default PaymentResultPage;
|
||||
@ -58,8 +58,7 @@ function WallpaperPage(): JSX.Element {
|
||||
const api = useApi();
|
||||
const { i18n } = useTranslation();
|
||||
const locale = i18n.language;
|
||||
const token =
|
||||
"eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOjIzNjEyLCJpYXQiOjE2OTM0MTg5MTAsImV4cCI6MTcwMjA1ODkxMCwianRpIjoiNzg5MjkwYWItODg0YS00MGUyLTkyNjEtOWI2OGEyNjkwNmE0IiwiZW1haWwiOiJvdGhlckBleGFtcGxlLmNvbSIsInN0YXRlIjoicHJvdmVuIiwibG9jIjoiZW4iLCJ0eiI6LTI4ODAwLCJ0eXBlIjoiZW1haWwiLCJpc3MiOiJjb20ubGlmZS5hdXJhIn0.J2ocWIv5jKzuKMcwMgWMiNMyGg5qLlMAeln-bQm_9lw";
|
||||
const token = useSelector(selectors.selectToken)
|
||||
|
||||
const {
|
||||
user,
|
||||
|
||||
@ -17,6 +17,9 @@ const routes = {
|
||||
attention: () => [host, "attention"].join("/"),
|
||||
feedback: () => [host, "feedback"].join("/"),
|
||||
paymentMethod: () => [host, "payment", "method"].join("/"),
|
||||
paymentResult: () => [host, "payment", "result"].join("/"),
|
||||
paymentSuccess: () => [host, "payment", "success"].join("/"),
|
||||
paymentFail: () => [host, "payment", "fail"].join("/"),
|
||||
wallpaper: () => [host, "wallpaper"].join("/"),
|
||||
static: () => [host, "static", ":typeId"].join("/"),
|
||||
legal: (type: string) => [host, "static", type].join("/"),
|
||||
@ -115,6 +118,9 @@ export const withoutFooterRoutes = [
|
||||
routes.client.compatibilityResult(),
|
||||
routes.client.home(),
|
||||
routes.client.breathResult(),
|
||||
routes.client.paymentResult(),
|
||||
routes.client.paymentSuccess(),
|
||||
routes.client.paymentFail(),
|
||||
];
|
||||
export const hasNoFooter = (path: string) =>
|
||||
!withoutFooterRoutes.includes(path);
|
||||
@ -134,6 +140,9 @@ export const withoutHeaderRoutes = [
|
||||
routes.client.compatibility(),
|
||||
routes.client.subscription(),
|
||||
routes.client.paymentMethod(),
|
||||
routes.client.paymentResult(),
|
||||
routes.client.paymentSuccess(),
|
||||
routes.client.paymentFail(),
|
||||
];
|
||||
export const hasNoHeader = (path: string) =>
|
||||
!withoutHeaderRoutes.includes(path);
|
||||
|
||||
Loading…
Reference in New Issue
Block a user