15

I have a custom implementation of a RESTful API for a PHP application that returns json data, and in order to communicate the status of the operation, ie whether there were failures in the request, I'm setting a custom HTTP Header with a (very tiny) json object as a string. This works well since I can send responses and easily retrieve them client side without messing with the actual data sent.

The question is, are there any drawbacks I may not have realized of using this method? It doesn't seem to be very common for applications to set custom http headers, so I'm wondering whether it is a bad practice or bad "taste" somehow.

11
  • You mean in the status code? Like "200 {error:true}" ? Or a real header as "X-Something: whatever"? Commented Jun 29, 2012 at 15:02
  • 2
    The HTTP spec already addresses this. If there was a failure, you should return the proper HTTP status code and a description of the error in the body, not a custom header. Commented Jun 29, 2012 at 15:06
  • What if there is no proper HTTP code for the error in question? Commented Jun 29, 2012 at 15:11
  • @Artefact2 Then send a valid HTTP code that indicates a generic error (e.g. 500) and embed a specific error code in the returned JSON data. Commented Jun 29, 2012 at 15:12
  • 1
    Not necessarily malformed, imagine you are asking for two icecreams and I return you one; it's not what you expected, but you can still do something with it (provided you handle it properly) Commented Jun 29, 2012 at 18:23

1 Answer 1

16
Answer recommended by PHP Collective

This is an interesting question. There shouldn't be any reason for it to be a problem, but you should take a few things into account:

  1. The headers need to be unique to your application. Not just now, but forever. You should ensure you're prefixing them, e.g. X-MyApplication-Foo: Bar. Not doing this might cause conflicts in future.

  2. Firewalls are sometimes (rarely) a little overzealous with filtering unknown HTTP headers. This shouldn't be a problem, but it's something to keep in mind.

  3. Older browsers have smaller limitations on header field sizes than modern browsers, so you need to test across as many as you can get hold of.

Is there are reason you can't use the standard HTTP error codes? I understand that you might want to provide stack traces or other useful debugging information, but in the case of an error, wouldn't you just return a JSON blob that contains the error information, rather than the normal "result" JSON data? You could easily detect the difference based on the HTTP error code and handle the two cases differently.

The reason I'm concerned by your suggested approach is that headers are used to alter or cause browser behaviour - they're not intended to be a data storage mechanism.

Pseudo-code example:

switch(httpResponseCode)
{
    case 200:
        parseResult(json);
        break;
    case 403:
        parseForbidden(json);
        break;
    case 500:
        parseServerError(json);
        break;
    default:
        // bad response code, handle appropriately
}
Sign up to request clarification or add additional context in comments.

3 Comments

The thing with headers is that, as opposed to a JSON reply, they can be set anywhere from the application, which makes it ideal to replace for instance throw exception statements across the application when the call is made through AJAX. Otherwise, if a class that depends on another class which depends on another class fails, the JSON reply data has to be sent back and forth in order to get the error response back, so the choice of the headers seemed natural to save time. But maybe I'm just being lazy.
Great points either way. Somehow it already felt natural to prefix the header with the application name.
Why not just have a global array variable to store such headers? You can serialize the array down into JSON when you write the result back to the client.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.