System Information
4.0 :
Mac OS :
Database :
Node Version :
NPM Version :
Yarn Version :
const { createCoreController } = require("@strapi/strapi").factories;
module.exports = createCoreController(
"api::application.application",
({ strapi }) => ({
async getFormDetailsBasedOnApplicationAction(ctx) {
try {
/**
* Queries the RCMP collection type
* using the Entity Service APIs
* to retrieve information about the documents
*/
const user = ctx.state.user;
if (!user) {
return ctx.badRequest(null, [
{ messages: [{ id: "No authorization header was found" }] },
]);
}
const entries = await strapi.entityService.findMany(
"api::application.application",
ctx.query
);
const finalEntries = [];
Promise.all(
entries.map(async (entry) => {
let formData = {};
if (entry && entry.formType === "RCMP") {
formData = await strapi.entityService.findOne(
"api::rcmp-form.rcmp-form",
entry.orderId,
{
populate: { document: true },
}
);
finalEntries.push({ ...entry, formData });
} else if (entry && entry.formType === "FBI_APOSTILLE") {
formData = await strapi.entityService.findOne(
"api::fbi-apostille-form.fbi-apostille-form",
entry.orderId,
{
populate: { document: true },
}
);
finalEntries.push({ ...entry, formData });
}
})
)
.then((results) => {
ctx.body = {
data: finalEntries,
};
return ctx;
})
.catch((e) => {
ctx.body = e;
return ctx;
// Handle errors here
});
} catch (err) {
ctx.body = err;
return ctx;
}
},
})
);
Am i returning the data correctly? Or do I have to sanitize the output?
Hey @vinikatyal ,
It seems okay with the return method. You can also use ctx.send({})
instead of return/ctx.body .
Can you show me the console error?
Shekhar:
ctx.send({})
No errors just below message:
{
"data": null,
"error": {
"status": 404,
"name": "NotFoundError",
"message": "Not Found",
"details": {}
}
}
Have you given roles permission to the custom created API route?
Yes I have given, it works on my local gets all the data
But it doesn’t work on live server, right? Double check everything on live server too.
Shekhar:
ctx.send({})
yes double checked my routing is as below:
Hmm, that’s odd. Can you compare the whole Api url for both local and live server, see if anything’s wrong with the URL.
Also please adjust you route file code like below:
//.src/api/application/routes/application.js
'use strict';
const { createCoreRouter } = require('@strapi/strapi').factories;
const defaultRouter = createCoreRouter('api::application.application');
const customRouter = (innerRouter, extraRoutes = []) => {
let routes;
return {
get prefix() {
return innerRouter.prefix;
},
get routes() {
if (!routes) routes = innerRouter.routes.concat(extraRoutes);
return routes;
},
};
};
const myExtraRoutes = [
{
method: 'GET',
path:'/application-details',
handler:'api::application.application.getFormDetailsBasedOnApplicationAction'
}
];
module.exports = customRouter(defaultRouter, myExtraRoutes);
I am sure this will work properly at each places.
Shekhar:
const defaultRouter = createCoreRouter('api::application.application');
const customRouter = (innerRouter, extraRoutes = []) => {
let routes;
return {
get prefix() {
return innerRouter.prefix;
},
get routes() {
if (!routes) routes = innerRouter.routes.concat(extraRoutes);
return routes;
},
};
};
const myExtraRoutes = [
{
method: 'GET',
path:'/application-details',
handler:'api::application.application.getFormDetailsBasedOnApplicationAction'
}
];
module.exports = customRouter(defaultRouter, myExtraRoutes);
Tried this did not work
"use strict";
/**
* application controller
*/
const { createCoreController } = require("@strapi/strapi").factories;
module.exports = createCoreController(
"api::application.application",
({ strapi }) => ({
async getFormDetailsBasedOnApplicationAction(ctx) {
try {
/**
* Queries the RCMP collection type
* using the Entity Service APIs
* to retrieve information about the documents
*/
const user = ctx.state.user;
if (!user) {
return ctx.badRequest(null, [
{ messages: [{ id: "No authorization header was found" }] },
]);
}
const entries = await strapi.entityService.findMany(
"api::application.application",
ctx.query
);
const finalEntries = [];
Promise.all(
entries.map(async (entry) => {
let formData = {};
if (entry && entry.formType === "RCMP") {
formData = await strapi.entityService.findOne(
"api::rcmp-form.rcmp-form",
entry.orderId,
{
populate: { document: true },
}
);
finalEntries.push({ ...entry, formData });
} else if (entry && entry.formType === "FBI_APOSTILLE") {
formData = await strapi.entityService.findOne(
"api::fbi-apostille-form.fbi-apostille-form",
entry.orderId,
{
populate: { document: true },
}
);
finalEntries.push({ ...entry, formData });
}
})
)
.then(async (results) => {
const sanitizedEntries = await this.sanitizeOutput(
finalEntries,
ctx
);
console.log(sanitizedEntries)
return ctx.send(this.transformResponse(sanitizedEntries));
})
.catch((e) => {
ctx.body = e;
return ctx.send(this.transformResponse(e));
// Handle errors here
});
} catch (err) {
ctx.body = err;
return ctx.send(this.transformResponse(err));
}
},
})
);
**strong text**
Its weird because its consoling the output of sanitized entries on the server as well
Server outputs response but router says 404 not found
Shekhar
December 4, 2023, 9:40am
12
Okay. So there’s nothing wrong with the route call but something wrong with your Promise.all()
code block.
I see you are using finalEntries.push()
instead or returning value under the Promise.all()
. Before the values are pushed in to the finalEntries the API just run off. Meaning, Api is executed successfully and is not awaiting for finalEntries
values in response.
I think that might be the culprit
Can you test it by replacing the below code with your Promise code block:
const finalEntries = Promise.all(entries.map(async (entry) => {
let formData = {};
let responseData = {};
if (entry && entry.formType === "RCMP") {
formData = await strapi.entityService.findOne("api::rcmp-form.rcmp-form", entry.orderId, {
populate: { document: true },
});
} else if (entry && entry.formType === "FBI_APOSTILLE") {
formData = await strapi.entityService.findOne("api::fbi-apostille-form.fbi-apostille-form", entry.orderId, {
populate: { document: true },
});
}
responseData = { ...entry, formData };
}))
.catch((e) => {
ctx.body = e;
return ctx;
});
console.log(finalEntries) // Check this with your old code and then check it with the above code
I hope this may work as I use the same concept in my project.
Shekhar:
const finalEntries = Promise.all(entries.map(async (entry) => {
let formData = {};
let responseData = {};
if (entry && entry.formType === "RCMP") {
formData = await strapi.entityService.findOne("api::rcmp-form.rcmp-form", entry.orderId, {
populate: { document: true },
});
} else if (entry && entry.formType === "FBI_APOSTILLE") {
formData = await strapi.entityService.findOne("api::fbi-apostille-form.fbi-apostille-form", entry.orderId, {
populate: { document: true },
});
}
responseData = { ...entry, formData };
}))
.catch((e) => {
ctx.body = e;
return ctx;
});
Where exactly? should this be placed i dont see it returning the values
I understand what you are saying its actually not resolving the promise just going outside and trying to find a response but then it doesnt so it causes a 404 error
Shekhar
December 4, 2023, 11:19am
15
Yes correct. That’s what I was trying you to explain and that is why I shared you a different code.
Check my code, I have assigned return values from inside of the whole promise to finalEntries variable. Try debugging it using console.log().
Then send it to the api response via
ctx.body = finalEntries;
OR ctx.send({ data: finalEntries })
Shekhar
December 4, 2023, 1:44pm
17
@vinikatyal I have to check it myself by creating a demo in my local and the following code worked for me.
The route url:
The controller function:
Output:
1 Like
Thanks so much really appreciate your replies
2 Likes
@Shekhar thank you for your help.
2 Likes