完成顶部导航条
> 添加左侧logo
> 添加右侧用户信息展示
> 修复一些登录注册的跳转问题
> 修复axios拦截器错误的头设置
> 修复authApi错误的接口路径
> 组织api文件结构
Change-Id: Ifaec7e9a78ad6862ce7d0ce76be5181185186edd
diff --git a/src/routes/ProtectedRoute.tsx b/src/routes/ProtectedRoute.tsx
new file mode 100644
index 0000000..238fdf4
--- /dev/null
+++ b/src/routes/ProtectedRoute.tsx
@@ -0,0 +1,36 @@
+import React, { useEffect } from 'react';
+import { useAppSelector, useAppDispatch } from '../store/hooks'; // 导入 hooks
+import { useNavigate } from 'react-router';
+import { refreshToken } from '../feature/auth/authSlice'; // 导入刷新 token 的 thunk
+
+interface ProtectedRouteProps {
+ children: React.ReactNode;
+}
+
+const ProtectedRoute: React.FC<ProtectedRouteProps> = ({ children }) => {
+ const { isAuth, token } = useAppSelector((state) => state.auth);
+ const navigate = useNavigate();
+ const dispatch = useAppDispatch();
+
+ useEffect(() => {
+ const tryRefreshToken = async () => {
+ if (!token) {
+ navigate('/login'); // 如果没有 token,跳转到登录页
+ }
+ if (!isAuth && token) {
+ try {
+ await dispatch(refreshToken(token)).unwrap(); // 尝试刷新 token
+ } catch {
+ navigate('/login');
+ }
+ }
+ };
+
+ tryRefreshToken(); // 执行 token 刷新
+ }, [isAuth, token, dispatch, navigate]);
+
+ // 如果已认证则渲染 children,否则返回 null
+ return isAuth ? <>{children}</> : null;
+};
+
+export default ProtectedRoute;
diff --git a/src/routes/routes.ts b/src/routes/routes.ts
new file mode 100644
index 0000000..585b1f6
--- /dev/null
+++ b/src/routes/routes.ts
@@ -0,0 +1,29 @@
+import { createBrowserRouter } from "react-router";
+import Home from "../feature/Home";
+import AuthLayout from "../feature/auth/AuthLayout";
+import Login from "../feature/auth/Login";
+import Register from "../feature/auth/Register";
+import Forget from "../feature/auth/Forget";
+import AppLayout from "../AppLayout";
+import withProtect from "./withProtect";
+
+export default createBrowserRouter([
+ {
+ Component: AppLayout,
+ children: [
+ {
+ path: "/",
+ // 使用 ProtectedRoute 来包裹需要保护的页面
+ element: withProtect(Home),
+ },
+ {
+ Component: AuthLayout,
+ children: [
+ { path: "login", Component: Login },
+ { path: "register", Component: Register },
+ { path: "forget", Component: Forget },
+ ],
+ },
+ ],
+ },
+]);
diff --git a/src/routes/withProtect.ts b/src/routes/withProtect.ts
new file mode 100644
index 0000000..bcde943
--- /dev/null
+++ b/src/routes/withProtect.ts
@@ -0,0 +1,10 @@
+import React from 'react';
+import ProtectedRoute from './ProtectedRoute';
+
+const withProtect = (Component: React.ComponentType) => {
+ return React.createElement(ProtectedRoute, {
+ children: React.createElement(Component)
+ });
+};
+
+export default withProtect;
\ No newline at end of file