How to fix/troubleshoot React Express 404 Error with static site? - node.js

I have an input that calls this submit function onSubmit:
const onSubmit = (e: React.FormEvent<HTMLFormElement>) => {
e.preventDefault();
setfruit(item);
console.log("sent")
fetch('/api/tasks/add', {
method: 'post',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ Name: item.Name,Quantity: item.Quantity, edit: item.edit }),
}).then(() => {
setItem(itemd)
getTasks();
});
};
and my route:
router.post('/add', (req, res) => {
const { Name, Price, edit } = req.body;
const newTask = new Task({ Name, Price, edit });
newTask.save()
.then(task => res.json(task))
.catch(err => res.json(500, err));
});
Heres my index.js:
const express = require('express');
const path = require('path');
const bodyParser = require('body-parser');
const app = express();
const routeTasks = require('./src/routes/tasks');
app.use(express.static(path.join(__dirname, './client/build')));
app.use(bodyParser.json());
app.use('/api/tasks', routeTasks, (req, res) => res.sendStatus(401));
app.get('*', (req, res) => {
res.sendFile(path.join(__dirname + './client/build/index.html'));
});
const port = 5000;
app.listen(port);
console.log(`listening on ${port}`);
Every time I call the onSubmit function, I get a 404 error. I can't tell why.
I used this repo as a guide for creating my express server but for some reason when I switch the underlying React app it stops working.
https://github.com/jmsv/simple-mern

Per Phil's comment, my issue was that the example Repo I was going off of used a React proxy which I hadn't configured in my own app. Once I added that to the package.json file, it worked.

Related

Node Express how to edit the app.post url

I have a simple example of Google App Script sending a post request to my Node application. This is working perfectly.
GAS
function send_webhook_test() {
const url = 'http://my.ip.address/folder'
var body = {msg:'hello from gas'}
var params = {
'method': 'post',
'muteHttpExceptions': true,
'contentType': 'application/json',
'payload':JSON.stringify(body)
};
var res = UrlFetchApp.fetch(url, params);
console.log(res)
}
Node
const express = require("express")
const bodyParser = require("body-parser")
const app = express()
const PORT = 3000
const path = require('path');
app.use(bodyParser.json())
app.get('/',function(req,res){
res.sendFile(path.join(__dirname+'/index.html'));
});
app.post('/', (req, res) => {
console.log(req)
console.log(req.body)
res.status(200).end()
})
app.listen(PORT, () => console.log(`Server running on port ${PORT}`))
I would like to change the app.post from ('/') to ('someValue'). So I make the following edit:
GAS
const url = 'http://my.ip.address/folder/someValue'
Node
app.post('/someValue', (req, res) => {
console.log(req)
console.log(req.body)
res.status(200).end()
})
But this returns the error Cannot POST //someValue. How do I correctly change the post url?
Your request is adding a '/'char before the /someValue route.
You can use a middleware to sanitize the path before searching for the routes, or you can review your GAS code to remove the duplicated '/'

Accessing data from a REST API works with cURL but not fetch in node

I am trying to get data from a udemy API. I can get it with cURL in the console but not with fetch. Please can anyone look at my code and let me know what I am doing wrong?
const fetch = require("node-fetch");
const express = require("express");
const app = express();
const port = process.env.PORT || 3000;
const path = require("path");
app.use(express.static("public"));
app.use(express.static(path.resolve(__dirname, "public")));
app.get("/", (req, res) => {
res.sendFile("index.html", { root: __dirname });
});
app.get("/contact", (req, res) => {
res.sendFile("contact.html", { root: __dirname });
});
const client_id = "client_id";
const client_secret = "client_secret";
const client = Buffer.from(`${client_id}:${client_secret}`).toString("base64");
fetch("https://www.udemy.com/api-2.0/courses/", {
headers: {
Authorization: `Basic ${client}`,
},
})
.then((res) => res.json())
.then((json) => console.log(json))
.catch((err) => {
console.log(err);
});

When I run the server, it gives me a message "Cannot GET /". What am I doing wrong?

I am trying to do a GET request in order to retrieve some images from my Cloudinary account. But when I run the server, I get a 400 status code on my UI with reading
Cannot GET /
How can I solve this issue?
const express = require('express');
const dotenv = require('dotenv');
const cors = require('cors');
const { json } = require('body-parser');
const axios = require('axios');
const app = express();
app.use(cors());
app.use(json());
const { parsed: config } = dotenv.config();
const BASE_URL = `https://api.cloudinary.com/v1_1/${config.CLOUD_NAME}/resources/image`;
const auth = {
username: config.API_KEY,
password: config.API_SECRET,
};
app.get('/photos', async(req, res) => {
const response = await axios.get(BASE_URL + '/resources/image', {
auth,
params: {
next_cursor: req.query.next_cursor,
},
});
return res.send(response.data);
});
app.get('/search', async (req, res) => {
const response = await axios.get(BASE_URL + '/resources/search', {
auth,
params: {
expression: req.query.expression,
},
});
return res.send(response.data);
});
const PORT = 7000;
app.listen(PORT, console.log(`Server running on port ${PORT}`));
If you open your server URL in browser you will get Cannot GET / because you don't have base route.
It's not needed in most cases, since you don't access your node server from browser, it just run's in the background.
You generally display your frontend (Angular, React) in browser.
But if you don't like the message you can add a base route.
app.get('/', (req, res) => res.send('Hello World'));
I'm not sure what are you trying to achieve, but at least you won't get this error.

express server returns 405 on routes in production

Im building an express instance for the first time and ive run into an issue where everything works locally, but when deployed sending a post request to the route responds:
Failed to load resource: the server responded with a status of 405
(Not Allowed)
Ive included the relevant code below:
server/index.js
const express = require('express');
const bodyParser = require('body-parser')
const path = require('path');
const app = express();
app.use(express.static(path.join(__dirname, 'build')));
const routes = require('./routes')(express)
require('./db')
// parse application/x-www-form-urlencoded
app.use(bodyParser.urlencoded({ extended: false }))
// parse application/json
app.use(bodyParser.json())
app.get('/', function (req, res) {
res.sendFile(path.join(__dirname, 'build', 'index.html'));
});
app.listen(process.env.PORT || 8080);
app.use('/', routes);
routes/index.js
var mongoose = require("mongoose");
const randomId = require('random-id');
const Submissions = require('../api/Submissions')
// routes/index.js
module.exports = (express) => {
// Create express Router
var router = express.Router();
// add routes
router.route('/submission')
.post((req, res) => {
let newSubmission = new Submissions(req.body);
newSubmission._id = randomId(17, 'aA0');
// Save the new model instance, passing a callback
newSubmission.save(function(err,response) {
if (err) {
console.log(err)
} else {
res.setHeader('Content-Type', 'application/json');
res.json({'success':true})
}
// saved!
})
});
return router;
}
client.js
let submission = {
name: this.state.newSubmission.name.trim(),
body: this.state.newSubmission.body.trim(),
email: this.state.newSubmission.email.trim(),
};
const requestOptions = {
method: "POST",
headers: { "Content-Type": "application/json" },
body: JSON.stringify(submission),
};
fetch("/submission", requestOptions)
.then((response) =>
response.json().then((data) => ({
data: data,
status: response.status,
}))
)
.then((res) => {
if (!res.data.success) {
notifier.warning('Failed to submit');
} else {
notifier.success('Submission successful');
}
});

express.js form post req.body is empty body {}

I have the following reactjs code and using expressjs to handle the post request. req.body always returns {} from the app. But it works in Postman.
my reactjs code snippet:
handleSubmit(e) {
e.preventDefault();
fetch(config.urlDev + '/notes', {
method: 'post',
body: { "email":"test" },
//headers: {'Content-Type':'x-www-form-urlencoded'}
headers: {'Content-Type':'application/json'}
})
.then((res) => res.json())
.then((res) => {
console.log(res)
})
.catch((err) => {
console.log(err)
})
}
my expressjs code snippet:
module.exports = function (app, db) {
app.post('/notes', (req, res) => {
console.log(req.body)
console.log(req.params)
res.send(req.body)
})
}
server.js:
const express = require('express');
const MongoClient = require('mongodb').MongoClient
const bodyParser = require('body-parser')
const db = require('./config/db');
const app = express();
const port = 8000;
const cors = require('cors');
const path = require('path');
app.use(cors())
//app.use(bodyParser.json())
app.use(bodyParser.urlencoded({extended:true}))
MongoClient.connect(db.url, {useUnifiedTopology: true}, (err, database) => {
if (err) return console.log(err)
const mydb = database.db('notes')
require('./app/routes') (app, mydb);
app.listen(port, () => {
console.log ("server on " + port)
})
})
postman
Try un-commenting the line
//app.use(bodyParser.json()) and it should work.
or alternatively if you are sending headers in the fetch request as headers: {'Content-Type':'x-www-form-urlencoded'} instead of headers: {'Content-Type':'application/json'} it should work.

Resources