I am looking for a way to dynamically update the :id paramter in my react application using react router dom. I have these codes:
import Blog from './pages/Blogpage/Blog'
import {
BrowserRouter as Router,
} from "react-router-dom";
<Route path="/allPosts/page/:id">
{<Blog/>}
</Route>
This is the link on navigation bar that takes user to the component called Blog.
<li className='topListItem'>
<Link className='link' to={`/allPosts/page/${sesssionPageNumber}`}>
BLOG
</Link>
</li>
Now, what I want to do is when a user clicks a button, the page address number changes. sessionPageNumber is a useState and I would like the URL which has :id parameter to also change as the useState number increases or decreases.
const handleNext = ()=>{
setPage(page 1)
}
<MdNavigateNext onClick={handleNext} className='custom-next-prev-icon'/>
The problem is that the URL parameter does not change as the useState is updated via the button. The URL :id parameter remains the same which is the default value.
Is there a way I can update the URL :id parameter when the handleNext
function is called on the button?
CodePudding user response:
Yes, you can use the useNavigate
hook for exactly this. You just need to instantiate the hook at the top of your component, and then you can use it to navigate the user dynamically like so:
import { useNavigate } from 'react-router-dom';
export default function Blog(props) {
const navigate = useNavigate();
// ...
const handleNext = () => {
navigate(`/allPosts/page/${sesssionPageNumber 1}`);
}
// ...
}
CodePudding user response:
You can issue an imperative navigation action from the current page value.
Based on your route declaration I'll assume you are using react-router-dom@5
, so you will use the useHistory
hook to accomplish this. Remember that all route path params are a string type, so you will need to convert id
to a number if you want to add 1 to it so you don't accidentally apply string concatenation, i.e. "1" 1 -> "11"
vs Number("1") 1 -> 2
.
Example:
import { useHistory, useParams } from 'react-router-dom';
...
const history = useHistory();
const { id } = useParams();
...
const handleNext = ()=>{
history.push(`/allPosts/page/${Number(id) 1}`);
}
...
<MdNavigateNext onClick={handleNext} className='custom-next-prev-icon'/>
If on the offhand chance you are using react-router-dom@6
then replace the useHistory
hook with the useNavigate
hook.
Example:
import { useNavigate, useParams } from 'react-router-dom';
...
const navigate = useNavigate();
const { id } = useParams();
...
const handleNext = ()=>{
navigate(`/allPosts/page/${Number(id) 1}`);
}
...
<MdNavigateNext onClick={handleNext} className='custom-next-prev-icon'/>
and fix the route
<Route path="/allPosts/page/:id" element={<Blog/>} />
Additional note
You very likely don't need to store any sesssionPageNumber
locally as this is easily derived from the current URL path, i.e. the id
route path param.