Tag Archives: testing

Two futures of software testing

Michael Bolton won an award for his talk on two futures of software testing. The message of it is in essence for testers to focus on the needs of the business instead of the plan. Even though it’s a presentation it has lots of notes and a lot of nice stuff there that turns testers to being more agile. Check it out.

Agility in operations

It seems like Facebok is pretty agile in how it handles new features and roll outs. According to an article on the High Scalability site they actually do major releases every week. One of the things that struck me was this:

Be Innovative, Not Safe. Fear of failure often shuts down the organizational brain and makes it hide behind excessive rules and regulations. A technology company should have a bias towards action and innovation. Release software. Don’t stifle genius. Rely on your tools and processes to recover from problems.

This isn’t a solution to problems, but it is a pretty accurate description of what I want to achieve myself. Making a release shouldn’t be difficult or scary. This means that we need tools and methods that:

  • Enables us to be relatively certain that we don’t introduce any errors
  • Enables us to recover from a failure, because we will eventually fail

Tools like JUnit, Fitnesse, Selenium are all tools that allow us to verify the behaviour of our application. They help us verify that what we have done doesn’t introduce any errors. This should enable us to roll out quite easily, but I think in many projects one doesn’t trust the quality of the tests and you fear rolling out because you don’t have a good recovery plan.

I think we have a lot of tools available to us when it comes to writing tests, we just have to get better at using them, and eventually improving the tools. Where we seem to be missing is the part where we do good rollbacks. Maybe we don’t even need tools for that? I’d like to hear how you do it, and what tools you use or are missing.

Swimlane testing at Eclipse

Found some really interesting stuff about automated testing with a tool they’ve dubbed Swim. It basically uses the tests as online documentation. By abstracting actions to the correct level, and supplying generated screenshots every step of the way, tests can be verified and used as documentation. Through Ole Mortens blog. Check out Jon Udells entry for an explanation.

Integration, development and stubs

In my current project we have a fair bit of integration. Loose coupling and all that is excellent, but it does create some challenges:

  • Integrating systems are only available inside the firewall. Sometimes it is relevant to test and develop outside our normal network.
  • Different integrating systems have different availability. You can’t rely on all of them beeing available all the time.

To overcome these we want to be able to stub the integrating systems. But introducing stubs also leads to some complications:

  • The test team needs to be able to check which systems are stubbed and which systems have real integration when testing.
  • The test team will need different configurations at different times, and I’m too lazy to package 20 installations. 😉

So what I need is:

  • A webinterface to display the status of the integration points (stub or real implementation)
  • A webinterface to change which points are stubbed or not

The solution

Since we are using Spring all the wiring and configuration is stored in XML files, and I could probably manipulate files on the disk, but it didn’t sound like an attractive solution. After asking a bit around at the java.no forum I settled on a proxy based solution in the spirit of Spring’s LocalStatelessSessionProxyFactoryBean. Implementation was easy enough, and it seems to work. In it’s essence it is a proxy and a proxyfactory wrapped in one class (FactoryBean and MethodInterceptor is implemented) that handles which class will be invoked (stub/real).

It also has some shortcomings that you should be aware of:

  • No security as to who can use it
  • It is not tested with proxies inside the proxy, but I guess that will work.
  • You should probably restart your app before making config changes. Any state in the beans real/stub will be missing when switching.

The config

The config should be pretty self explanatory with two beans, one interface and one boolean injected into the ProxyFactory. The stubEnabled boolean could be omitted. It defaults to running the real implementation.


  
    MyService
  
  
    
  
  
    
  
  
    true
  

The proxy

The proxy is the object that sits around the real and stub implementations. It will direct the execution to the correct bean depending on it’s settings.

The signature looks like this (the larger methods impls is further down):

public class IntegrationPointProxyFactoryBean implements FactoryBean, MethodInterceptor, InitializingBean {
	/* Required interface methods. See Spring docs for info. */
	public Object getObject() {
		return this.proxy;
	}
	public boolean isSingleton() {
		return false;
	}
	public Class getObjectType() {
		if (this.proxy == null) {
			return this.businessInterface;
		} else {
			return this.proxy.getClass();
		}
	}
	public Object invoke(MethodInvocation invocation) throws SecurityException, NoSuchMethodException, IllegalArgumentException, IllegalAccessException, InvocationTargetException;
	public void afterPropertiesSet();

	/* New methods specific for this bean */
	public void setBusinessInterface(Class businessInterface);
	public void setRealImplementation(Object realImplementation);
	public void setStubImplementation(Object stubImplementation);
	public void setStubEnabled(boolean stubEnabled);
}

The set* methods are just plain old dependency injection methods that sets a class variable, I won’t write about them. To make the solution better you might want to do some before/after consistency checks in them. The interesting stuff happens in the afterPropertiesSet and invoke methods.

afterPropertiesSet

public void afterPropertiesSet() {
	/* A bunch of consistency checks for null etc */

	// Initialise the proxyobject which is this object
	this.proxy = ProxyFactory.getProxy(this.businessInterface, this);
}

Thats pretty much all you need to do to create a proxy with Springs utilities. The object you are assigning as the proxy must implement the MethodInterceptor interface.

That was the config, the rest of the stuff happens runtime in the invoke method.

invoke

public Object invoke(MethodInvocation invocation) throws SecurityException, NoSuchMethodException, IllegalArgumentException, IllegalAccessException, InvocationTargetException {
	Method aopMethod = invocation.getMethod();
	Object runObject = null;
	if (this.stubEnabled) {
		runObject = this.stubImplementation;
	} else {
		runObject = this.realImplementation;
	}
	Method classInvocation = runObject.getClass().getMethod(aopMethod.getName(), aopMethod.getParameterTypes());

	return classInvocation.invoke(runObject, invocation.getArguments());
}

The controller

This is all nice and dandy, but it won’t do you much good if you don’t have something to control and display this behaviour. You need a controller doing the following:

  • Retrieve all beans of type IntegrationProxtFactoryBean and pass them to the JSP
  • If enabled, switch implementation between real and stub

IntegrationPointController

public class IntegrationPointController extends AbstractController {
	protected ModelAndView handleRequestInternal(HttpServletRequest request, HttpServletResponse response) {
		Map beans = this.getApplicationContext().getBeansOfType(IntegrationPointProxyFactoryBean.class);

		// Switch implementasjon
		if (request.getParameter("point") != null) {
			String pointName = request.getParameter("point");
			IntegrationPointProxyFactoryBean pointBean = (IntegrationPointProxyFactoryBean) beans.get(pointName);
			pointBean.setStubEnabled(!pointBean.isStubEnabled());
		}

		Map model = new HashMap();
		model.put("points", beans);

		return new ModelAndView("config/showPoints", model);
	}
}

And the JSP is something like this (not the prettiest code, but this is just util stuff anyway):


  
Name:
Real:
Stub:
[ ">Switch]

This is the first time I try to do such an extensive article, I hope it turned out alright. Let me know if you think otherwise. 🙂