Skip to content

Commit fb09b02

Browse files
authored
Merge pull request #151 from CS3219-AY2425S1/enhancement/frontend/refactor-auth-wrapper
Enhancement/frontend/refactor auth wrapper
2 parents 2e58b03 + 0dc5b1c commit fb09b02

File tree

8 files changed

+40
-15
lines changed

8 files changed

+40
-15
lines changed
Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,10 @@
11
import AdminUserManagement from "@/components/admin-user-management/admin-user-management";
2+
import AuthPageWrapper from "@/components/auth/auth-page-wrapper";
23

34
export default function AdminUserManagementPage() {
4-
return <AdminUserManagement />;
5+
return (
6+
<AuthPageWrapper requireAdmin>
7+
<AdminUserManagement />
8+
</AuthPageWrapper>
9+
);
510
}
Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,13 @@
1+
import AuthPageWrapper from "@/components/auth/auth-page-wrapper";
12
import QuestionListing from "@/components/questions/questions-listing";
23
import { Suspense } from "react";
34

45
export default function QuestionListingPage() {
56
return (
6-
<Suspense>
7-
<QuestionListing />
8-
</Suspense>
7+
<AuthPageWrapper requireLoggedIn>
8+
<Suspense>
9+
<QuestionListing />
10+
</Suspense>
11+
</AuthPageWrapper>
912
);
1013
}
Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,14 @@
1+
import AuthPageWrapper from "@/components/auth/auth-page-wrapper";
12
import UserSettings from "@/components/user-settings/user-settings";
23

34
export default function UserSettingsPage({
45
params,
56
}: {
67
params: { user_id: string };
78
}) {
8-
return <UserSettings userId={params.user_id} />;
9+
return (
10+
<AuthPageWrapper requireLoggedIn userId={params.user_id}>
11+
<UserSettings userId={params.user_id} />;
12+
</AuthPageWrapper>
13+
);
914
}

frontend/app/layout.tsx

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import "./globals.css";
44
import { ThemeProvider } from "@/components/theme-provider";
55
import { Toaster } from "@/components/ui/toaster";
66
import AuthProvider from "@/app/auth/auth-context";
7+
import AuthPageWrapper from "@/components/auth/auth-page-wrapper";
78
import { Navbar } from "@/components/navbar";
89

910
const geistSans = localFont({
@@ -40,7 +41,7 @@ export default function RootLayout({
4041
>
4142
<AuthProvider>
4243
<Navbar />
43-
{children}
44+
<AuthPageWrapper>{children}</AuthPageWrapper>
4445
</AuthProvider>
4546
<Toaster />
4647
</ThemeProvider>

frontend/components/admin-user-management/admin-user-management.tsx

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,6 @@ import {
1515
import LoadingScreen from "@/components/common/loading-screen";
1616
import AdminEditUserModal from "@/components/admin-user-management/admin-edit-user-modal";
1717
import { PencilIcon, Trash2Icon } from "lucide-react";
18-
import AuthPageWrapper from "@/components/auth/auth-page-wrapper";
1918
import { User, UserArraySchema } from "@/lib/schemas/user-schema";
2019

2120
const fetcher = async (url: string): Promise<User[]> => {
@@ -88,7 +87,7 @@ export default function AdminUserManagement() {
8887
};
8988

9089
return (
91-
<AuthPageWrapper requireAdmin>
90+
<>
9291
<div className="container mx-auto p-4">
9392
<h1 className="text-2xl font-bold mb-4">User Management</h1>
9493
<AdminEditUserModal
@@ -137,6 +136,6 @@ export default function AdminUserManagement() {
137136
</TableBody>
138137
</Table>
139138
</div>
140-
</AuthPageWrapper>
139+
</>
141140
);
142141
}

frontend/components/auth/auth-page-wrapper.tsx

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,10 +6,13 @@ import { useAuth } from "@/app/auth/auth-context";
66
import { Button } from "@/components/ui/button";
77
import { useRouter } from "next/navigation";
88

9-
type AuthCheck = (user: { isAdmin: boolean } | undefined | null) => boolean;
9+
type AuthCheck = (
10+
user: { id: string; isAdmin: boolean } | undefined | null
11+
) => boolean;
1012

1113
interface AuthPageWrapperProps extends React.HTMLProps<HTMLDivElement> {
1214
children: ReactNode;
15+
userId?: string;
1316

1417
// User access rules
1518
authCheck?: AuthCheck; // Custom predicate which is true when user is to be granted access
@@ -19,20 +22,24 @@ interface AuthPageWrapperProps extends React.HTMLProps<HTMLDivElement> {
1922

2023
const AuthPageWrapper: React.FC<AuthPageWrapperProps> = ({
2124
children,
25+
userId,
2226
...props
2327
}) => {
2428
const auth = useAuth();
2529
const router = useRouter();
2630

2731
const authCheck = (
28-
user: { isAdmin: boolean } | undefined | null
32+
user: { id: string; isAdmin: boolean } | undefined | null
2933
): boolean => {
3034
if (props?.requireLoggedIn && !user) {
3135
return false;
3236
}
3337
if (props?.requireAdmin && !user?.isAdmin) {
3438
return false;
3539
}
40+
if (userId && user?.id !== userId) {
41+
return false;
42+
}
3643
if (props?.authCheck) {
3744
return props.authCheck(user);
3845
}
@@ -53,7 +60,9 @@ const AuthPageWrapper: React.FC<AuthPageWrapperProps> = ({
5360
<Button
5461
size="lg"
5562
onClick={() => {
56-
auth?.user ? router.push("/") : router.push("/auth/login");
63+
auth?.user
64+
? router.push("/app/questions")
65+
: router.push("/auth/login");
5766
}}
5867
>
5968
Return Home

frontend/components/navbar.tsx

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,10 @@ export function Navbar() {
2222

2323
const isActive = (path: string) => pathname === path;
2424

25+
if (!auth?.user) {
26+
return;
27+
}
28+
2529
return (
2630
<nav className="bg-background border-b">
2731
<div className="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8">

frontend/components/user-settings/user-settings.tsx

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,6 @@ import ProfileTab from "@/components/user-settings/profile-tab";
2323
import LoadingScreen from "@/components/common/loading-screen";
2424
import { useAuth } from "@/app/auth/auth-context";
2525
import { cn } from "@/lib/utils";
26-
import AuthPageWrapper from "../auth/auth-page-wrapper";
2726
import { User, UserSchema } from "@/lib/schemas/user-schema";
2827

2928
const fetcher = async (url: string): Promise<User> => {
@@ -309,7 +308,7 @@ export default function UserSettings({ userId }: { userId: string }) {
309308
}
310309

311310
return (
312-
<AuthPageWrapper requireLoggedIn>
311+
<>
313312
{error ? (
314313
<div>Error: Failed to load user data</div>
315314
) : !user ? (
@@ -496,6 +495,6 @@ export default function UserSettings({ userId }: { userId: string }) {
496495
</Tabs>
497496
</div>
498497
)}
499-
</AuthPageWrapper>
498+
</>
500499
);
501500
}

0 commit comments

Comments
 (0)