Returning REST 400-Bad Request with additional information - rest

Hey,
I have a REST based server, and in some cases I want to return a failure code (400 for example), BUT, I wish to add additional URL.
Something like - "failure, but here's what you can do now.."
Is there any good convention to do so?
Is it even a good idea to return error with additional information?
Thanks,
Udi

It is always a good idea to return additional information in an error message. The HTTP spec itself says so: "Except when responding to a HEAD request, the server SHOULD include an entity containing an explanation of the error situation, and whether it is a temporary or permanent condition. These status codes are applicable to any request method. User agents SHOULD display any included entity to the user."
One thing to watch out for: some versions of Internet Explorer will not show the user your additional error information if it is not a certain number of bytes. Make sure your response entities for error messages are at least 512 bytes to be sure.

Related

REST HTTP Response status code to indicate client input is non-verified?

We have POST API that gives particular user's contact details in response. But as this is confidential data, to access this detail, anyone accessing it needs to put verified mobile number.
The request looks like:
POST /api/userdetails
{
"userid": 123,
"mobile": "+1394839843"
}
What should be status code if "mobile" number is not a verified number in our database?
What should be status code if "mobile" number is not a verified number in our database?
From a very high level: think about what you would expect a plain old web site to do if a user submitted a form with a "not verified number" and do that.
The charts in Michael Kropat's Stop Making It Hard breaks the process down into more specific questions.
Is there a problem with the request? That's clearly a yes, here, so we know immediately that you'll want to use some code from the 4xx class.
From there, it's just a matter of looking through the semantics of each code and seeing which one best fits.
400 Bad Request is the generic client error, so you use that if you can't find a better match.
403 Forbidden is roughly "I understand your request, but decline to act upon it." This is most commonly associated with authentication and ACLs, but the standard doesn't actually require that. Given your description, it's not a bad match.
422 Unprocessable Entity from WebDav, is another possibility. I'd reject it, on the grounds that the schema of the message body is perfectly correct, the problem is that the specified value isn't aligned with the current state of the server. You might want to review a previous discussion about 400 vs 422

400 vs 422 response to POST that references an unknown entity

I'm trying to figure out what the correct status code to return on different scenarios with a "rest-like" API that I'm working on.
This example is borrowed from another question about syntax type issues in the body, but my question assumes valid syntax throughout.
Let's say I have an endpoint that allows POST'ing purchases in JSON format. It looks like this:
{
"account_number": 45645511,
"upc": "00490000486",
"price": 1.00,
"tax": 0.08
}
What is the appropriate status code if:
the account number does not exist
the account is closed or the
account identified is not the right kind of account
These are all firmly business layer issues that prevent "processing" from occuring, however, one scenario involves something that in a GET would be a 404.
Note that the account number is not in the URL, so is 404 misleading?
Let's take these one at a time. Each of these codes is a signal to your client that the server is functioning correctly, and that something must be changed in the request before it can be successfully carried out.
HTTP 400
The 400 (Bad Request) status code indicates that the server cannot or will not process the request due to something that is perceived to be a client error (e.g., malformed request syntax, invalid request message framing, or deceptive request routing).
400 typically indicates a syntax error; as a user, I should look at the structure of the request before trying again.
HTTP 404
The server has not found anything matching the Request-URI. No indication is given of whether the condition is temporary or permanent. The 410 (Gone) status code SHOULD be used if the server knows, through some internally configurable mechanism, that an old resource is permanently unavailable and has no forwarding address. This status code is commonly used when the server does not wish to reveal exactly why the request has been refused, or when no other response is applicable.
404 is the standard code used when a web server can't match a url path to anything. As a client, I should look at the URL of the request before trying again.
HTTP 422
The 422 (Unprocessable Entity) status code means the server understands the content type of the request entity (hence a 415 (Unsupported Media Type) status code is inappropriate), and the syntax of the request entity is correct (thus a 400 (Bad Request) status code is inappropriate) but was unable to process the contained instructions. For example, this error condition may occur if an XML request body contains well-formed (i.e., syntactically correct), but semantically erroneous, XML instructions.
422 is generally used for content violations. As a user, I should look at the content of my request before trying again.
Now in your case, account number is an identifying number, but is not included in the URL. A 404 would signal to your user that the URL is wrong, not the payload. Stated another way, suppose your url is:
http://www.myservice.net/endpoint
A 404 would indicate to me that no service exists at /endpoint, instead of no account number. No matter what content I submit, the server will not process my request. The fix I should make then would be to look for an error in the URL, instead of the data payload. So to me a 422 would point me in the right direction, unless you begin to include the account number in the URL.
Ultimately these are design preferences, just make sure you communicate them clearly to your users.
If you consider the accounts to be part of the state of the resource (though indirectly) then you might also consider 409 since that state is in conflict with the semantics of the request.
However, 422 is gaining popularity via Ruby on Rails and Dropwizard where it is used to indicate non-syntactic issues with the body. That growing tendency represents a strong signal to a developer using the API that they need to exclude syntax and focus on the body. Developer time is usually the single largest cost your customers will ever incur, so by directing the attention of their developers you will keep them happy.
So 409 is a possible answer, though rather novel, and 422 is the more conventional approach, although obviously RoR and DropWizard are both rather new so these conventions can be said to be changing fast!
I'd say 422 is adequate in your case, but 400 isn't bad if it's consistent with the rest of your API. It's a common convention to use 400 as an umbrella error code when there's something wrong on the client side, but either the error doesn't fit a particular error code, or you don't want to use too many of them.
A 404 is definitely wrong if there's something wrong with the POST payload.
Case 1 : Account number doesn't exist.
This is a standard case for 404.
Case 2 : Account is closed.
This has do with the logic if you keep the account details when you close it.
If you donot keep the account details when the account is closed, you can give 404.
If you keep the account details after it is closed, you must be marking it (like raising some flag) (or whatever logic you have). In this case, Status code 400 with a proper message of why it is failed and possibly remediation will do.
Case 3 : Account identified is not the right kind of account.
403, as the account is not authorised for completing any purchases makes sense to me. If there is no concept like authorised account, 400 with a explanatory message will do. But I would insist to go with 403 in this case.
Actually, in this case 404 sounds good to me.

How to send response code in REST services.?

I am developing RESTful Services to CREATE operations. In my use case, it is enough to tell the clients whether the transaction is success or fail. And if fail, we need to send them back error code.
Is it possible to send only these information back without sending xml response or JSON response. If so, how to do it.
We have existing error code in 5 digits, we wont be changing this for this api. If this is not possible.
Will JSON response better than XML response.? We are accepting XML request.
Requesting your comments.
I'm going to assume this service will be called over HTTP, since that's what most people mean when they say "RESTful service."
Generally speaking, most people map "create" type functionality to POST methods (though you can also do it with PUT).
If you just need to indicate that the record was created, the answer is "None of the above" (i.e., you don't need a response body at all). Usually a 201 Created is returned with a Location header which specifies the URL of the newly-created resource. In theory, you could also return a 204 No Content since you don't need to pass anything other than the status code (though this would be more appropriate for a PUT, otherwise there is no way to communicate to the client the identifier of the newly-created resource).
For failures, usually a 400-series error is returned if the request message is bad (i.e., it's the client's fault) and a 500-series error is returned if a system error occurs when processing (i.e., it's the server's fault). If you need to convey additional information in the response body, consider returning a response that uses a media type of something like application/vnd.error which allows you to express context information about where the error occurred.

Asp.NET Web Api: Returning meaningful errors to client?

I have created myself a standard asp.net web api project and it has a Post on there.
The post basically will insert some values into a database but before doing so I need to do a number of different checks on an alternative database, if anything doesn't check out I want to return the client with a NON 200 http status code but which should I use?
What is the recommended status code to return? I would also like to return some text with it which would contain additional information that could identify what the error was.
Or is it recommended to return 200 and an additional JSON payload identifying if there was a problem and what it is
Does anyone have any examples??
Thanks in advance
400 BadRequest could be used if what you are performing is validation logic and this validation logic fails for some reason. As far as the additional information is concerned, you might return some info in the body, for example as JSON payload:
{
"errorMessage":"Validation failed because user doesn't exist in alternative database"
}
If on the other hand you are attempting to update an entity that doesn't exist, you could also send a 404 status code.
In addition to what Darin stated on this thread, here is a good reference on status codes. I have also found this article valuable in handling errors with ASP.NET WebAPI.

Best way to return error messages on REST services?

I've been looking at examples of REST API's like Netflix http://developer.netflix.com/docs/REST_API_Reference#0_59705 and Twitter and they seem to place error messages in the statusText header response instead of the responseText. We're developing an internal RESTful api and I am arguing for sending custom statusText messages and ignoring the responseText.
For the scope of our app, we're returning error 400 when the user has tried doing something they aren't supposed to, and the only error messages that will be updated in the UI for the user will be delivered with 400. I am of the belief that the message should be sent as a modified statusText but one of the engineers (who knows a bit less about REST than me) is arguing for sending it in the responseText.
What's the best way to go?
HTTP defines that you should put a descriptive error message in the response entity body, aka responseText.
statusText is not rendered or processed by any client.
I'd use the status text for the error message type, aka 400 Client Error, and the body for a description of the problem that can be rendered to the user, in whatever the format the client may be able to process.
Edit: Note that since then, a new standardised format exists to communicate in a standard fashion error details back to the client, which you can find at https://www.rfc-editor.org/rfc/rfc7807 and which I would recommend.
I think you're right, the general approach is use the existing error mechanism built into HTTP.
In general, try to map your errors to existing HTTP errors, for example if they request something they don't have permission to, return a 403 error.
If they request something that doesn't exist, return a 404.
Alex
According to the HTTP specification (rfc2616): "HTTP status codes are extensible"
However I don't think that creating new statuses for every different error message is the correct approach:
I would say choose HTTP Status appropriately (HTTP Status Code Definitions) if you can't find any category which matches your requirement create a custom one (but I'm sure you will) and put error messages in the HTTP response body.
Picking appropriate status code for your responses is extremely important as it is a key enabler of self-descriptive messages.
The entity body should be a representation of the resource's state and ideally contain hyperlinks to available next states in your application
Http Status Codes are pretty self explanatory and should be used as such. Returning 200 OK with validation errors is pretty Soap-y and misleading. Any REST Client implementation 4xx and 5xx errors go into a error block and it really depends on case to case basis if you really want to use the response body for non 2xx responses.