views:

156

answers:

3

I have a Grails controller action that is used for Ajax purposes, though you can still navigate and view the page in the browser.

class QuoteController {

def quoteService

/**
 * This page uses the ajaxRandom function defined below to display random quotes.
 */
def random = {
    def randomQuote = quoteService.getRandomQuote()
    [quote:randomQuote]
}

/**
 * I do not want this to be a valid page, but maintain its use as a simple Ajax method.
 */
def ajaxRandom = {
    def randomQuote = quoteService.getRandomQuote()
    response.outputStream << "<q>${randomQuote.content}</q><p>${randomQuote.author}</p>"
}
}

Is there a way to redirect if someone visits the URL via browser while maintaining the method's Ajax functionality from within a page?

A: 

A simple way is to append a param to the url when calling it via ajax e.g. ?ajax=true

Then check for it and redirect if it's not there (such as when a use hits it with their browser).

If that is too easy to work around, inspect the request to see what is different between a browser request and an ajax request.

cheers

Lee

leebutts
A: 

If you AJAX requests are always POSTS then you could check the method and assume a POST is an AJAX call because it's pretty hard for the average user to create a POST accidentally, where as they can always GET any URL (if they know of it)

Hope this helps.

Scott Warren
+1  A: 
def ajaxRandom = {
    if(!request.xhr) { // this calls the dynamic method request.isXhr()
     redirect action: 'random'
    } else {
     def randomQuote = quoteService.getRandomQuote()
     response.outputStream << "<q>${randomQuote.content}</q><p>${randomQuote.author}</p>"
    }
}

This works because most of the Ajax JS Libraries add the X-Requested-With header to the request. Grails add this isXhr() method dynamically to the HttpServletRequest class.

// test whether the current request is an XHR request
HttpServletRequest.metaClass.isXhr = {->
     'XMLHttpRequest' == delegate.getHeader('X-Requested-With')                
}
Siegfried Puchbauer
This worked perfectly! Do you recommend any resources for more tips and tricks like this?
Wraith