I am having trouble in changing the page in react with react-router-dom. here is my router :-
import { Route, Switch, BrowserRouter } from 'react-router-dom';
import HomePage from '../pages/grocery';
import Profile from '../pages/profile';
import CheckoutPage from '../pages/checkout';
export default function Routes(props) {
return (
<BrowserRouter>
<Switch>
<Route path="/" name="Home" component={HomePage} exact />
<Route path="/profile" name="Profile" component={Profile} />
<Route path="/checkout" name="Checkout" component={CheckoutPage} />
</Switch>
</BrowserRouter>
);
}
and here is my Link tag
<Link to="/profile">Profile</Link>
the problem here is that the second Route element, have a "/" too, and the first one will access any element that starts with an "/".
How to fix this?
with Route you can put "exact" just before path, so it will only access that specific route, no matters what comes after that.
example:
<Route exact path="/" name="Home" component={HomePage} />
<Route exact path="/profile" name="Profile" component={Profile} />
<Route exact path="/checkout" name="Checkout" component={CheckoutPage} />
this way you will not have problems accessing your others pages or components.
Related
I have one Navbar in React with the following code
import './App.css';
import { BrowserRouter as Router, Route, Link, Switch } from 'react-router-dom';
import Header from './components/header/Header';
import Home from './components/home/Home';
import About from './components/about/About';
import Accessories from './components/accessories/Accessories';
import Category1 from './components/accessories/categories/Category1';
import Category2 from './components/accessories/categories/Category2';
import Category3 from './components/accessories/categories/Category3';
import Category4 from './components/accessories/categories/Category4';
import Contact from './components/contact/Contact';
import Footer from './components/footer/Footer';
const App = () => {
return (
<div className="App">
<Header />
<Router>
<Switch>
<Route exact path="/">
<Home />
<About />
<Accessories />
<Contact />
</Route>
<Route exact path="/category1">
<Category1 />
</Route>
<Route exact path="/category2">
<Category2 />
</Route>
<Route exact path="/category3">
<Category3 />
</Route>
<Route exact path="/category4">
<Category4 />
</Route>
</Switch>
</Router>
<Footer />
</div>
);
}
export default App;
I can go smoothly from / to /category1, but when I reroute to / from /category1, no rerendering is happening until I refresh the page.
I have no idea what to do now. Thank you for any help in advance
Edited: I just changes all my Links to anchor tags and now they are working but is it a good practice?
<Route exact path="/">
<Home />
<About />
<Accessories />
<Contact />
</Route>
Put the above code after all the routes are being defined and it should work
<Switch>
<Route exact path="/category1">
<Category1 />
</Route>
<Route exact path="/category2">
<Category2 />
</Route>
<Route exact path="/category3">
<Category3 />
</Route>
<Route exact path="/category4">
<Category4 />
</Route>
<Route exact path="/">
<Home />
<About />
<Accessories />
<Contact />
</Route>
</Switch>
The '/' path should be defined at the last after all the paths have been defined
You have to use the element to redirect to other routes. In "/category1", you can use the element to redirect "/" without reloading the page.
I have one problem that I can not understand. I am totally a beginner in ReactJS so I hope you will help me. I made Navigation with React Router and it works, but when I start to render all other components in App.js nothings happened. When I am routing through the navigation bar it is rendering, but on scroll, nothing happened.
This is my App.js without rendering other components that work normally, but when I add something like , it is the same without scroll.
my code :
const App = () => {
return (
<div>
<Router>
<Topbar />
<About />
<Switch>
<Route exact path="/" component={Home} />
<Route path="/about" component={About} />
<Route path="/service" component={Service} />
<Route path="/portfolio" component={Portfolio} />
<Route path="/contact" component={Contact} />
</Switch>
</Router>
</div>
);
};
export default App;
You need to use a redirect
1/ import {Redirect} from 'react-router-dom';
2/ Change your Home route to <Route exact path="/home" component={Home} />
3/ Add the redirect (It must be the last route)
<Route exact path="/">
<Redirect to="/home" />
</Route>
Example :
import React from 'react';
import {
BrowserRouter as Router,
Route,
Switch,
Redirect
} from 'react-router-dom';
import Home from './Home';
import About from './About';
import Service from './Service';
import Portfolio from './Portfolio';
import Contact from './Contact';
const App = () => {
return (
<Router>
<Switch>
<Route path="/" component={Home} />
<Route path="/about" component={About} />
<Route path="/service" component={Service} />
<Route path="/portfolio" component={Portfolio} />
<Route path="/contact" component={Contact} />
{/* Redirect */}
<Route exact path="/">
<Redirect to="/home" />
</Route>
</Switch>
</Router>
);
};
export default App;
If you want to check a demo : Stackblitz
I'm trying show Error component if matches not found, but nothing happens - when I choose non-existing route, I see only blank page.
The Main component adds sidebar menu in example and renders all it childes inside in rest.
When all Route componets placed directly inside Switch - all works (including Error).
But in example below, Error component does not render - if route does not match - only blank page.
If Error component placed inside Main, in that case it will be rendered even for existing routes.
import React from 'react';
import { Switch, Route } from "react-router-dom";
import Signin from "../../containers/Signin";
import Signup from "../../containers/Signup";
import Error from "../../containers/Error";
import Courses from "../../containers/Courses";
import Course from "../../containers/Course";
import Quiz from "../../containers/Quiz";
import Header from "../Header";
import "./App.css";
import Library from "../../containers/Library";
import QuizResults from "../../containers/QuizResults";
import Main from "../Main";
import StudentsList from "../../containers/StudentsList";
function App()
{
return (
<div className="App">
<Header isLogged={false}/>
<Switch>
<Route exact path='/' component={Signin} />
<Route path='/signup' component={Signup} />
<Main>
<Route path='/courses' component={Courses} />
<Route path='/course/:id' component={Course} exact/>
<Route path='/quiz' component={Quiz} />
<Route path='/library' component={Library} />
<Route path='/quiz-results' component={QuizResults} />
<Route path='/students' component={StudentsList} />
<Route component={Error} />
</Main>
</Switch>
</div>
);
}
export default App;
So, how to properly render Error component if no matches found?
Try using a wildcard.
<Route path="/*" component={Error} />
Add exact word to the route. And better approach will be to set the Error component name to NotFound or FourZeroFour . It will work then.
<Router>
<Switch>
<Route exact path='/' component={Signin} />
<Route exact path='/signup' component={Signup} />
<Main>
<Route exact path='/courses' component={Courses} />
<Route exact path='/course/:id' component={Course} />
<Route exact path='/quiz' component={Quiz} />
<Route exact path='/library' component={Library} />
<Route exact path='/quiz-results' component={QuizResults} />
<Route exact path='/students' component={StudentsList} />
<Route component={NotFound} />
</Main>
</Switch>
</Router>
Solution for this problem - place another Switch around Route components:
import React from 'react';
import { Switch, Route } from "react-router-dom";
import Signin from "../../containers/Signin";
import Signup from "../../containers/Signup";
import NotFound from "../../containers/NotFound";
import Courses from "../../containers/Courses";
import Course from "../../containers/Course";
import Quiz from "../../containers/Quiz";
import Header from "../Header";
import "./App.css";
import Library from "../../containers/Library";
import QuizResults from "../../containers/QuizResults";
import Main from "../Main";
import StudentsList from "../../containers/StudentsList";
function App()
{
return (
<div className="App">
<Header isLogged={false}/>
<Switch>
<Route exact path='/' component={Signin} />
<Route exact path='/signup' component={Signup} />
<Main>
<Switch>
<Route exact path='/courses' component={Courses} />
<Route exact path='/course/:id' component={Course} />
<Route exact path='/quiz' component={Quiz} />
<Route exact path='/library' component={Library} />
<Route exact path='/quiz-results' component={QuizResults} />
<Route exact path='/students' component={StudentsList} />
<Route path='*' component={NotFound} />
</Switch>
</Main>
</Switch>
</div>
);
}
export default App;
I am trying to access the FolderDetail component once the url /folders/xy is called. Instead of getting FolderDetail component I always get the Folders component which lies in /folders... Please help.
import React from 'react';
import { BrowserRouter, Route, Switch } from 'react-router-dom';
function App() {
return (
<BrowserRouter>
<div className="App">
<Navigation />
<Switch>
<Route path="/" component={Home} exact />
<Route path="/folders" component={Folders} />
<Route path="/folders/:id" component={FolderDetail} />
<Route path="/login" component={Login} />
</Switch>
</div>
</BrowserRouter>
);
}
export default App;
You should add exact to all Routes components, this is a working codesandbox :
const App = () => {
return (
<BrowserRouter>
<div className="App">
<Navigation />
<Switch>
<Route exact path="/" component={Home} />
<Route exact path="/folders" component={Folders} />
<Route exact path="/folders/:id" component={FolderDetail} />
</Switch>
</div>
</BrowserRouter>
);
};
A switch takes the firs matched route so you need to reorder your routes like this, (also add exact)
<Switch>
<Route exact path="/folders/:id" component={FolderDetail} />
<Route exact path="/folders" component={Folders} />
<Route exact path="/login" component={Login} />
<Route exact path="/" component={Home} exact />
</Switch>
Always put the more specific routes first.
I am trying to figure out why if let’s say I am in the middle of the route/page /current-path, if I go to /new-path, then /new-path loads just in the middle or in the same position where I left the old path. The regular behavior should be if I go to a new route, the new route/page should load from the top.
I recorded a video for you to see what I talk about.
If you see, in the video I go to a new route and if I want to go to the top, I have to scroll to it.
This is the component where I have my routes:
import { BrowserRouter as Router, Route, Link, Switch } from 'react-router-dom';
// … rest of the imports here
const App = () => (
<ReduxProvider store={reduxStore}>
<Router>
<div className="App">
<div className="App-container">
<Switch>
<Route path="/applications" component={Applications} />
<Route path="/terms" component={Terms} />
<Route path="/signup" component={SignupPage} />
<Route path="/choose-profile" component={ChooseProfile} />
<Route path="/profile-completion" component={ProfileCompletion} />
<Route path="/investor-personal-profile" component={InvestorProfile} />
<Route path="/startup-application" component={StartupApplication} />
<Route path="/investor-application" component={InvestorApplication} />
<Route exact path="/startup/:startup" component={StartupProfile} />
<Route path="/search" component={SearchStartup} />
<Route exact path="/investor/search" component={SearchProfile} />
<Route path="/wiretransfer-instructions" component={WireTransfer} />
<Route exact path="/about-us" component={AboutUs} />
<Route exact path="/how-it-works" component={HowItWorks} />
<Route exact path="/faq" component={Faqs} />
<Route exact path="/:startup" component={StartupPublicProfile} />
<Route path="/" component={HomePage} />
</Switch>
</div>
</div>
<Footer />
</Router>
</ReduxProvider>
);
export default App;
I already tried to go to a new route with the Link component of react router, <Link to="/about-us">About Us</Link> and also like this =>
<button onClick={() => history.push('/faq')}>
FAQ and Guides
</button>
So what could I be doing wrong?