Saturday, September 10, 2011

Make your ASP.NET Page Methods Secure

One of the most persistent misconceptions about ASP.NET’s page methods is the notion that they have some intrinsic protection against requests that don’t originate from the page where they’re defined. Since a page method’s code resides within a page’s code-behind file, it’s intuitive to assume that those methods benefit from some form of inherent security.

Unfortunately, that is not the case

Exploiting your page’s insecurities

In case it’s hard to believe these code-behind methods truly are so easily accessible, let’s take a look at a quick example. Let’s say you have a page method that returns sensitive business information, like so:
 
[WebMethod]
public static int SecretFormula() {
  return 42;
}

Assuming that method is defined in a Default.aspx file’s code-behind, located in a folder named TopSecret, here’s a bit of jQuery you could use to request the secret formula from any page on the site:
 
$.ajax({
  url: '/TopSecret/Default.aspx/SecretFormula',
  type: 'POST',
  contentType: 'application/json',
  data: '{}',
  success: function(result) {
    alert(result.d);
  }
});

In fact, you can even make that request from a plain HTML file. In this example, I’m making the request right from a simple HTML file named index.htm:



Not only is the request not originating from the ASPX file that contains the page method, that request wasn’t originating from an ASPX file at all!

Is this really a problem?

You might be asking yourself if this is really a problem to begin with. After all, you aren’t very likely to write client-side code that requests sensitive data unless you actually need that data, regardless of whether you write that code on an ASPX page, HTML page, or anywhere else.
The trouble is, a villain could land on any of your site’s pages, open up Firebug, and start probing for weaknesses like this one. In this case, the obscurity of the exact location of the page method might lead you to a false sense of security, but if an attacker has any knowledge of your system’s architecture then the door is wide open.
Even more troubling, as long as an attacker uses POST requests with an application/json Content-Type, they could use a tool as simple as Fiddler to interrogate your site’s services remotely. A few lines of server-side code, and your competition could set up a site driven by the page method APIs on your site that you thought were private!

A fixable problem

Page methods aren’t indefensible against the shenanigans of external interlopers though. You can secure them with ASP.NET’s built-in authorization mechanism, just as you would any other ASPX page (or ASMX service). In fact, if you secure an ASPX page with ASP.NET authorization, page methods defined in its code-behind are automatically equally secure.

To deny unauthenticated access to methods in our TopSecret folder, adding an authorization entry to the web.config in that folder is all that’s necessary:

<?xml version="1.0"?>
<configuration>
<system.web>
<authorization>
<deny users="?" />

</authorization>
</system.web>
</configuration>

Now, an unauthenticated user trying to access the SecretFormula method from index.htm (or anywhere else, without authenticating first) is denied access:


Attempting to request the same page method with jQuery after securing it.

Of course, there are a variety of ways to control access to these methods. You might test to see which role a user’s in and respond accordingly, or you might only need to verify some token stored in the Session.
Regardless of the particular mechanism, the key is to remember that none of this is automatic and that you must be mindful of regulating access to your page methods.

Reference: Encosia.