diff --git a/src/RootApp.tsx b/src/RootApp.tsx
index 609cfc6fdd..144d8f93e8 100644
--- a/src/RootApp.tsx
+++ b/src/RootApp.tsx
@@ -14,7 +14,7 @@ import theme from 'themes/theme';
import { HistoryRouter } from 'components/router/HistoryRouter';
const DashboardApp = loadable(() => import('./apps/dashboard/App'));
-const StableApp = loadable(() => import('./apps/stable/App'));
+const StableAppRouter = loadable(() => import('./apps/stable/AppRouter'));
const RootAppRouter = loadable(() => import('./RootAppRouter'));
const queryClient = new QueryClient();
@@ -33,9 +33,7 @@ const RootAppLayout = ({ history }: { history: History }) => {
{isExperimentalLayout ?
:
-
-
-
+
}
diff --git a/src/apps/stable/App.tsx b/src/apps/stable/App.tsx
deleted file mode 100644
index 9b0adbab9c..0000000000
--- a/src/apps/stable/App.tsx
+++ /dev/null
@@ -1,55 +0,0 @@
-import React from 'react';
-import { Navigate, Outlet, Route, Routes } from 'react-router-dom';
-
-import { DASHBOARD_APP_PATHS } from 'apps/dashboard/App';
-import AppBody from 'components/AppBody';
-import ConnectionRequired from 'components/ConnectionRequired';
-import { toAsyncPageRoute } from 'components/router/AsyncRoute';
-import { toViewManagerPageRoute } from 'components/router/LegacyRoute';
-import { toRedirectRoute } from 'components/router/Redirect';
-
-import { ASYNC_USER_ROUTES } from './routes/asyncRoutes';
-import { LEGACY_PUBLIC_ROUTES, LEGACY_USER_ROUTES } from './routes/legacyRoutes';
-import { REDIRECTS } from './routes/_redirects';
-
-const Layout = () => (
-
-
-
-);
-
-const StableApp = () => (
-
- }>
- {/* User routes */}
- }>
- {ASYNC_USER_ROUTES.map(toAsyncPageRoute)}
- {LEGACY_USER_ROUTES.map(toViewManagerPageRoute)}
-
-
- {/* Public routes */}
- }>
- } />
-
- {LEGACY_PUBLIC_ROUTES.map(toViewManagerPageRoute)}
-
-
- {/* Suppress warnings for unhandled routes */}
-
-
-
- {/* Redirects for old paths */}
- {REDIRECTS.map(toRedirectRoute)}
-
- {/* Ignore dashboard routes */}
- {Object.entries(DASHBOARD_APP_PATHS).map(([ key, path ]) => (
-
- ))}
-
-);
-
-export default StableApp;
diff --git a/src/apps/stable/AppLayout.tsx b/src/apps/stable/AppLayout.tsx
new file mode 100644
index 0000000000..f3b186c8db
--- /dev/null
+++ b/src/apps/stable/AppLayout.tsx
@@ -0,0 +1,12 @@
+import React from 'react';
+import { Outlet } from 'react-router-dom';
+
+import AppBody from 'components/AppBody';
+
+export default function AppLayout() {
+ return (
+
+
+
+ );
+}
diff --git a/src/apps/stable/AppRouter.tsx b/src/apps/stable/AppRouter.tsx
new file mode 100644
index 0000000000..57ca5f461b
--- /dev/null
+++ b/src/apps/stable/AppRouter.tsx
@@ -0,0 +1,16 @@
+import { History } from '@remix-run/router';
+import React from 'react';
+import { RouterProvider, createHashRouter } from 'react-router-dom';
+
+import { STABLE_APP_ROUTES } from './routes/routes';
+import { useLegacyRouterSync } from 'hooks/useLegacyRouterSync';
+
+const router = createHashRouter([
+ ...STABLE_APP_ROUTES
+]);
+
+export default function StableAppRouter({ history }: { history: History }) {
+ useLegacyRouterSync({ router, history });
+
+ return ;
+}
diff --git a/src/apps/stable/routes/routes.tsx b/src/apps/stable/routes/routes.tsx
new file mode 100644
index 0000000000..bf00037546
--- /dev/null
+++ b/src/apps/stable/routes/routes.tsx
@@ -0,0 +1,46 @@
+import { RouteObject, redirect } from 'react-router-dom';
+import React from 'react';
+
+import { DASHBOARD_APP_PATHS } from 'apps/dashboard/App';
+import ConnectionRequired from 'components/ConnectionRequired';
+import { toAsyncPageRouteConfig } from 'components/router/AsyncRoute';
+import { toViewManagerPageRouteConfig } from 'components/router/LegacyRoute';
+import { toRedirectRouteConfig } from 'components/router/Redirect';
+import AppLayout from '../AppLayout';
+import { REDIRECTS } from './_redirects';
+import { ASYNC_USER_ROUTES } from './asyncRoutes';
+import { LEGACY_PUBLIC_ROUTES, LEGACY_USER_ROUTES } from './legacyRoutes';
+
+export const STABLE_APP_ROUTES: RouteObject[] = [
+ {
+ path: '/*',
+ element: ,
+ children: [
+ {
+ /* User routes */
+ element: ,
+ children: [
+ ...ASYNC_USER_ROUTES.map(toAsyncPageRouteConfig),
+ ...LEGACY_USER_ROUTES.map(toViewManagerPageRouteConfig)
+ ]
+ },
+
+ /* Public routes */
+ { index: true, loader: () => redirect('/home.html') },
+ ...LEGACY_PUBLIC_ROUTES.map(toViewManagerPageRouteConfig),
+
+ /* Suppress warnings for unhandled routes */
+ { path: '*', element: null }
+ ]
+ },
+
+ /* Redirects for old paths */
+ ...REDIRECTS.map(toRedirectRouteConfig),
+
+ /* Ignore dashboard routes */
+ ...Object.entries(DASHBOARD_APP_PATHS).map(([, path]) => ({
+ path: `/${path}/*`,
+ element: null
+ }))
+
+];