1

It's extremely common to see code like this for checking XHR:

if (
     isset($_SERVER['HTTP_X_REQUESTED_WITH']) &&      
     strtolower($_SERVER['HTTP_X_REQUESTED_WITH']) == 'xmlhttprequest'
) {
    // ajax happened
}

Why is strtolower always used here instead of just comparing to XMLHttpRequest? Is it just paranoia or is there a real reason?

Wesley Murch
  • 101,186
  • 37
  • 194
  • 228
  • 1
    Some frameworks etc. can send that string without "correct" size of chars. If you are sure that your code sends "XMLHttpRequest", against "xmlhttprequest", you can simplify that line. – aso Sep 12 '13 at 15:31
  • @WesleyMurch — Are you writing a service that is accessed via across domains via CORS then? Or do you have a frontend developer who doesn't act as part of your team? – Quentin Sep 12 '13 at 15:37
  • @Quentin For sake of discussion, yes. – Wesley Murch Sep 12 '13 at 15:38
  • The question to ask is: are you 100% that all the existing browsers in the world send the correct case, and that all the existing web / proxy / caching servers keep the case unmodified. If not, then it is preferable to do so. – Tchoupi Sep 12 '13 at 15:38
  • Due to the comments so far, I now believe I have a fundamental misunderstanding of `HTTP_X_REQUESTED_WITH`. Where does this value come from and at what point(s) might it be modified? – Wesley Murch Sep 12 '13 at 15:39
  • @MathieuImbert — It has nothing to do with browsers. – Quentin Sep 12 '13 at 15:40
  • The browser will include this header when the request is sent by javascript. – Tchoupi Sep 12 '13 at 15:40
  • @WesleyMurch — Some developers, when working with XMLHttpRequest, including developers of some libraries (like YUI or jQuery), call `xhr.setRequestHeader("X-Requested-With: XMLHttpRequest")` instead of using something sane like `Accept: application/json`. – Quentin Sep 12 '13 at 15:42
  • @MathieuImbert — No. Browsers will not add it "when the request is sent by javascript". Browsers will add it when the developer includes code to set it. – Quentin Sep 12 '13 at 15:42
  • See [this](http://stackoverflow.com/questions/2579254/php-does-serverhttp-x-requested-with-exist-or-not#comment2585875_2579271) comment by bobince. – Amal Murali Sep 12 '13 at 15:43
  • @Quentin Apologies. You are right, it is indeed usually included by Javascript frameworks. – Tchoupi Sep 12 '13 at 15:43
  • OK so I still don't quite get it, in what real-life case would the value not be exactly `XMLHttpRequest`? Are there some existing, relevant frameworks that are sending a lowercase version? Is this *value* even considered a standard by any means? – Wesley Murch Sep 12 '13 at 15:47
  • @WesleyMurch — Then whomever writes the code doesn't say exactly `XMLHttpRequest`. I haven't done a survey of every Ajax helper library to find out. It isn't remotely standard (the standard would be the `Accept` header) – Quentin Sep 12 '13 at 15:58

1 Answers1

2

HTTP headers in the request are always included by the client. A client can be a shell script, a browser or an Ajax call fired by Javascript or a Javascript framework. The "j" in Ajax stands for Javascript, but the HTTP request of thus can be created with any other script or program.

From Common non-standard request headers:

X-Requested-With: mainly used to identify Ajax requests. Most JavaScript frameworks send this header with value of XMLHttpRequest XMLHttpRequest.

All headers starting with X-are non standard headers, which means there is no official document defining their values.

From https://www.rfc-editor.org/rfc/rfc6648:

Historically, designers and implementers of application protocols
have often distinguished between standardized and unstandardized
parameters by prefixing the names of unstandardized parameters with
the string "X-" or similar constructs.

The HTTP protocol is not fixed or static, there are just standards you should follow.

You can even create your own HTTP request and put individual headers in, for example:

X-Requested-With: MySuperCURLScript
X-MyOwnHeader: Cool!

To answer your question, if one client sends the header X-Requested-With: XMLHttpRequest, the other sends X-Requested-With: xmlHttpRequest, you can simply lowercase 'em all and be sure not to miss different notations. Simple as that!

Security aspect: The headers and its contents are only information, not something you should 100% rely on. If you have a deep look into CURL, or Google results for "send http header with php", you'll quickly find out that any information can be sent and faked easily. HTTP headers have often been abused to hack servers, by sending manipulated cookies (- a cookie is a header, simple as that: Cookie: ...), manipulated file information (upload a fake gif which is an exe file and so on), manipulating session data, POST / request data.

Community
  • 1
  • 1
Daniel W.
  • 31,164
  • 13
  • 93
  • 151