How to throw error code in Custom HTTP Module? - c#

I am writing an authorization function in Custom HTTP Module.This is my code:
private bool CheckAuthorization(HttpContext context)
{
string auth = context.Request.Headers["Authorization"];
if (string.IsNullOrEmpty(auth) || auth != "123")
{
context.Response.StatusCode = -404;//HttpStatusCode.MethodNotAllowed;
context.Response.Write("404 Not allowed!");
//webOperationContext.OutgoingResponse.StatusCode = HttpStatusCode.MethodNotAllowed;
}
return true;
}
My develop enviroment is:C# + .NET Framwork 4.0 + Visual Studio 2013 + WCF.My purpose is: When checked authorization failed,the request should not invoke the WCF method,and return a 404 method not allowed error.It is still invoke WCF method right now through return the error tips.Thank you!

You can throw an HttpException which will not be handled and supply the necessary error to the browser.
throw new HttpException(404, "HTTP/1.1 404 Unauthorized");
Throwing an exception will cause the request to terminate and your WCF method should not run. However, if you have a try catch wrapping the CheckAuthorization call, then it's important that you rethrow the HttpException. In order for it to work you cannot handle the exception, let the ASP.Net pipeline handle it.

Related

Why does HttpClient.PostAsync not throw on failure?

In an ASP.Net Core web service if an HttpClient.GetStringAsync call fails for 404 error or whatever, it throws an HttpRequestException. This is great.
If on the other hand an HttpClient.PostAsync call fails for 404, it does not throw an exception. I have to check the status code, fabricate an exception and throw it manually.
Why the discrepency, and is there a more elegant way of dealing with this?
HttpResponseMessage response = await _http.PostAsync("api/pollapi/request", new StringContent(requestInput));
if (!response.IsSuccessStatusCode)
{
throw new HttpRequestException($"Response status does not indicate success: {(int)response.StatusCode} ({response.StatusCode}).");
}
You can use HttpResponseMessage.EnsureSuccessStatusCode method that:
Throws an exception if the IsSuccessStatusCode property for the HTTP response is false.

How to catch "A potentially dangerous Request.Path value was detected from the client (:)" to avoid web role crash?

My MVC 5 web application running on Azure Cloud Service crashed with an unhandled exception "A potentially dangerous Request.Path value was detected from the client (:)".
The cause for this crash was some third party (maybe malicious) hit my endpoints with url:
http://myExampleHost.com/m:443/templates
The colon in the url cannot pass the path validation.
Some answers (A potentially dangerous Request.Path value was detected from the client (*)) suggest change the validate rules. However, out of security concerns, we may not want to compromise on this.
The ideal behavior for it that: we catch the exception, log it and return some error messages without crashing. How should we do that?
A more general question on this would be: how to catch an exception before the request hits controllers in MVC?
The ideal behavior for it that: we catch the exception, log it and return some error messages without crashing. How should we do that?
Per my understanding, you could leverage the Application_Error event to capture unhandled exception(s) within ASP.NET. Here is my test, you could refer to it:
protected void Application_Error()
{
HttpContext httpContext = HttpContext.Current;
var exception=Server.GetLastError();
var httpException = exception as HttpException ?? new HttpException(500, "Internal Server Error", exception);
var jsonResponse = new
{
Message = exception.Message,
StatusCode = httpException.GetHttpCode(),
StackTrace=httpException.StackTrace
};
httpContext.Response.ContentType = "application/json";
httpContext.Response.ContentEncoding = Encoding.UTF8;
httpContext.Response.Write(JsonConvert.SerializeObject(jsonResponse));
httpContext.Response.End();
}
Note: You could also redirect to a specific error page.
Moreover, you could leverage the customErrors in web.config and catch the error page for the specific HTTP error code. Also, you could check the HTTP status code under the Application_EndRequest event and write your custom response, details you could refer to this similar issue. Additionally, I would recommend you follow Demystifying ASP.NET MVC 5 Error Pages and Error Logging for more details about error handling.

Web API always returns internal server error instead of error which I have thrown

I am using HttpClient to invoke this web API
using (var client = new HttpClient(new HttpClientHandler() { Credentials = _credentials }))
{
client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
return await client.PostAsJsonAsync(controlActionPath, entityObject);
}
Web API controller I am throwing bellow error:
throw new DuplicateNameException("User already exists.");
However web app always getting internal server error instead of DuplicateNameException.
It would be helpful, if someone suggest what will be the best way to get the exact exception back to Web application from Web API.
Because you are throwing an exception, that automatically becomes an internal server error, because it's still in your internal server-side code. You can either create an exception handler like in this answer or you can throw a specific HttpResponseException type as detailed in the Web API documentation on exception handling:
var response = new HttpResponseMessage(HttpStatusCode.BadRequest)
{
ReasonPhrase = "User already exists."
};
throw new HttpResponseException(response);

How to throw exception in Web API?

How can I throw a exception to in ASP.net Web Api?
Below is my code:
public Test GetTestId(string id)
{
Test test = _test.GetTest(id);
if (test == null)
{
throw new HttpResponseException(HttpStatusCode.NotFound);
}
return test;
}
I don't think I am doing the right thing, How do my client know it is a HTTP 404 error?
It's absolutely fine.
Alternatively, if you wish to provide more info (to allow, as you say, the client to distinguish from regular 404):
if (test == null)
{
throw new HttpResponseException(Request.CreateErrorResponse(HttpStatusCode.NotFound,
"this item does not exist"));
}
This blogpost should help you understand WebAPI error handling a bit better.
What you have in your code snippet should work. The server will send back a 404 Not Found to the client if test is null with no response body. If you want a response body, you should consider using Request.CreateErrorResponse as explained in the blog post above and passing that response to the HttpResponseException.

How to handle a exception thrown in c# by a javascript web app?

I'm developing a web application with a client side build with html5 and javascript using, overall, dojo framework (I'm using xhr.post function to communicate with server). The server side is an asmx service in c#.
Here comes the problem: when a webmethod of my service throws an exception:
try
{
throw new Exception("TEST");
}
catch (Exception ex)
{
throw ex;
// TODO: send some info to the client about the error
}
the client is realized than an error has occured and fires the error callback function:
deferred = xhr.post({
url: that.config.urlService,
handleAs: that.config.handleAs,
contentType: that.config.contentType,
postData: that.config.parameters
});
deferred.then(function (res) {
that.success(res);
},
function (err) {
if (that.config.callbackFail) {
that.config.callbackFail(err, that.config.parameters);
}
}
);
But in the 'err' paramater I don't have the exception info, I have the message:
'NetworkError: 500 Internal Server Error - http:/.../Services/Applications/Metrawa/ServiceManagement/WSJob.asmx/Filter'
and inspecting the call to server with firebug, in the response tab I can see strange characters, like if the exception hasn't been serialized.
What I want is to get the exception info in javascript. I've searched some info about this, like to create an own serializable exception class, but it doesn´t work neither. Any solution?
Thanks in advance.
You may opt to handle the exception in your server-side code and send it back as JSON, XML or even String--i.e. something your client can understand.
I would catch the exception server side and always return a valid object with a "Result" property:
eg res.Result (as "OK" or "ERR" etc and handle that on the client)

Categories