FunctionMonkey
FunctionMonkey copied to clipboard
Requests with exceptions on Application Insights have Sucess = "True" instead of "False"?
I'm using IHttpResponseHandler to handle the execeptions using CreateResponseFromException:
public async Task<IActionResult> CreateResponseFromException<TCommand>(TCommand command, Exception exception)
where TCommand : ICommand
{
this.logger.LogError(exception.InnerException, exception.InnerException.Message);
IActionResult response = new ContentResult()
{
StatusCode = (int)HttpStatusCode.InternalServerError
};
return response;
}
I'm logging here the exceptions to Application Insights using the Microsoft ILogger abstraction. When an exception occurs is properly log, but the request is assumed as "Sucess" instead of "Failed", because the exception was handled by Function Monkey (I think). Is possible to set the request to "Failed"?
I think to set the request to failed you literally need to fail the function - which means throwing an exception. In the code above you could throw an exception immediately under your call to the logger and that should return a 500 status code and fail the function.
Let me know how you get on. Will leave this open for now.
Yes if I do that it works, but the above code was just a simple sample to understand the issue.
In my real scenario, when people call the Http API, I need to provide a structured ErrorContent with the exceptions/errors and still have the "Sucess = False". If I throw an Exception I'm not able to provide that.
So as I understand this is a limitation of Azure Functions/ Application Insights. Since the only way to write "Sucess = False" is the function to fail with an exception.
Not sure if this Logging should be active by default on FunctionMonkey, otherwise exceptions would be "hidden". Is this the proper place to Log the exceptions?
Yes that's correct. I'm not sure there is anything I can do to turn this off. I may be misunderstanding?
I think the following code should be changed catch(System.Exception ex) { {{#if HasHttpResponseHandler}} var responseTask = pluginFunctions.CreateResponseFromException(command, ex); var handledResponse = responseTask != null ? (await responseTask) : null; return handledResponse ?? CreateResponse(500, "Unexpected error", pluginFunctions); {{else}} log.LogError(ex, $"Error occurred executing command {command.GetType().Name}"); return CreateResponse(500, "Unexpected error", pluginFunctions); {{/if}} }
to catch(System.Exception ex) { {{#if HasHttpResponseHandler}} var responseTask = pluginFunctions.CreateResponseFromException(command, ex); var handledResponse = responseTask != null ? (await responseTask) : null; if (handledResponse == null) throw; return handledResponse; {{else}} log.LogError(ex, $"Error occurred executing command {command.GetType().Name}"); throw; {{/if}} }
In this case the original exception will be thrown and a function will "Fail".
What do you think?
Interesting. That could well do it. And I don't think anythng is lost from a FM / REST point of view. I'll have an experiment with that.
My custom ResponseHandler just throws an original exception and it works well (Failure in App Insights as expected). The problem with the handler is that it hides the origin of the exception by re-throwing via "throw ex". Using just "throw" in the catch area would solve it.