Integrating security into QA testing

I wrote about this some time ago.

Fortify are now doing a webinar on this topic.

Security Testing with Watij

Watij is a tool designed for functional web testing. It’s effectively a Java API which drives an instance of Internet Explorer. You can then use your favourite unit testing framework to structure tests and make assertions of the results. Like similar functional testing tools, watij can be used to script security defects in web applications. This is inline with good security and development practice of writing abuse cases and specifically testing for failure conditions rather than only testing for success conditions.I wrote a paper (pdf) on using functional testing tools in this way, some time ago, and since then I’ve been having a look at the various tools to find one most suitable for security testing. Today, I whipped up some simple tests of the owasp.org website using Watij. It was easy to install and be up and running in Eclipse in a few minutes. Before starting on the tests, I wanted to define common functions, such as login and logout:
 
 
public static void login(String username, String password) throws Exception {
	ie.navigate(“https://www.owasp.org/index.php?title=Special:Userlogin&returnto=Main_Page”);
	ie.textField(name,“wpName”).set(username);
	ie.textField(name,“wpPassword”).set(password);
	ie.button(name, “wpLoginattempt”).click();
}
	
public static void logout() throws Exception {
	ie.navigate(“https://www.owasp.org/index.php?title=Special:Userlogout&returnto=Special:Userlogin”);
}
 
 
As you can see the syntax and API is quite intuitive. Now that these are defined, time to write the startup code for the tests - using JUnit 4 this is run only once for the whole test case:
 
 
//Run only once to initialise the browser
@BeforeClass
public static void init() throws Exception {
	ie = new IE();
	ie.start(“https://www.owasp.org/index.php/Main_Page”);
	if (ie.containsText(“There is a problem with this website’s security certificate”)) {
		ie.link(name,“overridelink”).click();			
	}
	if (!ie.url().equals(“https://www.owasp.org/index.php/Main_Page”)) throw new RuntimeException(“Error getting to the front page!”);
	webapp = new WebApp(ie);
}
And finally, we can write the tests which should be self explanatory:
 
@Test
public void testLoginLogout() throws Exception {
	webapp.login(username, password);
	assertTrue(“Logged in.”, ie.containsText(“You are now logged in”));
	webapp.logout();
	assertTrue(“Logged out.”, ie.containsText(“You are now logged out”));
}
 
@Test
public void testUserEnumeration() throws Exception {
	webapp.login(“notauser”,“test”);
	if (ie.containsText(“There is no user by the name”)) {
		fail(“Usernames can be enumerated through the login error messages”);
	}
}
 
@Test
public void testBruteForce() throws Exception {
	int count=5;
	for (int i=0;i<count;i++) {
	webapp.login(username,“wrongpassword”);
	}
	webapp.login(username,password);
	if (ie.containsText(“You are now logged in”)) {
		fail(“After “+count+” incorrect login attempts, the user could still login.  This exposes the accounts to brute force attacks.”);
		webapp.logout();
	}	
}
 
Here’s a video of the result:

Quite slick. But say I’d like to test whether a user who’s not logged in can post articles to the wiki. Well the “Edit” page is only displayed when you are logged in, so there’s no way I can click on a non-existent link. And just because the link isn’t there doesn’t necessarily mean that the server won’t accept the request. So what we need to do is perform the POST request to submit an article to the wiki directly and this is where watij stumbles. There’s no easy way to create an arbitrary POST request. The recommended approach is to use something like HTTPUnit or HtmlUnit to perform this specific test. Ok, no problem, so I can just use the login function I’ve already defined in the watij tests, then read the session cookie and pass the cookie onto an HTTPunit test, right? Wrong. You can’t read IE cookies from the watij API! So the only option is to re-code the login function in HttpUnit and use that instead. Lots of code duplication and now I’m mixing two different testing frameworks, not ideal.

To summarise the issues with using watij to test security:

On the plus side, the JavaScript support is as good as it’s gonna get so you’d very very rarely run into a web application which doesn’t support IE.

On the whole, I can see the attraction for using watij to positively test functionality - but because of the reasons above, I don’t think it’s the best choice for performing negative testing (i.e. test what’s not there). I hope to write a similar entry about Canoo’s WebTest, which provides similar testing functionality, but using XML tests and it’s own HTTP and Html engines.

Defining security requirements

The vast majority of security assessments I’ve worked on have used “best practice” to define the security requirements of the application under test. Clients are content to rely on security assessment firms to decide what should and shouldn’t be tested, and this is usually OK for bug hunting.  But apart from the well known bugs which constitute security vulnerabilities there is an often overlooked class of security issues:  lack of, or poorly implemented security features, such as:These are not bugs as such, but they do pose a risk to the security of the application - and they are completely preventable, if they had simply been defined as requirements right at the start of the project!  The closest definition there is to a generic set of security requirements for web applications is the OWASP Guide to Building Secure Web Applications, and it’s a good basis to start defining your own set of security standards.  Because one size definitely does not fit all.  Security requirements should define both how your application should behave (security use cases) and also how it should not behave (abuse cases).  Since these will be protecting the business from risk, they should be considered first class business requirements.  Now, instead of shooting in the dark, the architects and developers will have a clear idea of how the application should behave from a security perspective.  When it comes to the testing phase, testing of the security features can be a part of the normal unit, integration and acceptance testing.  This means that the traditional penetration test performed at the end of the project should uncover fewer surprises - and importantly fewer security issues which require major application redesign.  Additionally, the penetration testers should be using the security requirements as the standard by which to judge the application.  Want even more bang for you buck?  How about inserting the security requirements document as a standard part of agreements with third party developers and other software suppliers?  These can be bound to legal contracts and SLAs so that you don’t end up footing the bill for someone else’s poor security!