How can you use multiple outlets in react-router 6? - react-router-dom

For example, say I have a Header and Content sub components that I would like to render on 1 page (single route path).
const App = () => {
<div>
<header><Outlet /></header>
<content><Outlet /><content>
</div>
}
const RouteConfig = () => {
return (
<Routes>
<Route path="/" element={<App />} />
<Route path="/app" element={<Header />} />
<Route path="/app" element={<Content /> />
</Route>
</Routes>
)
}
The above outputs the header contents for both Outlets, instead of the header and the contents. Is there a way to have multipe outlets?

Related

Provider.render(): A valid React element (or null) must be returned. You may have returned undefined, an array or some other invalid object

When I try to run the website it shows the error in the this line and says it is not valid
ReactDOM.render(<App />, document.getElementById("root"));
Here is the App component in App.js file
class App extends Component {
render() {
return (
<Provider store={store}>
<Router>
<SideBar />
<Switch>
<Route exact path="/" component={Home} />
<Route exact path="/signup" component={Signup} />
<Route exact path="/login" component={Login} />
<Route exact path="/dashboard" component={Dashboard} />
<Route exact path="/dashboard/course" component={Course} />
<Route
exact
path="/dashboard/course/lectures"
component={Lecture}
/>
<Route
exact
path="/dashboard/course/discussion"
component={Discussion}
/>
<Route component={NotFound} />
</Switch>
<DeletePopup />
</Router>
</Provider>
);
}
}

How to hide footer and menu when notfound page rendering in Router v6 [duplicate]

This question already has answers here:
How do I render components with different layouts/elements using react-router-dom v6
(2 answers)
Closed 10 months ago.
As you can see I want to hide menu bar and footer when notfound page is rendering .I tried all the other solutions but didn't happen to work in my Scenario. I wanted the Navbar and footer hide in 3 notfound Page. I use react-router version 6 and fuctional App component. Please Help me figure out this solution
`
<Menubar />
<Routes>
<Route path='/' element={<Home />} />
<Route path='/home' element={<Home />} />
<Route path='/inventory/:id' element={
<PrivateRoute>
<Inventory />
</PrivateRoute>
} />
<Route path='/manageinventory' element={
<PrivateRoute>
<ManageInventory />
</PrivateRoute>
} />
<Route path='/addinventory' element={
<PrivateRoute>
<AddInventory />
</PrivateRoute>
} />
<Route path='/myitems' element={
<PrivateRoute>
<MyItems />
</PrivateRoute>
} />
<Route path='/login' element={<Login />} />
<Route path='/register' element={<Register />} />
<Route path='/blogs' element={<Blog />} />
<Route path='*' element={<NotFound />} />
</Routes>
<Footer />
Use a master page that contains Navbar and Footer and each Created component will contains a master page except the notFound Page
{/* Layout component */}
import React from "react";
import Sidebar from "./Navbar ";
import Sidebar from "./Footer ";
const Layout = ({ children}) => {
return (
<>
<Navbar />
<main>{children}</main>
<Footer />
</>
);
};
export default Layout;
and for any new component, you will call the master page
{/* For Home, Inventory, ... components */}
import React from "react";
import Layout from "../components/Layout";
const Home = () => {
return (
<Layout>
{/* your code jsx here */}
</Layout>
);
};
export default DahsboardScreen;

how to set condition in react router DOM version 6?

I want to convert this code which has been written in react router v5 to v6 but I don't know how to do it, in general I want to set if the user doesn't have an account, redirect them to registration page an so on.
I'm aware of switch change and redirect the only problem is in this line of code :
<Route exact path="/">
{user ? <Home /> : <Redirect to="/register" />}
</Route>
the whole code:
import "./app.scss";
import Home from "./pages/home/Home";
import Register from "./pages/register/Register";
import Watch from "./pages/watch/Watch";
import Login from "./pages/login/Login";
import {
BrowserRouter as Router,
Switch,
Route,
Redirect,
} from "react-router-dom";
import { useContext } from "react";
import { AuthContext } from "./authContext/AuthContext";
const App = () => {
const { user } = useContext(AuthContext);
return (
<Router>
<Switch>
<Route exact path="/">
{user ? <Home /> : <Redirect to="/register" />}
</Route>
<Route path="/register">
{!user ? <Register /> : <Redirect to="/" />}
</Route>
<Route path="/login">{!user ? <Login /> : <Redirect to="/" />}</Route>
{user && (
<>
<Route path="/movies">
<Home type="movie" />
</Route>
<Route path="/series">
<Home type="series" />
</Route>
<Route path="/watch">
<Watch />
</Route>
</>
)}
</Switch>
</Router>
);
};
export default App;
You can use the element prop of v6, you don't need to use an exact prop on <Route path="/"> anymore. This is because all paths match exactly by default. If you want to match more of the URL because you have child routes use a trailing * as <Route path="/*" />.
import { BrowserRouter, Navigate, Route, Routes } from 'react-router-dom';
.
.
.
return (
<BrowserRouter>
<Routes>
<Route path="/" element={user ? <Home /> : <Navigate to="/register" replace />} />
.
.
.
</Routes>
</BrowserRouter>
)
.
.
.
Also you can see more detail in reactrouter docs:
https://reactrouter.com/docs/en/v6/getting-started/overview

routing problem: my routes on render are not working?

import Home from "./Pages/home/Home";
import TopBar from "./components/topbar/Topbar.jsx";
import Single from "./Pages/single/Single";
import Write from "./Pages/write/Write";
import Settings from "./Pages/settings/Settings";
import Login from "./Pages/login/Login";
import Register from "./Pages/register/Register";
import { BrowserRouter as Router, Routes, Route, Link } from "react-router-dom";
function App() {
const user = true;
return (
<Router>
<TopBar />
<Routes>
<Route exact path="/" component={Home} />
<Route path="/register" component={user ? <Home /> :{Register}} />
<Route path="/login" component={user ? <Home /> : {Login}} />
<Route path="/write" component={user ? <Write /> : {Register}} />
<Route path="/settings" component={user ? <Settings /> : {Register}} />
<Route path="/post/:Id" component={Single} />
</Routes>
</Router>
);
}
export default App;
This is my code but the homepage isnt rendering apart from topbar how do i resolve this. Am not sure if the syntax is correct.
Yeah, the syntax is a little mixed up. In react-router-dom version 6 the Route components render their components on the element prop as JSX, not on any component or render prop as a reference to a React component or function that returns JSX.
function App() {
const user = true;
return (
<Router>
<TopBar />
<Routes>
<Route path="/" element={<Home />} />
<Route path="/register" element={user ? <Home /> : <Register />} />
<Route path="/login" element={user ? <Home /> : <Login />} />
<Route path="/write" element={user ? <Write /> : <Register />} />
<Route path="/settings" element={user ? <Settings /> : <Register />} />
<Route path="/post/:Id" element={<Single />} />
</Routes>
</Router>
);
}

Jest enzyme test router with props

I have react application and started covering it with unit tests.
My app file contains:
export default class App extends Component {
render() {
return (
<Provider store={store}>
<Router history={history}>
<div>
<Header />
<Switch>
<Route exact path="/" component={Home} />
<Route exact path="/detail/:collectionName/:RecordId/:firmId" component={DetailDialog} />
<Route exact path="/dashboard" component={Dashboard} />
<Route path="/auth-login" component={LogIn} />
<Route path="/auth-register" component={Register} />
<Route path="/user-manager" component={this.props.decoded.role==='Admin' ? Admin : Home} />
</Switch>
</div>
</Router>
</Provider>
);
}
}
I want to make next test: go to login, check href and by href check component.
it.only('test right component is attached', () => {
const wrapper = shallow(<Login loginUser={fn}/>);
const registerLink = wrapper.find("[data-qa='sign-up']").props().href;
const history = jest.fn();
const props = {
decoded: {role: 'Admin'}
}
const router = mount(
<MemoryRouter initialEntries={[registerLink]}>
<App history={history} {...props} />
</MemoryRouter>
);
expect(router.find(Register)).toHaveLength(1);
});
Until mounting everything is ok. But on mount I receive the next error:
console.error
Error: Uncaught [Error: Unable to find node on an unmounted component.]
What am I doing wrong? How can I mount the component and check that Register is inside?
Try to pass a history prop not as a jest.fn(), but as a { push : jest.fn() }

Resources