Skip to content

Commit ebe2a7f

Browse files
committed
fix: client
1 parent 3c8a2d7 commit ebe2a7f

File tree

10 files changed

+24
-116
lines changed

10 files changed

+24
-116
lines changed

client/index.html

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
88
<meta name="description" content="LEARN-Hub - A recommendation system for Computer Science education activities for primary school students" />
99
<meta name="theme-color" content="#3b82f6" />
10+
<meta name="mobile-web-app-capable" content="yes" />
1011
<meta name="apple-mobile-web-app-capable" content="yes" />
1112
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent" />
1213
<meta name="apple-mobile-web-app-title" content="LEARN-Hub" />

client/src/components/layout/UserHeader.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ export const UserHeader: React.FC<UserHeaderProps> = ({
2121
}) => {
2222
const { t } = useTranslation();
2323
const isAdmin = user?.role === "ADMIN";
24-
const isGuest = user?.role === "GUEST";
24+
const isGuest = !user || user.role === "GUEST";
2525

2626
const roleDescription = isAdmin
2727
? t("sidebar.adminView")

client/src/contexts/AuthContext.tsx

Lines changed: 1 addition & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -31,11 +31,6 @@ export interface AuthContextType {
3131
resetPassword: (
3232
email: string,
3333
) => Promise<{ success: boolean; message?: string }>;
34-
guestLogin: () => Promise<{
35-
success: boolean;
36-
message?: string;
37-
user?: User;
38-
}>;
3934
logout: () => Promise<void>;
4035
refreshUser: () => Promise<void>;
4136
updateProfile: (
@@ -125,17 +120,9 @@ export const AuthProvider: React.FC<AuthProviderProps> = ({ children }) => {
125120
return await authService.resetPassword(email);
126121
};
127122

128-
const guestLogin = async () => {
129-
const result = await authService.guestLogin();
130-
if (result.success && result.user) {
131-
setUser(result.user);
132-
}
133-
return result;
134-
};
135-
136123
const logout = async () => {
137-
await authService.logout();
138124
setUser(null);
125+
await authService.logout();
139126
};
140127

141128
const refreshUser = async () => {
@@ -212,7 +199,6 @@ export const AuthProvider: React.FC<AuthProviderProps> = ({ children }) => {
212199
requestVerificationCode,
213200
registerTeacher,
214201
resetPassword,
215-
guestLogin,
216202
logout,
217203
refreshUser,
218204
updateProfile,

client/src/contexts/__tests__/AuthContext.test.tsx

Lines changed: 0 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -229,33 +229,6 @@ describe("AuthContext", () => {
229229
expect(result.current?.isAuthenticated).toBe(true);
230230
});
231231

232-
it("should handle guest login", async () => {
233-
vi.mocked(authService.isAuthenticated).mockReturnValue(false);
234-
const mockUser = {
235-
id: 0,
236-
email: "guest@example.com",
237-
role: "GUEST" as const,
238-
};
239-
vi.mocked(authService.guestLogin).mockResolvedValue({
240-
success: true,
241-
user: mockUser,
242-
});
243-
244-
const { result } = renderHook(() => React.useContext(AuthContext), {
245-
wrapper,
246-
});
247-
248-
await waitFor(() => {
249-
expect(result.current?.isLoading).toBe(false);
250-
});
251-
252-
await act(async () => {
253-
await result.current?.guestLogin();
254-
});
255-
256-
expect(result.current?.user).toEqual(mockUser);
257-
expect(result.current?.isAuthenticated).toBe(true);
258-
});
259232

260233
it("should handle verification code login", async () => {
261234
vi.mocked(authService.isAuthenticated).mockReturnValue(false);

client/src/main.tsx

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,6 @@
1-
import { StrictMode } from "react";
21
import { createRoot } from "react-dom/client";
32
import "./index.css";
43
import "./i18n";
54
import App from "./App.tsx";
65

7-
createRoot(document.getElementById("root")!).render(
8-
<StrictMode>
9-
<App />
10-
</StrictMode>,
11-
);
6+
createRoot(document.getElementById("root")!).render(<App />);

client/src/pages/AccountDashboardPage.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ export const AccountDashboardPage: React.FC = () => {
4646
password: "",
4747
});
4848

49-
const isGuest = user?.role === "GUEST";
49+
const isGuest = !user || user.role === "GUEST";
5050

5151
const handleInputChange = (
5252
field: keyof UpdateProfileRequest,

client/src/pages/ActivityDetails.tsx

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@ import {
1717
import { FavouriteButton } from "@/components/favourites/FavouriteButton";
1818
import { apiService } from "@/services/apiService";
1919
import { useAuth } from "@/hooks/useAuth";
20-
import type { Activity } from "@/types/activity";
2120
import { useTranslation } from "react-i18next";
2221

2322
export const ActivityDetails: React.FC = () => {
@@ -28,16 +27,10 @@ export const ActivityDetails: React.FC = () => {
2827
const isAdmin = user?.role === "ADMIN";
2928
const { t } = useTranslation();
3029

31-
// Get activity data from navigation state or fetch from API
32-
const stateActivity = location.state?.activity as Activity | undefined;
3330
const fromBrowser = location.state?.fromBrowser as boolean | undefined;
3431

3532
const documentApi = useApi();
3633
const fetchActivity = useCallback(async () => {
37-
if (stateActivity && !isAdmin) {
38-
return stateActivity;
39-
}
40-
4134
if (id) {
4235
const fetchedActivity = await apiService.getActivity(id);
4336
if (!fetchedActivity) {
@@ -47,7 +40,7 @@ export const ActivityDetails: React.FC = () => {
4740
}
4841

4942
throw new Error("No activity ID provided");
50-
}, [stateActivity, id, isAdmin]);
43+
}, [id]);
5144

5245
const {
5346
data: activity,
@@ -56,7 +49,7 @@ export const ActivityDetails: React.FC = () => {
5649
refetch,
5750
} = useDataFetch({
5851
fetchFn: fetchActivity,
59-
enabled: !!(stateActivity || id),
52+
enabled: !!id,
6053
dependencies: [fetchActivity],
6154
});
6255

client/src/pages/LoginPage.tsx

Lines changed: 11 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,6 @@ export const LoginPage: React.FC = () => {
5656
requestVerificationCode,
5757
registerTeacher,
5858
resetPassword,
59-
guestLogin,
6059
user,
6160
} = useAuth();
6261
const navigate = useNavigate();
@@ -74,20 +73,9 @@ export const LoginPage: React.FC = () => {
7473

7574
const handleGuestLogin = async () => {
7675
setIsLoading(true);
77-
try {
78-
const result = await guestLogin();
79-
if (result.success) {
80-
setMessage("Welcome! You're now browsing as a guest.");
81-
setRedirectPath("/recommendations");
82-
setShouldRedirect(true);
83-
} else {
84-
setMessage(result.message || "Failed to login as guest");
85-
}
86-
} catch {
87-
setMessage("An unexpected error occurred");
88-
} finally {
89-
setIsLoading(false);
90-
}
76+
setMessage("Welcome! You're now browsing as a guest.");
77+
navigate("/recommendations");
78+
setIsLoading(false);
9179
};
9280

9381
const handleSubmit = async (e: React.FormEvent) => {
@@ -683,18 +671,16 @@ export const LoginPage: React.FC = () => {
683671

684672
{message && (
685673
<Alert
686-
className={`${
687-
message.includes("successful")
688-
? "border-success/20 bg-success/5"
689-
: "border-destructive/20 bg-destructive/5"
690-
}`}
674+
className={`${message.includes("successful")
675+
? "border-success/20 bg-success/5"
676+
: "border-destructive/20 bg-destructive/5"
677+
}`}
691678
>
692679
<AlertCircle
693-
className={`h-4 w-4 ${
694-
message.includes("successful")
695-
? "text-success"
696-
: "text-destructive"
697-
}`}
680+
className={`h-4 w-4 ${message.includes("successful")
681+
? "text-success"
682+
: "text-destructive"
683+
}`}
698684
/>
699685
<AlertDescription
700686
className={

client/src/services/__tests__/authService.test.ts

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,7 @@ describe("AuthService", () => {
104104

105105
expect(header).toEqual({});
106106
});
107+
107108
});
108109

109110
describe("Token Validation", () => {
@@ -173,17 +174,6 @@ describe("AuthService", () => {
173174
});
174175
});
175176

176-
describe("Guest Login", () => {
177-
it("should create guest user without API call", async () => {
178-
const result = await authService.guestLogin();
179-
180-
expect(result.success).toBe(true);
181-
expect(result.user).toBeDefined();
182-
expect(result.user?.role).toBe("GUEST");
183-
expect(result.user?.email).toBe("guest@example.com");
184-
});
185-
});
186-
187177
describe("Token Refresh", () => {
188178
it("should refresh access token successfully", async () => {
189179
const refreshToken = createValidToken();

client/src/services/authService.ts

Lines changed: 5 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -299,32 +299,16 @@ export class AuthService {
299299

300300
// Logout
301301
async logout(): Promise<void> {
302+
const headers = this.getAuthHeader();
303+
this.clearTokens();
304+
302305
try {
303-
await fetch("/api/auth/logout", {
306+
await fetch(this.baseURL + "/api/auth/logout", {
304307
method: "POST",
305-
headers: this.getAuthHeader(),
308+
headers,
306309
});
307310
} catch (error) {
308311
logger.error("Error logging out", error, "AuthService");
309-
} finally {
310-
this.clearTokens();
311-
}
312-
}
313-
314-
// Login as guest
315-
async guestLogin(): Promise<AuthResponse> {
316-
try {
317-
// Create a guest user object without making any API calls
318-
const guestUser: User = {
319-
id: 0,
320-
email: "guest@example.com",
321-
role: "GUEST",
322-
};
323-
324-
return { success: true, user: guestUser };
325-
} catch (error) {
326-
logger.error("Error logging in as guest", error, "AuthService");
327-
return { success: false, message: "An unexpected error occurred" };
328312
}
329313
}
330314

0 commit comments

Comments
 (0)