React router dom don't render pages - javascript

my page don't render the HomePage
but if i only use
h1 Test HomePage h1
in render it work.
i wanna know where i should fix it or what im doing wrong
thanks for help
or you need to see the other file you can tell me
im kinda new to the programming
import React, { Component } from "react";
import { render } from "react-dom";
import HomePage from "./HomePage";
import RoomJoinPage from "./RoomJoinPage";
import CreateRoomPage from "./CreateRoomPage";
export default class App extends Component {
constructor(props) {
super(props);
}
render() {
return (
<div>
<HomePage/>
</div>
);
}
}
const appDiv = document.getElementById("app");
render(<App />, appDiv);
this is my HomePage Code
import React, { Component } from "react";
import RoomJoinPage from "./RoomJoinPage";
import CreateRoomPage from "./CreateRoomPage";
import {
BrowserRouter as Router,
Switch,
Route,
Link,
Redirect,
} from "react-router-dom";
export default class HomePage extends Component {
constructor(props) {
super(props);
}
render() {
return (
<Router>
<Switch>
<Route exact path="/">
<p>This is the home page</p>
</Route>
<Route path="/join" component={RoomJoinPage} />
<Route path="/create" component={CreateRoomPage} />
</Switch>
</Router>
);
}
}

Related

React router changes url but not re-render

React Router change the URL but the component is not rendered I have already looked for answer but none of those example is worked Current React Router & React Router DOM version is 6.
My MainComponent:
import React, { Component } from 'react';
import Header from './HeaderComponent';
import Footer from './FooterComponent';
import { Routes, Route, Redirect } from 'react-router-dom';
import Stafflist from './StaffComponent';
import {STAFFS} from '../shared/staffs';
import StaffDetail from './StaffDetailComponent';
class Main extends Component{
constructor(props){
super(props);
this.state ={
staffs : STAFFS
};
}
render(){
const StaffWithId = ({match}) =>{
return(
<StaffDetail staff={this.state.staffs.filter((staff) => staff.id === parseInt(match.params.staffId,10))}/>
)
}
return(
<div>
<Header/>
<Routes>
<Route exact path='/staff' element={<Stafflist staffs={this.state.staffs} />}/>
<Route path='/staff/:staffId' element={StaffWithId}/>
</Routes>
<Footer/>
</div>
);
}
}
export default Main;
Your problem seems to be this line:
<Route path='/staff/:staffId' element={StaffWithId}/>
StaffWithId is a functional component and shoul be called with brackets < />.
like this:
<Route path='/staff/:staffId' element={<StaffWithId/>}/>

Page contains from many component turn blank when reload page?

I'm a newbie in React js and currently i'm building a layout that contains from many components
For example, a home page layout that contains sidebar component, topbar component, footer component and main content component.
When i click on a link in sidebar component, the main content will be changed based on url of link i clicked on and other components will be same on all pages regardless of url.
Here is my code:
MainLayout.js
import React, { Component } from 'react';
import { Route } from 'react-router-dom';
import Sidebar from '../components/Sidebar';
const MainLayout = ({children, ...rest}) => {
return (
<div className="page page-dashboard">
{/* <div className="sidebar"><Sidebar></Sidebar></div> */}
<div className="main">
{children}
</div>
</div>
)
}
const MainLayoutRoute = ({component: Component, ...rest}) => {
return (
<Route {...rest} render={matchProps => (
<MainLayout>
<Component {...matchProps} />
</MainLayout>
)} />
)
};
export default MainLayoutRoute;
MainPage.js
import React, { Component } from 'react';
import { BrowserRouter as Router, Route, Redirect, Switch } from 'react-router-dom';
import Sidebar from './Sidebar';
import Header from './Header';
import Footer from './Footer';
import UsersList from './UsersList';
export default class MainPage extends Component {
render() {
return (
<Router>
<div>
<Header/>
<Sidebar/>
<div className="wrapper">
<Switch>
<Route path={"/users"} component={UsersList} />
</Switch>
</div>
<Footer></Footer>
</div>
</Router>
);
}
}
Sidebar.js
import React, { Component } from 'react';
import { BrowserRouter as Router, Route, Redirect, Switch, Link } from 'react-router-dom';
export default class Sidebar extends Component {
render() {
return (
<div className="sidenav">
<ul>
<li><Link to="/users">Users</Link></li>
<li><Link to="/settings">Setting</Link></li>
</ul>
</div>
);
}
}
UserList.js
import React, { Component } from 'react';
import { BrowserRouter as Router, Route, Redirect, Switch, Link } from 'react-router-dom';
export default class UsersList extends Component {
render() {
return (
<div>
<button><Link to="/newuser">Add new user</Link></button>
</div>
);
}
}
App.js
import React, { Component } from 'react';
import { BrowserRouter as Router, Route, Redirect, Switch } from 'react-router-dom';
import logo from './logo.svg';
import './App.css';
import './css/custom.scss';
/** Layouts **/
import LoginLayoutRoute from "./layouts/LoginLayout";
import MainLayoutRoute from "./layouts/MainLayout";
/** Components **/
import MainPage from './components/MainPage';
import LoginPage from './components/LoginPage'
export default class App extends Component {
render() {
return (
<Router>
<Switch>
<Route exact path="/">
<Redirect to="/login" />
</Route>
<LoginLayoutRoute path="/login" component={LoginPage} />
<MainLayoutRoute path="/home" component={MainPage} />
</Switch>
</Router>
);
}
}
But when i refresh the page, it turned blank like this:
Before i refresh page
After i refresh page
How can i fix this ?

Header component keeps rerendering when changing Route on React

When pressing {Link} and changing Route, the header component NavBar keeps rerendering, even when is outside the Switch component from react-router-dom.
here are the files:
Main index.js file:
import React from 'react'
import styles from './styles.css'
import {Route, Switch} from 'react-router-dom'
import Home from './Home'
import Settings from './Settings'
import Layout from './Layout'
import Contact from './Contact'
import NavBar from 'App/components/NavBar'
export default class MainHome extends React.Component {
static propTypes = {}
render() {
return (
<div className={styles.container}>
<NavBar />
<Switch>
<Route path="/settings" component={Settings} />
<Route path="/contact" component={Contact} />
<Route path="/" component={Home} />
</Switch>
</div>
)
}
}
Home.js
import React from 'react'
import styles from './styles.css'
import {Link} from 'react-router-dom'
export default class Home extends React.Component {
static propTypes = {}
render() {
return (
<div className={styles.container}>
<h1>Hello world</h1>
<Link to="/contact">Contact</Link>
</div>
)
}
}
Contact.js
import React from 'react'
import styles from './styles.css'
import {Link} from 'react-router-dom'
export default class Contact extends React.Component {
static propTypes = {}
render() {
return (
<div className={styles.container}>
Contact
<Link to="/">Home</Link>
</div>
)
}
}
The current project is pretty simple: the index.js file has inside the Home and Contact components, and the NavBar component as a header outside the Switch.
#MattyJ I'm using react-router-dom#^4.2.1. The component with the Router looks like this:
import React from 'react'
import Root from 'App/Root'
import Pages from './Pages'
import {BrowserRouter} from 'react-router-dom'
export default class App extends React.Component {
render() {
return (
<BrowserRouter key={Math.random()}>
<Root>
<Pages />
</Root>
</BrowserRouter>
)
}
}
Pages encapsulates two components: App, where is located the Switch component from my question, and Auth for managing autentication:
import React from 'react'
import authRouteRegex from './Auth/routeRegex'
import {withRouter} from 'react-router'
import PropTypes from 'prop-types'
import DynamicComponent from 'App/components/DynamicComponent'
import App from './App'
#withRouter
export default class Pages extends React.Component {
static propTypes = {
location: PropTypes.object
}
render() {
if (authRouteRegex.test(this.props.location.pathname)) {
const Component = DynamicComponent(() => import('./Auth'))
return <Component />
}
return <App />
}
}

Same component used in multiple routes is being remounted react-router

I created a simple react application. It has a header and three other components called welcome, feature 1 and feature 2.
index.js
import React from 'react'
import { render } from 'react-dom'
import { BrowserRouter, Route } from 'react-router-dom'
import App from './App';
render((
<BrowserRouter>
<Route path="/" component={App} />
</BrowserRouter>
), document.getElementById('root'));
App.js
import React from 'react'
import Header from './Header'
import Main from './Main'
const App = () => (
<div>
<Header />
<Main />
</div>
)
export default App
Header.js
import React, { Component } from 'react';
export default class Header extends Component {
componentDidMount() {
APICall('/user')
}
render() {
return (
<div>I am header</div>
)
}
}
Main.js
import React, { Component } from 'react'
import { Route } from 'react-router-dom'
import Welcome from './Welcome'
import Feature1 from './Feature1'
import Feature2 from './Feature2'
export default class Main extends Component {
render() {
return (
<div>
<Route exact path="/" component={Welcome} />
<Route path="/feature1" component={Feature1} />
<Route path="/feature2" component={Feature2} />
</div>
)
}
}
welcome.js
import React, { Component } from 'react';
export default class Welcome extends Component {
render() {
return (
<div>Welcome!</div>
)
}
}
Feature1.js
import React, { Component } from 'react';
export default class Feature1 extends Component {
render() {
return (
<div>I am Feature1</div>
)
}
}
Feature2.js
import React, { Component } from 'react';
export default class Feature2 extends Component {
render() {
return (
<div>I am Feature2</div>
)
}
}
Welcome, Feature1 and Feature2 are in different routes where as Header is common in all the routes. Say I have a user and I want to show the username on the header. I will make an API call to get the username in componentDidMount() life-cycle hook of header.
Now if I change the route, I don't want the API call to be made again as the username is not going to change. And I thought that is how this was going to behave. As Header component is same in all the routes, I thought Header won't re-mount when I change the route. But that is not what is happening. It is remounting and making the API call again. How can I make sure that the API call is made only once?
I think in this case considering your Header is aware of what User is logged, i.e. App.js state passed down as props, you could use shouldComponentUpdate():
shouldComponentUpdate(nextProps, nextState) {
// see if user changed
if(nextProps.user !== nextState.user){
return true;
}
// returning false will prevent re-rendering
return false;
}
I hope this is somehow useful.
Have a good day!
change to this in index.js:-
<BrowserRouter>
<App />
</BrowserRouter>
It seems you messed up the routing then, because in your router you have only one route registered, which seems to trigger on any child route change. Also, routes should be wrapped in a Switch component.
Check out this structure
/** index.js */
import React from 'react'
import { render } from 'react-dom'
import App from './App';
render(<App />, document.getElementById('root'));
/** App.jsx */
import React from 'react'
import Header from './Header'
import Main from './Main'
import { BrowserRouter, Route, Switch } from 'react-router-dom'
const App = () => (
<div>
<Header />
<BrowserRouter>
<Switch>
<Route exact path="/" component={Homepage} />
<Route exact path="/f1" component={Feature1} />
<Route exact path="/f2" component={Feature2} />
<Route component={NotFound} />
</Switch>
</BrowserRouter>
</div>
)
export default App

history or context .push() not working because of blank object [duplicate]

I have a Dashboard with rotating slides, each of which has a corresponding tab in Bldgs. Both Dashboard.js and Bldgs.js are children to my App.js.
When a user clicks on a specific slide A in Dashboard.js, Dashboard needs to tell App.js so that App can tell Bldgs.js to have tab A displayed when it routes to Bldgs.
I believe that I am passing the correct index value from Dashboard up to App and down to Bldgs. However, an error is being thrown in my App.js file stating:
Uncaught TypeError: Cannot read property 'push' of undefined
My code was working fine before I started passing my handleClick() function to my Dashboard component.
Index.js
import React from 'react';
import ReactDOM from 'react-dom';
import App from './App';
import './index.css';
import injectTapEventPlugin from 'react-tap-event-plugin';
import MuiThemeProvider from 'material-ui/styles/MuiThemeProvider';
import { BrowserRouter as Router } from 'react-router-dom';
import { hashHistory } from 'react-router';
// Needed for onTouchTap
// http://stackoverflow.com/a/34015469/988941
injectTapEventPlugin();
ReactDOM.render(
<MuiThemeProvider>
<Router history={hashHistory}>
<App />
</Router>
</MuiThemeProvider>,
document.getElementById('root')
);
App.js
import React from 'react';
import { Route } from 'react-router-dom';
import Dashboard from './Dashboard';
import Bldgs from './Bldgs';
var selectedTab;
class App extends React.Component {
constructor(props) {
super(props);
this.handleClick = this.handleClick.bind(this);
selectedTab = 0;
}
handleClick(value) {
selectedTab = value;
// console.log(selectedTab);
this.props.history.push('/Bldgs');
// console.log(this.props);
}
render() {
var _this = this;
return (
<div>
<Route exact path="/" render={(props) => <Dashboard {...props} handleClick={_this.handleClick} />} />
<Route path="/Bldgs" component={Bldgs} curTab={selectedTab} />
</div>
);
}
}
export default App;
Dashboard.js
import React, { Component } from 'react';
import './Dashboard.css';
import { AutoRotatingCarousel, Slide } from 'material-auto-rotating-carousel';
...
var curIndex;
class Dashboard extends Component {
constructor(props) {
super(props);
this.handleEnter = this.handleEnter.bind(this);
this.handleChange = this.handleChange.bind(this);
curIndex = 0;
}
handleEnter(e) {
// console.log(curIndex);
this.props.handleClick(curIndex);
}
handleChange(value) {
// console.log(value);
curIndex = value;
}
...
}
export default Dashboard;
Bldgs.js
...
var curTab;
class Bldgs extends Component {
constructor(props) {
super(props);
this.handleChange = this.handleChange.bind(this);
this.goHome = this.goHome.bind(this);
curTab = 0;
}
handleChange(value) {
this.setState({'selectedTab': value});
console.log(this.state);
}
goHome(e) {
this.props.history.push('/');
}
...
}
export default Bldgs;
In order to make use of history in the App component use it with withRouter. You need to make use of withRouter only when your component is not receiving the Router props,
This may happen in cases when your component is a nested child of a component rendered by the Router or you haven't passed the Router props to it or when the component is not linked to the Router at all and is rendered as a separate component from the Routes.
import React from 'react';
import { Route , withRouter} from 'react-router-dom';
import Dashboard from './Dashboard';
import Bldgs from './Bldgs';
var selectedTab;
class App extends React.Component {
constructor(props) {
super(props);
this.handleClick = this.handleClick.bind(this);
selectedTab = 0;
}
handleClick(value) {
selectedTab = value;
// console.log(selectedTab);
this.props.history.push('/Bldgs');
// console.log(this.props);
}
render() {
var _this = this;
return (
<div>
<Route exact path="/" render={(props) => <Dashboard {...props} handleClick={_this.handleClick} />} />
<Route path="/Bldgs" component={Bldgs} curTab={selectedTab} />
</div>
);
}
}
export default withRouter(App);
Documentation on withRouter
for React-router V4
change the function to
onClick={this.fun.bind(this)}
fun() {
this.props.history.push("/Home");
}
and
import { withRouter } from 'react-router-dom';
export it later as:
export default withRouter (comp_name);
When working with functional components we can use useHistory() to history to push method
import { useHistory } from "react-router-dom";
and then in function we have to assign the useHistory()
let history = useHistory();
Now We can use history.push to relocate to desired page
history.push('/asdfg')
You are trying to push with out giving the task to a valid library. on App.js
So:
on App.js
You are using BrowserRouter which is handling the history of pages by default, with this react-router-dom function you are relying on BrowserRouter to do this fore you.
Use Router instead of BrowserRouter to gain control of you're history, use history to control the behavior.
Use npm history "yarn add history#4.x.x" / "npm i history#4.x.x"
import Route from 'react-router-dom'; //don't use BrowserRouter
import createBrowserHistory from 'createBrowserHistory';
Remember to exoport it !!
export const history = createBrowserHistory();
4.import history to Dashboard.js
5.import history to Bldgs.js
hope this helps !!!
#brunomiyamotto
See my App.js file below. I ended up passing {...this.props} to the NavBar Component that I had created.
The NavBar component is not part of my Switch routes.
import React, { Component } from 'react';
import { Route, Link, Redirect, Switch, withRouter } from 'react-router-dom'
import Navbar from './Navbar.js';
import Home from './Home/HomeCont';
import Login from './Register/Login';
import Dashboard from './Dashboard/DashboardCont';
import './App.css';
class App extends Component {
constructor(props){
super(props);
}
render() {
return (
<div className="App">
<header className="App-header">
//SOLUTION!!!
<Navbar {...this.props}/>
</header>
<Switch>
<React.Fragment>
<Route exact path="/" render={(props) => <Home {...props}/>}/>
<Route exact path="/login" render={(props) => <Login {...props}/>}/>
</React.Fragment>
</Switch>
</div>
);
}
}
export default withRouter(App);
Within my Navbar. The button I used had the following code. I had to .bind(this) to see the history and be able to user this.props.history.push("/")
<Button
color="inherit"
onClick={this.handleLogout.bind(this)}>Logout</Button>
My mistake was the wrong import in conjuction with BrowserRouter, ie:
incorrect:
import { useHistory } from 'react-router'
correct:
import { useHistory } from 'react-router-dom'
I solved this error by wrapping the component inside the BrowserRouter.
Don't forget about this, it's a very common mistake.
import { BrowserRouter} from 'react-router-dom';
<BrowserRouter>
<Menu/>
<BrowserRouter>
Only the router childrens receive the history hook.

Categories