Is there a way to have Nest use the ExceptionsHandler error message as the API response message when an exception is thrown? - exception

When an error is thrown within my Nest API, often times the error that is thrown is not an HttpException, and therefore the standard Nest API response that I see from the client's side is:
{
"statusCode": 500,
"message": "Internal server error"
}
But when I look at the console log, there is a much more descriptive error message, for example:
[Nest] 18476 - 06/23/2022, 2:28:07 PM ERROR [ExceptionsHandler] Cannot perform update query
because update values are not defined.
UpdateValuesMissingError: Cannot perform update query because update values are not defined.
Is there a way I can route this message to be the in the response body of the response given back to the API client?

You can use Global Filter in NestJs to catch error and then throw a good error.
For exemple, you can create a Exception Filter
// UpdateValuesMissingError.exception-filter.ts
import { ArgumentsHost, Catch, ExceptionFilter } from '#nestjs/common';
import { Request, Response } from 'express';
#Catch(UpdateValuesMissingError)
export class UpdateValuesMissingErrorFilter implements ExceptionFilter {
catch(exception: UpdateValuesMissingError, host: ArgumentsHost) {
const ctx = host.switchToHttp();
const response = ctx.getResponse<Response>();
const request = ctx.getRequest<Request>();
console.log(exception);
response.status(400).json({
statusCode: 400,
timestamp: new Date().toISOString(),
path: request.url,
});
}
}
and in your main.ts add this
app.useGlobalFilters(new HttpExceptionFilter());
And now in response.status(400).json({}) you can add everything you want in your body. Like the error message of Axios.

Related

Catch return json from POST with Axios when error 400 (Bad Request) occurs

I am making an http request in an api using React Native with Axios, I can get json and parsear it when the callback is 200, however, for example, when I call a method, for example, to register the user and step an email from a user who is already registered, he returns me an error 400 (Bad Request) but he also brings a json with the error message ("user already registered"). I need to get this error message since it is variable in the API and show to the user, but when I try to give it a console.log I get the following error:
json's return is this:
and my call code looks like this:
How to get this json even with return 400 in catch?
Thank you.
inside of your catch Block, the error object also provides you with a response body
//... your request here
.catch(error => {
console.log('response: ', error.response.data);
});
console.log(error) is calling the toString method of the error object which doesn't show you the response body.
error.response.data should give you the right content. Take a look at this part of the axios docs

How can I make Feathers (Express-based API Framework) Return Error Responses

I've read the Feathers book, so I know that to create an error response I simply instantiate the appropriate feathers-errors class:
import {BadRequest} from 'feathers-errors';
const errorResponse = new BadRequest(`foo`, `bar`);
However, I'm having difficulty returning that error response to the user. Even when I create an endpoint that does nothing but return an error response ...
class SomeService {
create(data) {
return new BadRequest(`foo`, `bar`);
}
}
it doesn't work: instead of getting an error response, I get no response, and inside the Chrome debugger I can see that the response is pending (until it eventually times out and becomes an ERR_EMPTY_RESPONSE).
I tried reading about Express error handling, and in the examples I saw people used next to wrap the the response. However, next comes from the error handler, and I'm not sure where in my Feathers code I can get that next function.
If anyone could help explain (using next or not) how I can return a complete, not pending, error response, I would greatly appreciate it.
Your services have to return a promise. If your code is not asynchronous you can turn it into a promise with Promise.resolve and Promise.reject:
class SomeService {
create(data) {
return Promise.reject(new BadRequest(`foo`, `bar`));
}
}
Also make sure you registered the Express error handler to get nicely formatted errors:
const errorHandler = require('feathers-errors/handler');
// Last in the chain
app.use(errorHandler);
There is also more information in the error handling chapter.

NodeJS request-json setting header breaks

I'm using request-json, found on npm, to query my API server. My server requires that an auth token be passed in the header, but using request-json's method of setting headers produces the following error:
Error: "name" and "value" are required for setHeader().
at ClientRequest.OutgoingMessage.setHeader (_http_outgoing.js:333:11)
at new ClientRequest (_http_client.js:101:14)
at Object.exports.request (http.js:49:10)
at Request.start (C:\Users\Michael\Desktop\FrescoWeb\node_modules\request-js
on\node_modules\request\request.js:904:30)
at Request.write (C:\Users\Michael\Desktop\FrescoWeb\node_modules\request-js
on\node_modules\request\request.js:1625:10)
at end (C:\Users\Michael\Desktop\FrescoWeb\node_modules\request-json\node_mo
dules\request\request.js:666:16)
at Immediate._onImmediate (C:\Users\Michael\Desktop\FrescoWeb\node_modules\r
equest-json\node_modules\request\request.js:690:7)
at processImmediate [as _immediateCallback] (timers.js:358:17)
I'm setting the header and hitting the endpoint in the following code:
var api = requestJson.createClient(config.API_URL);
api.headers['authtoken'] = req.session.token;
api.post(
'/v1/outlet/update',
params,
function(error, response, body){
if (error)
return res.json({err: error}).end();
if (!body)
return res.json({err: 'ERR_MISSING_BODY'}).end();
if (body.err)
return res.json({err: body.err}).end();
req.session.user.outlet = body.data;
req.session.save(function(){
res.json({}).end();
});
}
);
When I comment api.headers['authtoken'] = req.session.token; out, the call doesn't crash. Is there something that I am doing wrong, or do I have to migrate to request for http requests?
req.session.token should be req.session.user.token

How to catch UrlFetchApp.fetch exception

Is there any way to catch the exception from UrlFetchApp.fetch?
I thought I can use response.getResponseCode() to check the response code, but I'm not able to, for e.g when there is 404 error, the script not continue and just stop at UrlFetchApp.fetch
Edit: This parameter is now documented here.
You can use the undocumented advanced option "muteHttpExceptions" to disable exceptions when a non-200 status code is returned, and then inspect the status code of the response. More information and an example is available on this issue.
The trick is passing the muteHttpExceptions param of UrlFetchApp.fetch().
Here an example (untested):
var payload = {"value": "key"}
var response = UrlFetchApp.fetch(
url,
{
method: "PUT",
contentType: "application/json",
payload: JSON.stringify(payload),
muteHttpExceptions: true,
}
);
var responseCode = response.getResponseCode()
var responseBody = response.getContentText()
if (responseCode === 200) {
var responseJson = JSON.parse(responseBody)
// ...
} else {
Logger.log(Utilities.formatString("Request failed. Expected 200, got %d: %s", responseCode, responseBody))
// ...
}
For some reason if the URL is not available (e.g. the service you're trying to use is down) it still looks like is throwing an error so you may still need to use a try/catch block.
why don't you use try catch and handle the error in catch block
try{
//Your original code, UrlFetch etc
}
catch(e){
// Logger.log(e);
//Handle error e here
// Parse e to get the response code
}
You can manually parse the caught error, but it's not recommended. When catching the exception (that is being thrown in case muteHttpExceptions is turned off), the error object would be in the following format:
{
"message": "Request failed for ___ returned code___. Truncated server response: {___SERVER_RESPONSE_OBJECT___} (use muteHttpExceptions option to examine full response)",
"name": "Exception",
"fileName": "___FILE_NAME___",
"lineNumber": ___LINE_NUMBER___,
"stack": "___STACK_DETAILS___"
}
If you for some reason prefer not using muteHttpExceptions, you could catch the exception e, look at e.message, substring the text between "Truncated server response: " and " (use muteHttpExceptions option to examine full response)", JSON.parse() it, and the returned object would be the error returned from the api call.
I wouldn't suggest it over muteHttpExceptions, just wanted to show the best way to get the error object this way.
Anyways, try-catch your UrlFetchApp.fetch() call to make sure you catch the unhandled exceptions, like 404.

How to read the json response when a 422 (Unprocessable Entity) error occur in C# Visual Studio

I'm sending some JSON data to a web service using "PUT" method, but I'm having 422 unprocessable entity error. How can I actually see the server response in JSON? I digged deep into the exception but i still can't find the json response.
Ex:
JSON Request:
{
customer:
{
name: "asd",
address: "test"
}
}
and if everything was ok it should response to me some JSON data.
Ex:
{
customer:
{
id: 1,
name: "asd",
address: "test"
}
}
You can catch WebExpection and get Response from that and extract the correct error message:
Code :
catch (WebException ex)
{
using (var sr = new StreamReader(ex.Response.GetResponseStream()))
{
var data = sr.ReadToEnd();
throw new ApplicationException(data);
}
}
You could manually test this rest service with Fiddler.
422 HTTP error explanation: The request was well-formed but was unable to be followed due to semantic errors.
So check for example if JSON data you're sending is in the right format.
To answer your question: You cannot get a detailed answer in json specifying the syntax error than you have. It will be a manual trial and error process, to find the error.
As mentionned by user3470814, you should catch this kind of error and do something with it in your application.
And as mentionned by lucask, Fiddler will help you to see the exact string sent in your request.