Fix loading page hanging
This commit is contained in:
parent
b042e770c3
commit
1197a8cb06
3 changed files with 39 additions and 42 deletions
|
|
@ -3,6 +3,7 @@ import { ProtectedRoute } from "@ui/components/ProtectedRoute";
|
|||
import { SessionTestProvider } from "@ui/contexts/SessionContext";
|
||||
import { renderWithRouter } from "@ui/utils/testHelpers";
|
||||
import { Route, Routes } from "react-router-dom";
|
||||
import { TestUserStoreProvider } from "src/providers/UserStoreProvider";
|
||||
|
||||
describe("ProtectedRoute", () => {
|
||||
beforeEach(() => {
|
||||
|
|
@ -30,14 +31,16 @@ describe("ProtectedRoute", () => {
|
|||
|
||||
it("redirects to login when user is not authenticated", async () => {
|
||||
renderWithRouter(
|
||||
<SessionTestProvider>
|
||||
<Routes>
|
||||
<Route element={<ProtectedRoute />}>
|
||||
<Route path="/" element={<div>Protected Content</div>} />
|
||||
</Route>
|
||||
<Route path="/login" element={<div>Login Page</div>} />
|
||||
</Routes>
|
||||
</SessionTestProvider>,
|
||||
<TestUserStoreProvider user={null}>
|
||||
<SessionTestProvider>
|
||||
<Routes>
|
||||
<Route element={<ProtectedRoute />}>
|
||||
<Route path="/" element={<div>Protected Content</div>} />
|
||||
</Route>
|
||||
<Route path="/login" element={<div>Login Page</div>} />
|
||||
</Routes>
|
||||
</SessionTestProvider>
|
||||
</TestUserStoreProvider>,
|
||||
{ route: "/" }
|
||||
);
|
||||
|
||||
|
|
@ -71,31 +74,24 @@ describe("ProtectedRoute", () => {
|
|||
|
||||
it("renders protected content when user is authenticated", async () => {
|
||||
renderWithRouter(
|
||||
<SessionTestProvider
|
||||
testUser={{
|
||||
<TestUserStoreProvider
|
||||
user={{
|
||||
id: "123",
|
||||
app_metadata: {},
|
||||
user_metadata: {
|
||||
full_name: "Test User",
|
||||
email: "test@example.com",
|
||||
email_verified: true,
|
||||
first_name: "Test",
|
||||
last_name: "User",
|
||||
business_name: "Test Business",
|
||||
},
|
||||
aud: "authenticated",
|
||||
created_at: new Date().toISOString(),
|
||||
name: "Test User",
|
||||
email: "test@example.com",
|
||||
role: "authenticated",
|
||||
updated_at: new Date().toISOString(),
|
||||
avatar_url: "https://example.com/avatar.jpg",
|
||||
streamToken: null,
|
||||
short_user_id: "123",
|
||||
}}
|
||||
>
|
||||
<Routes>
|
||||
<Route element={<ProtectedRoute />}>
|
||||
<Route path="/" element={<div>Protected Content</div>} />
|
||||
</Route>
|
||||
</Routes>
|
||||
</SessionTestProvider>,
|
||||
<SessionTestProvider>
|
||||
<Routes>
|
||||
<Route element={<ProtectedRoute />}>
|
||||
<Route path="/" element={<div>Protected Content</div>} />
|
||||
</Route>
|
||||
</Routes>
|
||||
</SessionTestProvider>
|
||||
</TestUserStoreProvider>,
|
||||
{ route: "/" }
|
||||
);
|
||||
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@ import { useEffect, useState } from "react";
|
|||
import { Navigate, Outlet } from "react-router-dom";
|
||||
import { match } from "ts-pattern";
|
||||
import { LoadingSpinner } from "./LoadingSpinner";
|
||||
import { useMaybeUser } from "src/providers/UserStoreProvider";
|
||||
|
||||
interface ProtectedRouteProps {
|
||||
fallback?: string;
|
||||
|
|
@ -22,13 +23,14 @@ export const ProtectedRoute = ({ fallback, shouldRedirectToCurrentPage }: Protec
|
|||
|
||||
let status: "loading" | "should-land-user" | "should-redirect" | "should-pass" = "loading";
|
||||
|
||||
const user = useMaybeUser();
|
||||
const isFirstTimeUser = localStorage.getItem("xtablo-has-seen-landing-page") === null;
|
||||
|
||||
if (isLoading) {
|
||||
status = "loading";
|
||||
} else if (!session?.user && isFirstTimeUser) {
|
||||
} else if (!user && isFirstTimeUser) {
|
||||
status = "should-land-user";
|
||||
} else if (!session?.user) {
|
||||
} else if (!user) {
|
||||
status = "should-redirect";
|
||||
} else {
|
||||
status = "should-pass";
|
||||
|
|
@ -40,14 +42,10 @@ export const ProtectedRoute = ({ fallback, shouldRedirectToCurrentPage }: Protec
|
|||
)}`
|
||||
: (fallback ?? "/login");
|
||||
|
||||
return (
|
||||
<>
|
||||
{match(status)
|
||||
.with("loading", () => <LoadingSpinner />)
|
||||
.with("should-land-user", () => <Navigate to="/landing" replace />)
|
||||
.with("should-redirect", () => <Navigate to={redirectUrl} replace />)
|
||||
.with("should-pass", () => <Outlet />)
|
||||
.exhaustive()}
|
||||
</>
|
||||
);
|
||||
return match(status)
|
||||
.with("loading", () => <LoadingSpinner />)
|
||||
.with("should-land-user", () => <Navigate to="/landing" replace />)
|
||||
.with("should-redirect", () => <Navigate to={redirectUrl} replace />)
|
||||
.with("should-pass", () => <Outlet />)
|
||||
.exhaustive();
|
||||
};
|
||||
|
|
|
|||
|
|
@ -72,8 +72,11 @@ export const TestUserStoreProvider = ({
|
|||
user,
|
||||
}: {
|
||||
children: React.ReactNode;
|
||||
user: User;
|
||||
user: User | null;
|
||||
}) => {
|
||||
if (!user) {
|
||||
return children;
|
||||
}
|
||||
const store = createStore<User>()(() => user);
|
||||
|
||||
return (
|
||||
|
|
|
|||
Loading…
Reference in a new issue