Reputation: 4349
I am trying to setup verify account with react and have the following in my App.js
file
App.js
import SigninPage from './pages/signin';
import ResetPasswordPage from './pages/resetPassword'
import VerifyAccountPage from './pages/verifyAccount'
...
...
import { useHistory } from 'react-router';
import { logout } from './utils/auth';
function App() {
const history = useHistory();
return (
<Router>
<Switch>
<Route path='/' component={Home} exact />
<Route
path="/signout"
render={() => {
logout();
history.push('/');
return null;
}}
/>
<Route path='/signin' component={SigninPage} exact />
<Route path='/reset-password?reset-password-token=:resetPasswordToken' component={ResetPasswordPage} />
<Route path='/verify-account?token=:token&email=:email' component={VerifyAccountPage} exact />
</Switch>
</Router>
);
}
export default App;
and in my VerifyAccountPage component have the following
import { Redirect } from 'react-router-dom';
import { useHistory } from 'react-router';
import { verifyAccount, isAuthenticated } from '../../utils/auth';
const VerifyAccount = () => {
const { token, email } = this.props.match.params
const history = useHistory();
const [error, setError] = useState('');
const handleGet = async (e) => {
e.preventDefault();
setError('');
try {
const data = await verifyAccount(token, email);
if (data) {
history.push('/');
}
console.log(data);
} catch (err) {
if (err instanceof Error) {
// handle errors thrown from frontend
setError(err.message);
} else {
// handle errors thrown from backend
setError(err);
}
}
};
return isAuthenticated() ? (
<Redirect to="/#" />
) : (
<>
<Container>
<FormWrap>
<Icon to='/'>mywebsite</Icon>
<FormContent>
<Form action='#'>
<FormH1>Verify Account</FormH1>
<Text>Account has been verified!</Text>
</Form>
</FormContent>
</FormWrap>
</Container>
</>
);
};
export default VerifyAccount;
and here is verifyAccount.js
page
import React from 'react';
import VerifyAccount from '../components/VerifyAccount';
import ScrollToTop from '../components/ScrollToTop';
function VerifyAccountPage() {
return (
<>
<ScrollToTop />
<VerifyAccount />
</>
);
}
export default VerifyAccountPage;
here is
index.js
import React from 'react';
import ReactDOM from 'react-dom';
import App from './App';
ReactDOM.render(
<React.StrictMode>
<App />
</React.StrictMode>,
document.getElementById('root')
);
but this is not working and when I go to the link https://mywebsite.com/verify-account?token=3heubek&[email protected]
nothing happens other than a 200 or 304 status code
no request is sent to the API so means that the params are not getting pulled out
can anyone point me to what is going on?
package versions used from package.json file
"dependencies": {
"@testing-library/jest-dom": "^4.2.4",
"@testing-library/react": "^9.3.2",
"@testing-library/user-event": "^7.1.2",
"react": "^16.13.1",
"react-dom": "^16.13.1",
"react-icons": "^3.11.0",
"react-router-dom": "^5.2.0",
"react-scripts": "3.4.3",
"react-scroll": "^1.8.1",
"styled-components": "^5.2.0",
"@types/node": "^15.6.0",
"jwt-decode": "^3.0.0"
Upvotes: 6
Views: 53754
Reputation: 203466
Route match params are not the same thing as URL query string parameters.
You'll want to access the query string from the location object.
{ key: 'ac3df4', // not with HashHistory! pathname: '/somewhere', search: '?some=search-string', <-- query string hash: '#howdy', state: { [userDefined]: true } }
React-router-dom query parameters demo
They create a custom useQuery
hook:
const useQuery = () => new URLSearchParams(useLocation().search);
For your use case, on the page rendering the VerifyAccountPage
you want to then extract the query string parameters. Given path='/verify-account?token=:token&email=:email'
:
const query = useQuery();
const email = query.get('email');
const token = query.get('token');
If VerifyAccountPage
is a class-based component then you will need to access props.location
and process the query string yourself in a lifecycle method. This is because React hooks are only validly used by functional components.
componentDidMount() {
const { location } = this.props;
const query = new URLSearchParams(location.search);
const email = query.get('email');
const token = query.get('token');
...
}
path='/verify-account?token=:token&email=:email'
The path params are only relevant in the path portion of a URL, you can't define params for the queryString portion of the URL. The above path is equivalent to path='/verify-account'
from react-router-dom
's perspective.
Upvotes: 14
Reputation: 4709
React JS
http://localhost:3000/#/product?id=159
import React from "react";
import { useLocation } from "react-router-dom";
const MyComponent = () => {
const myParam = useLocation().search;
const productId= new URLSearchParams(search).get("id");
console.log(productId); // 159
}
Vanilla JavaScript
const siteUrl = window.location.search;
const urlParams = new URLSearchParams(siteUrl);
console.log( urlParams['id'] ) // 159
Upvotes: 2
Reputation: 1088
You can use withRouter
for getting router information such as location, history, path, and params.
import { withRouter } from "react-router-dom";
...
const VerifyAccount = withRouter(props) => {
const { token, email } = props.match.params;
console.log("toke, email: ", token, email) // And also show me how it looks!!!
...
}
And you should define your route like this.
<Route path='/verify-account/:token/:email' component={VerifyAccountPage} />
And you should call like this:
https://your-domain/verify-account/[token]/[email]
This will work.
Upvotes: 8