I'm sure I probably have something simple to fix, but have tried and tried and cannot find it. I have several API calls that are working just fine. But I have made a new one, which I made by copy and pasting ones that worked, and just changing values and names. But this new one, gives me a 500 error.
The API path should be:
"http://localhost:3000/billingcalculator/create"
Instead, it is:
"http://localhost:3000/undefined/billingcalculator/create" <-- where is the undefined coming from?
It gives this error:
PUT http://localhost:3000/undefined/billingcalculator/create 500 (Internal Server Error)
It references the line in the call that says throw new Error() ; but I don't see what's wrong with that. I use that exact same code all over the place and it works fine everywhere else.
Call that works perfectly:
createHCA() {
fetch(API_URL + `/hca/create`, {
method: "PUT",
body: JSON.stringify({
client: this.state.client,
short: this.state.short,
}),
headers: { "Content-Type": "application/json" },
})
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
.then(() => this.getHCAid())
.then(() => this.getAllHCAs());
this.setState({ showHide: false});
}
And this is the call that creates the error and cannot reach my API routes:
createBillProject() {
fetch(API_URL + `/billingcalculator/create`, {
method: "PUT",
body: JSON.stringify({
client: this.state.client,
source: this.state.source,
projectName: this.state.projectName
}),
headers: { "Content-Type": "application/json" },
})
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
.then(() => this.getBillProjLastId());
}
The API route I'm trying to reach is this:
app.put("/billingcalculator/create", function (req, res) {
console.log("It is getting to the billing route");
const client = req.body.client;
const source = req.body.source;
const projectName = req.body.projectName;
console.log(`client: ${client}`);
console.log(`source: ${source}`);
console.log(`project name: ${projectName}`);
connection.getConnection(function (err, connection) {
connection.query(
`INSERT INTO billcalc_projects (client, source, project_name)
VALUES (?, ?, ?)`,
[client, source, projectName],
function (error, results, fields) {
connection.release();
if (error) throw error;
res.json(results);
console.log(`Billing Project has been created`);
}
);
});
});
Thanks in advance for your help. It must be something simple that I'm just missing. But I haven't been able to figure it out.
Related
Using this tutorial I want to upload images to my database, So I have this in server side:
router.post('/upload', upload.single('upload'), async (req, res) => {
try {
const incident = await Incident.findById(req.body.id)
incident.image = req.file.buffer
incident.save()
res.send()
} catch (e) {
res.status(400).send(e)
}
}, (error, req, res, next) => {
res.status(400).send({
error: error.message
})
})
And I have the binary data of the image like this in front end:
data:image/jpeg;base64,/9j/4AAQSkZJRgABAQAAAQABAAD/4gIoSUNDX1BST0ZJTEUAAQEAAAIYAAAAAAIQAABtbnRyUkdCIFhZWiAAAAAAAAAAAAAAAABhY3NwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAA9tYAAQAAAADTLQAAAAAAAAAAAAAAA
In the tutorial it shows us that we can send a image via postman like this:
I used this to do the same thing as tutorial did in postman using fetch api with no luck:
const data = new FormData();
data.append("upload", image); // the image is the binary data I showed you
fetch('/accounts/upload', {
// headers: {
// 'Accept': 'application/json',
// 'Content-Type': 'application/json'
// },
method: 'post',
body: data,
})
.then(response => response.json())
.then(result => console.log(result))
.catch(error => console.log(error));
But I get 400 (Bad Request) each time!!
How can I fix this?
I figured out that req.body is empty object like : {} So I think there is something wrong with fetch maybe
EDIT 2: Here is a log from data inside:
function uploadImage(image) {
const data = new FormData();
data.append("upload", image);
console.log(data); // added this to log the data
fetch('/accounts/upload-image', {
method: 'post',
body: data,
})
.then(response => response.json())
.then(result => console.log(result))
.catch(error => console.log(error));
}
Result o the log is:
I have this fetch request a I am accepting it to
send me a statement !! if certain conditions are met
redirect me to anther page after certain time
problem is those 2 don't seem to work together if I send json resp the link is pointing to the default one future more I cannot pass the URL further down the response.
// Server side
exports.redirect = async (req, res, next) => {
//res.status(403)
res.json({ Error: 'Plase try again' })
res.redirect('/signup')
}
// Client side
fetch('/redirect', {
credentials: "same-origin",
mode: "same-origin",
method: 'POST',
//redirect: 'follow',
headers: {
"Authorization": `Bearer ${jwt}`,
"Content-Type": "application/json"
},
body: JSON.stringify(inputJSON)
})
.then(resp => {
console.log(resp.url)
return Promise.all([resp.json()])
}
).then(data => {
console.log(data);
let jsonData = data[0]
let div = document.querySelector(".form-group");
div.insertAdjacentHTML('afterend', `<div id="response">${jsonData.Error}</div>`)
//setTimeout(windows.location = data.url, 5000);
})
.catch((error) => {
console.error(error);
}).catch(err => {
if (err === "server") return
console.log(err)
})
}
})
For the general situation of when you want to pass something from an upper .then to a lower one, you'd be almost there, you just need to add the resp.url to the Promise.all array you already have:
.then(resp => {
return Promise.all([resp.json(), resp.url])
}
).then(([data, url]) => {
const div = document.querySelector(".form-group");
div.insertAdjacentHTML('afterend', `<div id="response">${data.Error}</div>`);
setTimeout(() => window.location = url, 5000);
})
But it doesn't make much sense to have a response that both has .json() and a redirect - pick one or the other. I'd recommend only a .json:
exports.redirect = async (req, res, next) => {
res.json({ Error: 'Plase try again', url: '/signup' });
}
.then(res => res.json())
.then(result => {
div.insertAdjacentHTML('afterend', `<div id="response">${result.Error}</div>`);
setTimeout(() => window.location = result.url, 5000);
})
Also make sure to pass a callback to setTimeout, and to use window.location, not windows.location.
Your final .catch(err => { block is superfluous too, it'll never be entered into and doesn't really make any sense anyway - feel free to completely remove it.
I have an app that does many API calls, but I release each and every connection like this?
app.put("/interview/create/questions/:lastEmployeeId", function (req, res) {
console.log("It is getting to the route");
const employee_id = req.body.lastEmployeeId;
const tableName = req.body.table;
connection.getConnection(function (err, connection) {
connection.query(
`INSERT INTO ${tableName} (employee_id)
VALUES (?)`,
[employee_id],
function (error, results, fields) {
if (error) throw error;
res.json(results);
console.log(`Interview has been created`);
}
);
connection.release();
});
});
Is this the correct way, because I'm getting a lot of inconsistent 502 and 503 errors. It feels to me like maybe it's running out of resources. The paths are correct, because sometimes they work, and sometimes they don't. It's random, so I can't figure out what to do.
Doesn't the connection.release() free up the resources? I currently have the max connections set to 50, which should be more than I need because only one person at a time will be using this, and there is a method where it makes 8 calls. I wouldn't mind some help refactoring this, but I still need this many calls I believe because I need it to create rows in 8 different tables. This long method below here is just taking a value entered in one table, and entering it as a reference in the 8 other tables.
createQuestions() {
fetch(
API_URL + `/interview/create/questions/${this.state.lastEmployeeId}`,
{
method: "PUT",
body: JSON.stringify({
lastEmployeeId: this.state.lastEmployeeId,
table: "audit_general",
}),
headers: { "Content-Type": "application/json" },
}
)
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
.then(
fetch(
API_URL + `/interview/create/questions/${this.state.lastEmployeeId}`,
{
method: "PUT",
body: JSON.stringify({
lastEmployeeId: this.state.lastEmployeeId,
table: "audit_culture",
}),
headers: { "Content-Type": "application/json" },
}
)
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
)
.then(
fetch(
API_URL + `/interview/create/questions/${this.state.lastEmployeeId}`,
{
method: "PUT",
body: JSON.stringify({
lastEmployeeId: this.state.lastEmployeeId,
table: "audit_performance",
}),
headers: { "Content-Type": "application/json" },
}
)
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
)
.then(
fetch(
API_URL + `/interview/create/questions/${this.state.lastEmployeeId}`,
{
method: "PUT",
body: JSON.stringify({
lastEmployeeId: this.state.lastEmployeeId,
table: "audit_policies",
}),
headers: { "Content-Type": "application/json" },
}
)
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
)
.then(
fetch(
API_URL + `/interview/create/questions/${this.state.lastEmployeeId}`,
{
method: "PUT",
body: JSON.stringify({
lastEmployeeId: this.state.lastEmployeeId,
table: "audit_risk",
}),
headers: { "Content-Type": "application/json" },
}
)
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
)
.then(
fetch(
API_URL + `/interview/create/questions/${this.state.lastEmployeeId}`,
{
method: "PUT",
body: JSON.stringify({
lastEmployeeId: this.state.lastEmployeeId,
table: "audit_strategy",
}),
headers: { "Content-Type": "application/json" },
}
)
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
)
.then(
fetch(
API_URL + `/interview/create/questions/${this.state.lastEmployeeId}`,
{
method: "PUT",
body: JSON.stringify({
lastEmployeeId: this.state.lastEmployeeId,
table: "audit_rewards",
}),
headers: { "Content-Type": "application/json" },
}
)
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
)
.then(
fetch(
API_URL + `/interview/create/questions/${this.state.lastEmployeeId}`,
{
method: "PUT",
body: JSON.stringify({
lastEmployeeId: this.state.lastEmployeeId,
table: "audit_workforce",
}),
headers: { "Content-Type": "application/json" },
}
)
.then((res) => {
if (!res.ok) {
throw new Error();
}
return res.json();
})
.then((data) => console.log(data))
.catch((err) => console.log(err))
);
}
You're releasing the connection before the query completes. This needs to be addressed:
app.put("/interview/create/questions/:lastEmployeeId", function (req, res) {
console.log("It is getting to the route");
const employee_id = req.body.lastEmployeeId;
const tableName = req.body.table;
connection.getConnection(function (err, connection) {
if (err) {
res.statusCode = 500;
res.send('DB connection could not be acquired.');
return;
}
connection.query(
`INSERT INTO ${tableName} (employee_id)
VALUES (?)`,
[ employee_id ],
function (error, results, fields) {
// throw here does nothing useful, it's inside a callback and
// the calling function may have terminated ages ago. You need
// to handle this error here and now.
if (error) {
res.statusCode = 500;
res.send('Nope!');
return;
}
res.json(results);
console.log(`Interview has been created`);
// Now you can release the handle
connection.release();
}
);
// Code here runs before the query can complete.
});
});
Think of your asynchronous program flow like this:
connection.getConnection(..., cbGC) executes and returns
** Long time passes
cbGC executes -> connection.query(..., cbQ) executes and returns
** Tiny eternity elapses
cbQ executes!
The time interval between calling a function that takes a callback and that callback actually executing can be significant, seconds or more, which means the calling function is not only dead, it is ancient history, probably garbage collected.
You need to organize your code around this principle of nesting anything that depends on that sequencing.
I'm trying to doing a basic GET request from ReactJS app to a Node.js API, but I'm getting a response with status 304. I need get a 200 status to save the response of GET in a variable. (Im running Reactjs app in port 3000 and Nodejs API in port 3300)
Node API:
app.get('/serviciosextras', async (req, res) => {
let connection;
console.log(('Servicios Extras'));
try {
connection = await oracledb.getConnection({
user: 'portafolio',
password: '123',
connectString: "localhost:1521/orcl"
});
const result = await connection.execute(
`SELECT dep.id_departamento,
se.id_servicio,
se.precio_servicio
FROM departamento_servicio_detalle dsd
JOIN departamento DEP ON (dsd.id_departamento = dep.id_departamento)
JOIN servicio_extra SE ON (dsd.id_servicio = se.id_servicio)
ORDER BY 1 ASC`
)
const resultSet = result.rows;
let lista = [];
resultSet.map(obj => {
let serviciosSchema = {
'id_departamento': obj[0],
'id_servicio': obj[1],
'precio_servicio': obj[2]
}
lista.push(serviciosSchema);
});
console.log(lista);
res.json(lista);
connection.close();
} catch (err) {
console.error(err);
}
});
GET request from Reactjs
const getExtraServices = () => {
let endpoint = `${URL}serviciosextras`;
const requestOptions = {
method: "GET",
mode: 'no-cors'
// headers: {
// "Content-Type": "application/json",
// Accept: "application/json"
// },
};
console.log(endpoint);
fetch(endpoint, requestOptions)
.then((res, err) => {
console.log(res);
})
.then(result => {
console.log('fue aqui');
console.log(result);
})
.catch(err => {
console.log('ERROR');
console.log(err);
})
}
Im calling the method from this button:(onClick={getExtraServices()})
<Fab onClick={(e) => {
e.preventDefault();
getExtraServices();
}} variant="extended">
<NavigationIcon style={{marginRight: 'theme.spacing(1)'}} />
Navigate
</Fab>
so... I'm getting this:
Firefox Console when I clicked button to call getExtraServices() res is undefined
Network console of GET request I got a response but the status is 304, so I can't get this from code. :/
Console of Nodejs API this console.log if from console.log(lista) before send the res.json(lista)
Does someone know how can I fix this? I need get the response of the GET request to charge a list in ReactJS app, but I can't because the response has body:null.
Error 304 isn't the problem.
It looks like you are missing a statement to turn your response into JSON.
Here's an example from MDN:
fetch('https://example.com/profile', {
method: 'POST', // or 'PUT'
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify(data),
})
.then(response => response.json())
.then(data => {
console.log('Success:', data);
})
.catch((error) => {
console.error('Error:', error);
});
In particular:
.then(response => response.json())
In your code:
fetch(endpoint, requestOptions)
.then((res, err) => {
console.log(res); // logging res
// no data being returned here
})
.then(result => {
console.log('fue aqui');
console.log(result); // therefore result is undefined
})
.catch(err => {
console.log('ERROR');
console.log(err);
})
I face a new problem that has been asked before in this link. But It is not relevant to my problem.
What I have implemented is a very simple API using nodejs, express-framework and mongoose.
The problem is with fetch API. I want to submit some ID and post it to the server. In the server side I redirect it to the proper URL base on the ID that user entered. Whenever I test this part, this error is being raised in front-end side and points to return response.json() line.
SyntaxError: Unexpected end of input
Here is my code:
Front-End:
function submitCode(){
var nationalCode = document.getElementById('nationalCode').value
var data = {
nationalCode: nationalCode,
creationDate: new Date().toLocaleDateString()
}
fetch('/submit', {
method: 'POST',
redirect:'manual',
headers: {
'Content-Type': 'application/json',
'Accept': 'application/json'
},
body: JSON.stringify(data)
},
).then(response => {
return response.json()
}).then(jsonData => {
console.log('success:', jsonData)
history.pushState(null, null, "/lashkhor")
}).catch(e => {
console.log('error:', e)
return e
})
}
Back-End:
app.post('/submit', (req, res) => {
var nationalCode = req.body.nationalCode
var creationDate = req.body.creationDate
query = {'nationalCode': nationalCode}
nationalCodeModel.find(query, (err, success) => {
if (err) {
console.log('error:', err)
}
else if (success.length == 0){
nationalCodeModel.create({
nationalCode: nationalCode,
creationDate: creationDate
})
console.log('salam khoshgele daei!')
res.redirect('/khoshgeledaei')
}
else if (success.length > 0) {
console.log('lashkhor detected')
res.redirect('/lashkhor')
}
})
})
app.get('/lashkhor', (req, res) => {
console.log('here')
res.send('salam')
})
I can't find any hint to solve it. I would be thankful if anyone could help me.
PS: Whole code is available in this repository
Thanks!
You are trying to parse text into json.
You can use res.json() instead of res.send() from your backend.