ColdFusion UDF for detecting jQuery AJAX operations…

Posted by Dan on Apr 9, 2009 @ 6:43 PM

Raymond Camden justed posted an article on detecting jQuery AJAX operation using ColdFusion. I honor of that post, I thought I'd share the UDF I've been using in my application for quite some time:

<cffunction name="isAjaxRequest" output="false" returntype="boolean" access="public">
    <cfset var headers = getHttpRequestData().headers />
    <cfreturn structKeyExists(headers, "X-Requested-With") and (headers["X-Requested-With"] eq "XMLHttpRequest") />

The code uses the exact same logic the technique in Raymond's post, but having the code in a function makes your detection code a lot easier to read.

Now when you want to detect if a request came from an AJAX operation, you can just do:

<cfif isAjaxRequest()>
    Came from jQuery! :)
    Didn't come from jQuery. :(

Doesn't get any easier than that!

Categories: HTML/ColdFusion, jQuery


  • Great tip, I could have used it several projects ago!

    But this is somewhat misleading. It tells you an "X-Requested-With" header is present with a value of "XMLHttpRequest". Not necessarily that jQuery made it though. Scriptaculous adds that header, too. Most likely others as well.
  • @Jules:

    While other libraries do send it, jQuery always sends with any XHR requests. So it's not going to tell you it's jQuery specifically, hopefully you know what library you're using on your website. :)
  • I know I could test this myself but I thought I'd highlight/ask anyway...

    What about a .get() or .post() request in jQuery I wonder?
  • @Adrian:

    The $.get() and $.post() methods in jQuery are just shortcuts to the $.ajax() method--they are all still AJAX operations. Any XHR call in jQuery will be invoked with the extra header.

    Some other libraries do the same thing. It's not part of the formal XMLHttpRequest() spec, but it's a nice way to easily determine an AJAX request.

    You could also use the same technique in your own code, you'd just have to build in the header addition into your XHR library.
  • When you say <cfif isAjaxRequest()> in a component, does that mean that isAjaxRequest must also be defined in that component, or do you extend the component, or do you mean <cfset obj = ...> <cfif obj.isAjaxRequest()> ?
  • @Phillip:

    How you handle it up to you. I essentially keep a class library of UDFs that I import into any template I need that class of library files.

    However, if I'm invoking a CFC AJAX, then I really don't have a need for the function in the first place--since I'm generally going to be return a structured data type (such as a struct.) So, how I called the function remotely is irrelevant.
  • I'm just making sure I have the syntax correct.
    If you are <cfif isAjaxRequest()> in a template, then you must first do a <cfinclude > of a .cfm file that contains all your commonly used UDFs, right?
  • @Phillip:

    Yes, or some people like to store their UDF libraries in a persistent cope (like the application scope) so they're always available and they don't have to reload on each page.

    Whatever fits your model the best.
  • Oh, ok. And I'm not asking you to speak for everyone. I'm just trying to understand your blog post.
    So do you say Application.isAjaxRequest() or do you do a cfinclude?
    I know the answer can be "You can do anything you want!", but I'm just trying to understand what Dan Switzer does.
    And I'm really hoping the answer to that isn't "It depends".
  • @Phillip:

    Unfortunately, it is "it depends." There's no "one ring to rule them all," it really depends on the application and what type of framework you're using to what makes sense.

    I've both cached UDFs in a persistent scope and used <cfinclude /> to import libraries into code. I just make my decision based upon what makes more sense to the current codebase.

    When working on code that's essentially procedural based, I tend to use <cfinclude /> more as "import" statement for loading the library--especially since I have some pretty large UDF libraries (which are organized by functionality.)
  • I just add a ajax=1 variable on the end of ajax requests. Or add a timestamp variable to also avoid caching. Then check for that.

Add Comment

Leave this field empty