Como ejercicio, estoy creando una aplicación de reacción (todavía estoy aprendiendo React) que implementa un sistema de inicio de sesión con firebase. Por supuesto, para implementar dicha función, es necesario reaccionar enrutador y lo he implementado con éxito. Sin embargo, una vez que el usuario inicia sesión, debería poder ver una barra lateral junto con otro contenido que se cambia dinámicamente. Ahora necesito volver a usar el enrutador de reacción para cambiar esas páginas cuando un usuario hace clic en un elemento específico en la barra lateral sin tener que representar la barra lateral con cada componente. He leído los documentos para anidar enrutadores, pero simplemente no puedo hacerlo funcionar. Cualquier ayuda es muy apreciada.
Aquí está el código:
Aplicación.js:
import "./App.css"; import LoginForm from "./components/LoginForm"; import { AuthProvider } from "./contexts/AuthContext"; import { BrowserRouter as Router, Switch, Route } from "react-router-dom"; import Dashboard from "./components/Dashboard"; import PrivateRoute from "./components/PrivateRoute"; function App() { return ( <div className="App"> <Router> <AuthProvider> <Switch> <PrivateRoute exact path="/" component={Dashboard} /> <Route path="/login" component={LoginForm} /> </Switch> </AuthProvider> </Router> </div> ); } export default App;
Tablero.js:
import React from "react"; import { useAuth } from "../contexts/AuthContext"; import { useHistory } from "react-router"; import Sidebar from "./Sidebar/Sidebar"; import { useRouteMatch } from "react-router"; const Dashboard = () => { const { currentUser, logout } = useAuth(); const history = useHistory(); let { path, url } = useRouteMatch(); const handleLogout = async () => { try { await logout(); history.push("/login"); } catch (error) { console.log(error); } }; if (!currentUser) return null; return ( <div> <Sidebar logout={handleLogout} /> </div> ); }; export default Dashboard;
PD. Soy bastante nuevo en reaccionar y cualquier sugerencia/crítica es bienvenida.
Siempre puede renderizar condicionalmente la barra lateral.
function Sidebar() { const { currentUser } = useAuth() if (!currentUser) return null // ... }
Dentro de su componente de aplicación, simplemente represente el componente de la barra lateral fuera del Switch:
function App() { return ( <div className="App"> <Router> <AuthProvider> <Sidebar /> <Routes /> </AuthProvider> </Router> </div> ); } function Routes() { const { currentUser } = useAuth() return ( <Switch> {currentUser && <PrivateRoutes />} <PublicRoutes /> </Switch> ) }
Básicamente, todo lo que necesita hacer es representar la barra lateral en todas las rutas. Si necesita renderizar contenido personalizado de la barra lateral basado en rutas, puede agregar otro Switch dentro de la barra lateral. Puede agregar tantos componentes Switch como desee siempre que estén dentro de su enrutador.
Aunque entiendo lo que intenta hacer, no creo que deba importarle colocar la barra lateral dentro del componente.
React es lo suficientemente poderoso como para almacenar en caché una gran cantidad de cosas y deshabilitar los renderizados innecesarios. Creo que el camino que debe seguir es descubrir cómo usar sabiamente useCallback
useMemo
, memo
y haga todos los trucos para evitar que se vuelvan a renderizar dentro de los componentes de la barra lateral. De esta manera, puede reutilizar el componente de la sidebar
, o cualquier componente, sin pensar en la ubicación.