react router dom v5 not rendering children - javascript

I tried a lot of tricks seen on the internet and on the official documentation of react router dom, like for example with or without "exact", other types of syntax but none of them allowed me to solve this mystery.
But, the question is why the second router does not display its components?
//index.js
ReactDOM.render(
<Provider
store={createStoreWithMiddleware(
reducers,
window.__REDUX_DEVTOOLS_EXTENSION__ &&
window.__REDUX_DEVTOOLS_EXTENSION__()
)}
>
<BrowserRouter>
<App />
</BrowserRouter>
</Provider>,
document.getElementById('root')
);
Main router from app.js, work perfectly.
//app.js
<Router>
<TransitionGroup>
<Switch location={location}>
<Route exact path="/" render={() => <HomeView handleClick={handleClick} />} />
[...]
<Route path="/Profil" render={() => <ProfilView />} />
</Switch>
</TransitionGroup>
</Router>
Profil page with a second router that not rendering components
<Row>
<Col xs={2} className='justify-content-center'>
<GroupBouton />
</Col>
<Col xs={10} className=''>
<Switch location={location}>
//when I go to this page I see the route below
<Route exact path={path} render={() => <h3>Choose a movie from the list above </h3>} />
//But this route is not rendering till I actualise the page by pushing F5
<Route path={`${path}/Myprofil`} render={() => <Myprofil />} />
</Switch>
</Col>
</Row>

Related

Nested routes content not showing up content

Below code is the entry point
<React.StrictMode>
<AppProvider>
<BrowserRouter>
<Routes>
<Route path='/admin/*' element={<Admin />} />
<Route path='*' element={<App />} />
</Routes>
</BrowserRouter>
</AppProvider>
</React.StrictMode>
I have Child routes under App.js and Admin.js, but routes under Admin is not routing as expected at the same time App.js routes are working accordingly.
Code for Admin.js is below
<div>
<ASideMenuNav />
<Routes>
<Route path='/admin/product' element={<AProductsInfo />} />
<Route path='/admin/offers' element={<AProductOffers />} />
</Routes>
</div>
Output is as shown below
enter image description here
Problem I am facing here is that when I click on any navigation menu its URL is changing but the content of the particular React component is not showing up.
Someone please tell me what am I missing. Is there something wrong with coding logic?
Descendent routes in the Routes component will have their paths built relative to the parent route. If the parent route path is "/admin/*" then the current paths are "/admin/admin/product" and "/admin/admin/offers". The solution is to remove the "/admin" path prefix on the descendent routes.
<div>
<ASideMenuNav />
<Routes>
<Route path="/product" element={<AProductsInfo />} />
<Route path="/offers" element={<AProductOffers />} />
</Routes>
</div>
Alternatively the Admin component could render an Outlet component and the routes could be converted to nested routes in the App.
<div>
<ASideMenuNav />
<Outlet />
</div>
<React.StrictMode>
<AppProvider>
<BrowserRouter>
<Routes>
<Route path='/admin' element={<Admin />}>
<Route path="product" element={<AProductsInfo />} />
<Route path="offers" element={<AProductOffers />} />
</Route>
<Route path='*' element={<App />}/>
</Routes>
</BrowserRouter>
</AppProvider>
</React.StrictMode>

How to remove a site header from specific pages React

I have set up a login page for my web app but the site header component I created earlier appears on the top. It has a menu in it that leads to other pages, so if it's on the login page a user doesn't need to login when they can just click the menu option that will lead them to the home page.
I would like the site header to be invisible on the login, register and reset pages.
index.js
return (
<BrowserRouter>
<SiteHeader />
<Routes>
<Route path="/reviews/:id" element={ <MovieReviewPage /> } />
<Route path="/movies/home" element={<HomePage />} />
<Route path="/movies/favorites" element={<FavoriteMoviesPage />} />
<Route path="/movies/upcoming" element={<UpcomingMoviesPage />} />
<Route path="/movies/:id" element={<MoviePage />} />
<Route exact path="/" element={<LoginPage />} />
<Route exact path="/register" element={<RegisterPage />} />
<Route exact path="/reset" element={<ResetPage />} />
<Route path="*" element={ <Navigate to="/" /> } />
</Routes>
</BrowserRouter>
);
};
There are many ways to do that, but personally, I prefer to do so.
export const MyLayout = ({children}) => {
return (
<>
<SiteHeader />
{children}
</>
)
}
And after all, put your PageComponent inside component wherever you need.
For example.
const HomePage = () => {
return (
<MyLayout>
<div> This is Home Page </div>
</MyLayout>
)
}
Add an Authentication Context Provider. You could then read the context and render the header when you're logged in, else not.
https://codesandbox.io/embed/authentication-with-react-context-d3x0r

Nested Routing not working in react-router version 6 [duplicate]

I was refactoring my React app after updating React Router to v6 and I got rid of the error I was getting in my routes, except now the desired layout is broken.
I need to include a permanent toolbar and a sidebar to be visible only in some pages. I tried to follow the docs but now the layout component is placed above all the pages it should be wrapping, not just overlapping them, but actually concealing them behind it.
The Layout component:
function Layout({ children }) {
return (
<div className="layout">
<Header />
<SidePanel />
<div className="main" style={{ marginTop: "100px" }}>
{children}
</div>
</div>
);
}
export default Layout;
The AppRouter component:
function AppRouter() {
return (
<Router>
<Routes>
<Route path="/" exact element={<Home />} />
<Route path="/login" element={<Login />} />
<Route path="/sign-up" element={<SignUp />} />
<Route element={<Layout />}>
<Route path="/diary" element={<Diary />} />
<Route path="/results" element={<Results />} />
<Route path="/details" element={<Details />} />
<Route path="/about" element={<About />} />
</Route>
</Routes>
</Router>
);
}
export default AppRouter;
Layout should render an Outlet for the children Routes to be rendered into.
import { Outlet } from 'react-router-dom';
function Layout() {
return (
<div className="layout">
<Header />
<SidePanel />
<div className="main" style={{ marginTop: "100px" }}>
<Outlet />
</div>
</div>
);
}
Outlet
An <Outlet> should be used in parent route elements to render their
child route elements. This allows nested UI to show up when child
routes are rendered.

Using material ui tabs with react router?

I have a project in react/typescript. I have a react router that looks like this
const Root = () => (
<>
<NavBar/>
<Router>
<Route path="/" component={Home} />
<Route path="/timer" component={TimerPage} />
</Router>
</>
);
And I have a material-ui appbar that looks like this
export default function NavBar() {
return (
<div>
<AppBar position="static">
<Tabs>
<Tab label="Timer" to="/timer" component={TimerPage} />
</Tabs>
</AppBar>
</div>
);
}
There are a few issues - first the 'to' in Tab doesn't compile. Secondly, how do I make these two components work together, given they do very similar things?
If you are trying to navigate to another page, wrap your tab component, let react-router handle with the navigation and navigate using react-router history,
<Tabs value={value} onChange={handleChange} aria-label="simple tabs
example">
<div onClick={() => history.push("/timer")}>
<Tab label="Timer" />
</div>
</Tabs>
<Router>
<Route path="/" component={Home} />
<Route path="/timer" component={TimerPage} />
</Router>
Route should be inside Switch. Also, if you write path="/" this means that whatever page you will visit will still go to "home" page. This is because react-router does something like "least" checking of routes. So, if you had defined path "/images", before "/images/1", both will route you to "/images". Instead you could change the order of these paths, or add exact keyword before the first one.
Take a look at example below.
<Router>
<Switch>
<Route exact path="/" component={Home} />
<Route path="/timer" component={TimerPage} />
</Switch>
</Router>
or
<Router>
<Switch>
<Route path="/timer" component={TimerPage} />
<Route path="/" component={Home} />
</Switch>
</Router>
As for your second issue, you should put your AppBar (or div or any container) inside Router and assign Link to component property of Tab:
<Router>
<AppBar position="static">
<Tabs>
<Tab label="Timer" to="/timer" component={Link} />
</Tabs>
</AppBar>
</Router>
Keep in mind that Link component is imported from react-router and not from #mui.

React: how to declare routes inside a component?

First off, I tried searching for this issue before I posted but couldn't find a solution for a similar use case.
So I have a component called App.js where I define all my top level routes:
<TransitionGroup>
<CSSTransition key={location.key} mountOnEnter={true} unMountOnExit={true} timeout={800} classNames="fade-up-down">
<Switch location={location}>
<Route exact path="/" component={Home} />
<Route exact path="/about" component={About} />
<Route exact path="/artists" component={Artists} />
<Route path="/artworks/:slug" component={Artwork} />
</Switch>
</CSSTransition>
</TransitionGroup>
Now, inside the home component, I want to have my second level of routes, which I didn't do in App.js because I had props to pass from Home.js to the child components. The routes portion in my Home.js looks like this:
<Switch>
<Route exact path="/" render={(props) => <Map {...props} artworks={artworks} />} />
<Route exact path="/grid" render={(props) => <Grid {...props} artworks={artworks} />} />
<Route exact path="/rainbow" render={(props) => <Rainbow {...props} artworks={artworks} />} />
</Switch>
The second level routes inside Home.js work fine, but when I try to go to any of the other top level routes, eg. /artists/ or /about, they do not work.
Can someone please point me to the right direction here? Thanks!
I don't think is it possible the way you want.
I think you are overriding the App Router when you navigate to you Home component.
Your routes has to be on a top lvl of your App
Moving the routes after the first one from to the top worked. Here's how it looks now:
<TransitionGroup>
<CSSTransition key={location.key} mountOnEnter={true} unMountOnExit={true} timeout={800} classNames="fade-up-down">
<Switch location={location}>
<Route exact path="/about" component={About} />
<Route exact path="/artists" component={Artists} />
<Route path="/artworks/:slug" component={Artwork} />
<Route path="/" component={Home} />
</Switch>
</CSSTransition>
</TransitionGroup>

Categories

Resources