access react route params in server side - javascript

i came up with this problem with ReactJS and ExpressJS: So basically user uploads some info on /info route with React & axios. then user gets route params from server side to redirect to:
axios.post('/info', SomeData)
.then(res => res.data)
.then(data =>{
window.location.replace(`/info/${data.id}`)
})
this is piece of cake but when user redirects to that page problem occurs, i need to get data from that page. i can get route params and perform request on client side like this:
componentDidMount(){
const { match: { params } } = this.props;
axios.get(`/api/info/${params.id}`)
}
but how can i get request on server side? how can express access that "id" to search it in database and query data with it to send back to client? like:
app.get('/api/info/:id', async (req,res)=>{
await db.find({id: req.params.id}, (data) =>{
res.status(200).send({data})
})
})
Any help? Thanks!

From the component itself same as the GET use your param and call your service same thing to POST
postUserInfo = () => {
const userInfo ={};
axios.post(`/api/info/${params.id}`,userInfo).then(()=>{
console.log("user info posted");
})
}
Example:
<Form onSubmit={this.postUserInfo}> </form>

Related

How to send data (a url string) in express to backend from frontend?

I am trying to build a wikipedia web scraper api and this is my code:
const app = express()
const port = 3000
const url = "https://en.wikipedia.org/wiki/Yeti_Airlines_Flight_691"
axios.get(url).then(async (res) => {
try {
if (res.status == 200) {
const result = // Doing cheerio stuff here
app.get('/', (req, res) => {
res.status(200).send(result)
})
app.listen(port, () => {
console.log(`Example app listening on port ${port}`)
})
}
} finally {
//
}
});
How can I send url dynamically to backend using express and do some stuff then send result back to frontend?
Client side:
This is a function you define in your frontend. You set a request link, which must be known here on client side and server side. Thus take something like /request. Then use axios to send a request to the server. You can pass any parameters with „dynamic“ Information as you called it. The server will receive these informations and can handle them.
const getData = () => {
// insert your server url here instead, with the /request at the end
const requestLink = `http://localhost:3001/request`;
axios
.get(requestLink, {
params: { url: "wikipedia.de/test123" },
})
.catch((error) => {
// here you can implement error handling
console.log(error);
})
.then((res) => {
// print result, received from the server
console.log(res);
});
};
Server side:
The backend is going to wait for a request to the defined link /request.
If he receives such a request, he is executing the code. The req variable contains your dynamic data, such as the wiki url.
Use res.json to send data back to your frontend.
app.get(`/request`, (req, res) => {
// do something with the request here
console.log(req.query);
// send result to the frontend
res.json({
status: "This could be an answer to the frontend.",
});
});

Get Request returning 404

I'm using the open weather API to make a get request based on a zipcode passed in as a query parameter. When I run the endpoint in Postman I receive a successful response and can see the data. When I run the request from my app (even with a hard coded value for testing) I get a 404 not found.
Endpoint from my server file:
const weatherCtlr = require('./controllers/weatherController);
app.get('/api/weather', weatherCtlr.getWeather);
My Controller
const axios = require('axios');
const {APIKEY} = process.env;
module.exports ={
getWeather :(req, res)=>{
const {zipcode} = req.body;
axios.get(`https://api.openweathermap.org/data/2.5/weather?zip=${zipcode}&APPID=${APIKEY}`)
.then(()=>{
res.sendStatus(200);
})
.catch(err=>console.log(err))
}
}
Client Side, (axios is imported)
getWeather =()=>{
const {zipcode} = this.state.canyon;
axios.get('/api/weather', {zipcode})
.then(res=> this.setState({weather: res.data)})
.catch(err=>console.log(err))
}
I call the method on an on click
onClick={()=>this.getWeather()}
I'm not really sure what the issue is. I know the api key is good because I when I test my actual endpoint localhost.../api/weather and send a zipcode in the body it works.
What stands out is that you send a body to your server using get:
getWeather =()=>{
const {zipcode} = this.state.canyon;
axios.get('/api/weather', {zipcode})
.then(res=> this.setState({weather: res.data)})
.catch(err=>console.log(err))
}
The GET method does not accept a body. Then on the server side you parse it out like this:
const {zipcode} = req.body;
I would be very surprised if you actually get that zipcode. Most likely that will be undefined.
So I would try changing your client side request to:
axios.post('/api/weather', {zipcode})
Once you get the response back from the API, you can send it back to your app like so:
axios.get(`https://api.openweathermap.org/data/2.5/weather?zip=${zipcode}&APPID=${APIKEY}`)
.then((response) => {
res.json(response.data);
})
.catch(err => {
console.log(err);
res.json({msg: 'Error'})
})

Redirect and send data from Node server back to React

I have a NodeJS server in which I'm using Express and a front-end with React. I want to know how to send data from the server to the front-end. All the solutions I've seen use a call from the front-end, then the server answers, and finally the front-end gets the data. My problem is that I don't have a call from the front-end, but a call back-end (router.get('/callback')) to back-end (router.get('/receipt/:id')). Here is the code for a better understanding.
router.get('/callback', (req,res) => {
const ref = req.query.reference;
verifyPayment(ref, (error,body)=>{
if(error){
//handle errors appropriately
console.log(error)
return res.redirect('/payment/error');
}
response = JSON.parse(body);
const data = _.at(response.data, ['reference', 'amount','customer.email', 'metadata.full_name']);
[reference, amount, email, full_name] = data;
newDonor = {reference, amount, email, full_name};
const donor = new Donor(newDonor);
donor.save().then((donor)=>{
console.log("--------------- donor" + donor);
if(!donor){
return res.redirect('/payment/error');
}
res.redirect('/payment/receipt/' + donor._id);
}).catch((e)=>{
res.redirect('/payment/error');
});
});
});
router.get('/receipt/:id', (req, res)=>{
const id = req.params.id;
Donor.findById(id).then((donor)=>{
if(!donor){
res.redirect('/payment/error')
}
// I'VE TRIED THIS
//res.redirect('http://localhost:3000/#' + donor.full_name);
/*
AND THIS
console.log(donor.full_name);
const resp = axios.post('http://localhost:3000', {params: {donor.full_name}});
console.log(resp.data);
*/
}).catch((e)=>{
res.redirect('/payment/error')
});
});
Now what I want is to come back to the front-end (a index.js using React) and get the data and show it. Any idea?????
You need to understand how the data pass between the Node server and your React App.
We use JSON objects to pass the data server to the client (look for REST APIs for more info)
Try this in your server
router.get('/receipt/:id', (req, res)=>{
const id = req.params.id;
Donor.findById(id).then((donor)=>{
if(!donor){
res.redirect('/payment/error')
}
//How to send the data
res.status(200).json({
message: "Data returned Successfully",
Fullname:"donor.full_name"
});
}).catch((e)=>{
res.redirect('/payment/error')
});

How to check user authentication in GET method?

My frontend is Reactjs and backend Nodejs and expressjs with Postgresql database.
I have a simple signin page which checks user authentication from database.
In my Reactjs app, after signing in, user uploads files and then there is a GET method on my nodejs which send files (res.sendFile) when user wants to get the file from server. It is just a simple
<img alt='none' src=`http://example.com/source/${filename}` />
in my Reactjs app which does request for file.
Problem: if I am not logged in to my app, I can paste the URL in my browser and the file is displayed which is NOT what I want.
I want the GET method on nodejs should check for authentication of user either if the user is signed in or not, and then only fulfill the request of sending file.
How can I do it?
Should I use some kind of POST method in my Reactjs app before it makes any GET request to the same location of GET method then parse the information then handle it to app.get etc...
This is my nodejs + expressjs.
server.js
app.post('/signin', (req, res) => { signin.handleSignin(req, res, db, bcrypt)})
app.get('/source/:fileid', (req, res) => {
const { fileid } = req.params;
res.sendFile(__dirname + /data/ + fileid);
});
./controllers/signin.js
const handleSignin = (req, res, db, bcrypt) => {
const { email, password } = req.body;
if (!email || !password ) {
return res.status(400).json('Incorrect form submission');
}
db.select('email', 'hash').from('login')
.where('email', '=', email)
.then(data => {
const isValid = bcrypt.compareSync(password, data[0].hash);
if (isValid) {
return db.select('*').from('users')
.where('email', '=', email)
.then(user => {
res.json(user[0])
})
.catch(err => res.status(400).json('unable to get user'))
} else {
res.status(400).json('wrong credentials' )
}
})
.catch(err => res.status(400).json('wrong credentials'))
}
module.exports = {
handleSignin: handleSignin
}
You have to implement authentication mechanism via cookie or session. After successful login you will set a cookie in the browser and on each HTTP req you will have access to cookie data.
Create a middleware function which will check for valid cookie data in req object for each API requests.
If a user is not logged in and trying to access the URL you won't receive data in the cookie and you can unauthorized (401) the access to that particular resource.
// On valid credentials, you can set the cookie like this
res.cookie(cookieName, cookieData, cookieOptions);
and middleware function can go like this
function checkSession(req, res, next) {
if(!req.cookies || !Object.keys(req.cookies).length){
res.sendStatus(401)
}
else next();
}
You can find more details on how to use cookie-parser here.

How to reroute a payload from a 3rd party POST to a client via GET

In my Express app I am receiving a payload from an external POST request:
router.post('/liveReleaseStore', (req,res) => {
let thing = req.body.myPayload
...
I also handle a GET request from my client:
router.get('/liveReleaseStore', (req, res) => {
let myResponse = ...
res.send(myResponse);
});
I need to reroute the payload so that when my client sends a GET to the server I am able to send back the data or tell the client that I haven't received any data yet.
What is the best way to about about this?
Thanks
You could initialize the data outside the two functions to null. And then send the data if it's been initialized by the post function.
let thing = null;
router.post('/liveReleaseStore', (req,res) => {
let thing = req.body.myPayload
...
}
router.get('/liveReleaseStore', (req,res) => {
if (thing === null)
return res.send('no data yet');
res.send(thing);
}

Categories

Resources