Another ASP.NET MVC custom ActionResult example

If you’re familiar with ASP.NET MVC this is probably not news to you. If you’re coming from Webforms, you might find this tip helpful.

One of my favorite things about MVC is how easy it is to build custom ActionResults. I previously wrote about building one for returning RSS feeds and this post expands on that idea a little bit.

When I originally set up the ManagedAssembly.com RSS feeds, I added some caching so that the feed would only be generated every 30 minutes resulting in a snapshot of the current set of popular stories. Unfortunately since I hosted the feeds directly, I have very little useful info about how much they’re being used. FeedBurner (when it works) is much better at that so I wanted to switch the feeds over to that but without changing the URLs so I don’t break any existing subscriptions. I had recently read in a post to Twitter by Scott Watermasyk that Graffiti CMS supports FeedBurner by sniffing the user agent and serving the live feed to FeedBurner but at the same URL, redirects real visitors to FeedBurner. This was the perfect solution to my problem, so here’s how I went about implementing it.

First I added a PermanentRedirectResult class that inherits from ActionResult to handle generating the 301 redirect. The built-in RedirectResult uses Response.Redirect which only is capable of issuing a 302 redirect (until ASP.NET 4.0 is out).

public class PermanentRedirectResult : ActionResult
{
    private string _url;
 
    public PermanentRedirectResult(string url) {
        _url = url;
    }
 
    public override void ExecuteResult(ControllerContext context) {
        context.HttpContext.Response.StatusCode = 301;
        context.HttpContext.Response.RedirectLocation = _url;
    }
}

Then in my ControllerBase class that all my controllers inherit from, I added a helper method to simplify calling the result:

public abstract class ControllerBase : Controller
{
    public PermanentRedirectResult PermanentRedirect(string url) {
        return new PermanentRedirectResult(url);
    }
}

Then in the action method I do a simple check for FeedBurner and if it’s not found, issue the redirect. Otherwise return the live feed.

public ActionResult Popular() {
    bool isBot = Request.UserAgent.Contains("FeedBurner");
 
    if (!isBot) {
        return PermanentRedirect(Settings.Feed.PopularFeedUrl);
    }
 
    // *snip* build and return live feed
}

Nice and straightforward and doesn’t break any existing subscriptions. Now with FeedBurner’s stats I can tell exactly how few of you are subscribing to the feed :)

Posted July 14th, 10:43 PM
Read more posts about ASP.NET MVC, Managed Assembly, Tips.

View Comments
Link

I won a contest!

I’m proud to announce that I was this week’s winner of the Twilio Developer Contest. I submitted my SimpleHotline project which I have previously blogged about. For the effort I will be receiving a Dell Vostro A90N netbook. I would say this even if I hadn’t won, but Twilio is a great service with a simple API and payment structure. If you’re building an app that needs to take or make phone calls, give Twilio a shot.

Thanks Twilio!

Posted July 6th, 10:29 PM
Read more posts about Life.

View Comments
Link

The Killer Twitter App Hasn’t Been Built Yet

Imagine an application that acts as a super proxy for your Twitter account. The server acts as the client, pulling updates from the API. Updates are relayed to your iPhone and desktop clients in near real-time1 with XMPP. No more multi-device API limitations getting in your way. Add in analytics, trends (specific to your follow list), link harvesting, groups, searches, filtering and more automatically sync’d to all your devices.

Why doesn’t this exist? This should be what Twitter itself does, but I can’t see them suddenly going in this direction. Build it and you can have my money.

[1] As in, as fast as it can be delivered once it is retrieved from the API. Not real-time to the initial update.

Posted July 1st, 9:51 PM
Read more posts about Thoughts.

View Comments
Link

My Projects

ManagedAssembly

RestSharp

jQuery Snippets for Visual Studio 2010

@dotnetlinks on Twitter

SnapLeague