I have a popup component overlaying the main content that I want to render through routing, but because I want it to build on existing routes without messing up my main page configuration, I have tried going for a nested route. However, I seem to have misunderstood how it is supposed to be done. I wrapped the export with "withRouter" and tried to do this:
<Fragment>
<Helmet>
<title>Videos - Saddex Productions</title>
</Helmet>
<Switch>
<Route path="/popup"
render={() => <Popup items={props.videos}/>}
/>
</Switch>
...
This doesn't work and only renders the main component. And I also don't want to outsource the code that's going to be rendered underneath, because it seems unneccessary. However, what should I do? Thanks in advance.
Solved: The reason it didn't work is because I presumed the router works like the Express router does - with relative paths. I included the base path like "videos/popup" and now it works, it seems.
Related
I am having a Server Side Rendered React app where I use HashRouter for react routing(v5). My Routes look like this
<HashRouter basename="/">
<Layout {...config} />
</HashRouter>
<Switch>
<Route exact={true} path="/" component={LPComp} />
<Route exact={true} path={this.props.siteBanner.Red} component={bannerPage} />
</Switch>
When I hit localhost:8888/parent/ and once it get loaded and if I hit localhost:8888/parent/banner in the same window the bannerPage component renders fine.
But I hit localhost:8888/parent/banner directly(consider in a new tab), then the component is not rendered properly.
Any ideas why this is happening?
Also to add on when I hit localhost:8888/parent/banner I can see LPComp(default route) also being loaded and then it disappears suddenly and the bannerPage component renders improperly.
Thanks in Advance
The behavior is making sense, since your routes is based on a prop/state this.props.siteBanner.Red. So the first thing is to put a console.log once you enter this component.
console.log(this.props.siteBanner.Red)
In your first case, you reach this component from its parent, this way the props mostly likely is resolved.
In your second case, you reach it directly, of course also from its parent, but most likely there's no time for the props to get resolved quickly. Couple of possibilities
useEffect is to update this variable
mouse click is required to get a value
setTimeout is used to defer
callback is used to get this variable
You can say there's 50ms delay in getting this prop resolved, but you need to dig out why yourself. Dynamic route is more advanced thing, it's easy to have permanent route.
Thank you all for your timely response, I was able to solve that issue by setting location=(req.url) from the server side configured static router. Going through this example I got the bigger picture I was missing.
https://medium.com/javascript-in-plain-english/server-side-rendering-in-react-redux-ab0af31c9c4b
While using react-router for a multi-page react app, I've found that the different components that are to be rendered based on the path display the stylesheets in those components, even when the corresponding component isn't displayed.
I was playing around with adding a Sponsors page to my website, and the CSS was behaving strangely. Digging deeper into the problem with chrome devtools, I found that the css from my homepage was on the page while it was not being displayed, causing unexpected styles.
I've tried researching if this is the expected behaviour without any luck. I removed the homepage from my routing code and the styles behaved as expected in the other component, proving that that import was the problem.
My routing code:
<Switch>
<Route
exact path="/"
render={props => <MainPage language = {this.state.language}/>}
/>
<Route
path="/Sponsors/"
render={props => <Sponsors language = {this.state.language}/>}
/>
</Switch>
Of course with
import Sponsors from './Pages/Sponsors/Sponsors.js'
import MainPage from './Pages/MainPage/MainPage.js';
at the top of that file.
and at the top of MainPage.js:
import './MainPage.css';
An import that looks like that, and the same type in Sponsors.css.
Any code in that MainPage.css will affect the elements in the Sponsors component, even when the url is at /Sponsors (i.e. the MainPage component shouldn't be rendering).
I'm looking to ensure I understand the behaviour of react-router, that the MainPage.css should not appear when MainPage is not being rendered. As an alternative I could write specific enough css that this never happens, but It was my understanding that the modular nature of react featured that not being a necessity, as in I can write it only specific enough for the code being rendered. Am I mistaken?
I understood you are trying to limit the scope of CSS to a module, generally it is having a global scope. you can use "CSS Modules", to overcome this behaviour.
please find the article from facebook.
https://facebook.github.io/create-react-app/docs/adding-a-css-modules-stylesheet
hope it will help to fix the issue.
I have been all around internet about the dynamic routing of React. But I couldn't find anything which explains how it works and how it is different than static routing in every single sense.
I understood it pretty well how the things go when we want to render something in the same page using React-Route.
My question is how does it work when a whole new page is wanted to be rendered? Because in this case all the DOM inside that page has to be re-rendered. Thus would it be static routing? or still dynamic in some ways?
I hope I've been clear.
Thanks for the answers in advance, I appreciate!
I don't think the above explanation is correct for Static vs Dynamic routing.Also there is not much explanation in the web for it, but there is a very nice explanation in React Router Docs.From the Docs
If you’ve used Rails, Express, Ember, Angular etc. you’ve used static
routing. In these frameworks, you declare your routes as part of your
app’s initialization before any rendering takes place. React Router
pre-v4 was also static (mostly). Let’s take a look at how to configure
routes in express:
In Static routing, the routes are declared and it imported in the Top level before rendering.
Whereas in Dynamic routing
When we say dynamic routing, we mean routing that takes place as your
app is rendering, not in a configuration or convention outside of a
running app.
So in Dynamic routing, the routing takes place as the App is rendering.
The examples explained in the above answer are both for static routing.
For Dynamic routing it is more like
const App = () => (
<BrowserRouter>
{/* here's a div */}
<div>
{/* here's a Route */}
<Route path="/tacos" component={Tacos}/>
</div>
</BrowserRouter>
)
// when the url matches `/tacos` this component renders
const Tacos = ({ match }) => (
// here's a nested div
<div>
{/* here's a nested Route,
match.url helps us make a relative path */}
<Route
path={match.url + '/carnitas'}
component={Carnitas}
/>
</div>
)
First in App component only one route is declared /tacos.When the user navigates to /tacos the Tacos component is mounted and there the next route is defined /carnitas.So when the user navigates to /tacos/carnitas, the Carnitas component is mounted and so on.
So here the routes are initialized dynamically.
Use react-router and react-router-dom, and write something like this:
onSubmit((e) => {
e.preventDefault();
this.props.history.push('<url>')
}
so at any place you may run this line and go to another locations conditionaly
<Route path="/:user" component={Home}>
<Route path="/:thing(/:version)" component={Thing}/>
</Route>
So, I've got two dynamic objects in my application that I'd like to be controlled by route params in react-router. Using the code above, both /0 and /0/3 take me to Home. I need /0/3 to take me to Thing. I'm not sure what I'm doing wrong here... Does react-router even support multiple dynamic params next to each other like this? I couldn't find anything in the docs.
What happens here is that you've given React Router two paths that can both match on /anything. By default then React Router matches the first one it can find.
To dig deeper, if I go to /pudding, React Router can't know if you meant /:user or /:thing. Since /:user occurs first, that option will be chosen.
You also need to make sure if nesting routes is what you want. Currently, your Thing route is nested below Home, which means that it is rendered via this.props.children in your Home component. So, for your current Thing route, Home will always be rendered too, with Thing as a child. If your Home component doesn't render this.props.children, Thing will not be shown.
I suspect you just want two different pages. What you could do to achieve that is the following:
<Router history={history}>
<Route path="/user/:user" component={Home} />
<Route path="/:thing(/:version)" component={Thing}/>
</Router>
This will make every /user/name go to the Home component, and every other /random (with an optional extra level) will go to Thing. If you wonder why in this case React Router doesn't take /user/name to the Thing route, it's because it still matches in the order your routes are specified. Because your Home route matches the requested URL, no siblings of this route are tested anymore.
I'm trying to follow the react-router tutorial here trying to navigate using a child route and it doesn't work.
For example given this route definition:
export default <Route path="wifi" component={ Wifi }>
<IndexRoute component={WifiView}/>
<Route path="list" component= {WifiListView}/>
<Route path="connect" component={WifiConnectView}/>
</Route>;
If we are on "/" and navigate to "/wifi" we are good. The WifiView is presented however if if from "/wifi" we call hasHistory.push('list') it doesn't find the route. I would assume that the route is relative to its current location since I'm not using the "/" but that isn't being respected.
Also the document said:
You can also use the router that Router provides on "context". First,
you ask for context in the component, and then you can use it...
But I don't see anything that mentions how to do that in TypeScript so I'm using the static hashHistory.
It looks like novice questions but I had nowhere to ask since the suggested Discord channels are all dead... Can anyone help with those?
Thanks! Appreciate any help!
Ok finally found the replies to my questions...
As for today, react-router don't support relative navigation which means, it hast to navigate to the whole chain of routes and that is why hasHistory.push('list') doesn't work.
In order to get the context.router we need to use withRouter high order component but that isn't exposed on the TypeScript definition files they provide.