act:ualise | technology

agile software development, software quality, scaling, testing and other tech

February 12, 2009
by j pimmel
0 comments

MockMe can JSUnit test your Prototype classes too!

Following my previous post I discovered a very helpful email in my inbox from Johannes Link, the author of MockMe, who provided an example of using MockMe to unit test my PrototypeJS classes.

One of the benefits of MockMe, vs JSMock or Jack, is it’s observance of the 3-A’s pattern (Arrange Act Assert), I quote:

  • Arrange is variable declaration and initialization.  
  • Act is invoking the code under test.  
  • Assert/verify that expectations were met.  

Both Jack and JSMock require expectations to be declared ahead of the ‘Act’, breaking the above pattern. This isn’t a ‘bad thing’, but reflecting on my long experience with EasyMock, it can lead to clutter in tests, reduce re-usability somewhat and can make tests more brittle and require more effort during refactorings. 

I have copied the same Prototype class code as for the previous example; once again we obviously need to include the mockMe.js file in our script declarations:

<script type="text/javascript" src="your-path-to/mockMe-version.js"></script>

Objects defined using Class.create:

var ContainedObject = Class.create({
	calcMaxMethodName: function() {
		return -1;
	},
	calcMinMethodName: function() {
		return -1;
	},
	getChildren: function() {
		return [];
	}
});

var ContainerObjectIMade = Class.create({
	initialize: function(containedObject) {
		this.delegate = containedObject;
	},
	doSomething: function() {
		return {
			"min": this.delegate.calcMinMethodName(),
			"max": this.delegate.calcMaxMethodName(),
			"children": this.delegate.getChildren()
		};
	}
});

Now for the test:

function testExample() {
	var mocker = new Mocker();
	mocker.mockClass(ContainedObject);

	when(ContainedObject.prototype.calcMaxMethodName)().thenReturn(100);
	when(ContainedObject.prototype.calcMinMethodName)().thenReturn(7);
	when(ContainedObject.prototype.getChildren)().thenReturn(2);

	var containerInstance = new ContainerObjectIMade(new ContainedObject());
	var json = containerInstance.doSomething();

	verify(once(), ContainedObject.prototype.calcMaxMethodName)();
	verify(once(), ContainedObject.prototype.calcMinMethodName)();
	verify(once(), ContainedObject.prototype.getChildren)();

	assertEquals(77, json.min);
	assertEquals(101, json.max);
	assertEquals(expectedArray, json.children);
}

As you can see, this approach is very concise indeed, thanks Johannes!

February 11, 2009
by j pimmel
0 comments

Hit the road Jack: OO Javascript testing made easy!

I’ve long been used to having decent testing frameworks in Java / Groovy / Grails however its taken me a while to stumble upon similar ways to test in Javascript. I tried my hand at using JSMock and then tried MockMe. They both seem very capable but I wanted something quick to test a class created using PrototypeJS‘s Class.create() method. Enter Jack to make it easy!

The example shown uses a mock instance passed to the instance of the containing class, which enables us to verify the functionality of that containing class.

We need to include the jack.js file in our script declarations:

<script type="text/javascript" src="your-path-to/jack.js"></script>

Objects defined using Class.create:

var ContainedObject = Class.create({
	calcMaxMethodName: function() {
		return -1;
	},
	calcMinMethodName: function() {
		return -1;
	},
	getChildren: function() {
		return [];
	}
});

var ContainerObjectIMade = Class.create({
	initialize: function(containedObject) {
		this.delegate = containedObject;
	},
	doSomething: function() {
		return {
			"min": this.delegate.calcMinMethodName(),
			"max": this.delegate.calcMaxMethodName(),
			"children": this.delegate.getChildren()
		};
	}
});

Now for the test:

function testExample() {
	jack(function(){
		var expectedArray = ['foo'];

		var mockObjectUnderTest = jack.create("objectNameKey",
			['calcMaxMethodName', 'calcMinMethodName', 'getChildren']);

		jack.expect("objectNameKey.calcMaxMethodName")
			.exactly("1 time")
			.returnValue(101);
		jack.expect("objectNameKey.calcMinMethodName")
			.exactly("1 time")
			.returnValue(77);
		jack.expect("objectNameKey.getChildren")
			.exactly("1 time")
			.returnValue(expectedArray);

		var containerInstance = new ContainerObjectIMade(mockObjectUnderTest);
		var json = containerInstance.doSomething();

		assertEquals(77, json.min);
		assertEquals(101, json.max);
		assertEquals(expectedArray, json.children);

	});
}

It couldn’t be easier to test your Javascript Objects!

February 10, 2009
by j pimmel
0 comments

Wired.com enlists Grails for new ‘Product Reviews’ site area

Grails gets centre stage for being used by Wired.com in it’s new ‘Product Reviews’ site area.  Needless to say, I was unsurprised by (and in full agreement with) the following statements in the release:

  • Our developers are much happier developing in Grails because they can accomplish tasks so much faster.
  • Grails makes it easier and saves time bringing new developers onto a project, because it provides a simpler, clearer, more intuitive development workfl ow and process
  • From a maintenance perspective, Grails simplifies debugging and reduces debugging time
  • Grails makes it much easier for Wired.com to test the Product Review application

And finally… in case it wasn’t clear enough… 

  • Grails makes it easier to focus on what we are trying to accomplish, in terms of business objectives, without having to think too much about all the wiring or boilerplate code typical of many Java based web applications.

January 28, 2009
by j pimmel
1 Comment

Agile; helping keep technical skills sharp?

Reading this question/answer on Stackoverflow I tangentially wondered whether working to Agile practices played any greater a role in my technical skills development compared to ‘back in the day‘ when I wasn’t using Agile methods.

There ought to be no difference in technical skills development whether the context is Agile or any other process – indeed for most it’s likely to be nothing to do with process at all.

Whilst that may be true, I would suggest that some Agile processes have definitely played a unique role in my own skills development, specifically:

  • Pair programming
    • Working together you learn countless ‘new tricks’ from colleagues, whether those are new APIs or ways of doing things
    • Working together you pare down more and keep things more DRY. Less really means more
  • TFD
    • Improves ones ability to break down larger more complex problems
  • Story Card Iterations
    • Keeps your work focused and reduces YAGNIs creeping in

So while specific technical skills or interests obviously relate to what you are creating, Agile can definately play a role in breeding a good development habit – the caveat being that employing Agile needs competent leadership for the above to flourish at it’s best.

January 22, 2009
by j pimmel
0 comments

Making your Selenium XPath tests more resilient

For the past few years myself and colleagues have used Selenium extensively to test-drive (and continuously test) all the web-apps which we’ve collectively been responsible for. In that time our massed experience meant we got pretty slick at writing these tests. Then when I started on a new project with a new team, I realised those tips/best practices hadn’t been documented and consequently saw developers new to Selenium introducing brittle tests through no fault of their own. 

Here’s a quick rundown of the most useful things we learnt about Selenium Test Xpaths. Please feel free to comment and add your own tips too!

  • Assuming you are following best practices for CSS styling you ought to already be using IDs and CLASS attributes in markup. If not, why not!?
  • Write XPaths which focus on the ‘pivots’ in a deeply nested XPath; where possible use ID and CLASS (and/or other relevant attributes) to filter down to your target element(s).So where previously you might have had:

    xpath=/div[0]/div[3]/div[6]/span[2]

    You could instead use:

    xpath=//div[@class="foo"]//span[@id="pageTitle"]
  • Test that attributes exist or have the right value, rather than testing text content in pages (especially where that content is dynamic)

    So for example, test that button ID x is in page, and click by the xpath of the button ID, rather than using the Selenium IDE recorded click ‘{text button visual name}’ method.

    Another example might be locating that a A HREF link is going to the right place

    Assert

    xpath=//div[@id="profile"]//a[@class="modifyProfile"]/@href

    is ‘/someLink’

  • For links (or src URL locations) employ regex or globs rather than test FQNs

    Assert that

    xpath=//div[@id="profile"]//a[@class="modifyProfile"]/@href

    is ‘glob:*/deepNestedContext/mofiyProfile.action’

  • A corollary from my opening point; make sure all markup is W3C valid. Helps to avoid shooting yourself in the foot using xpaths (ie: duplicate IDs)
  • Employ selenium extensions to compress repetitious, multi step / test activities into a single test action
  • When iterating over listed content, avoid index based xpaths – dynamic changes could cause failures. Try where possible to specify a search form of xpath

    eg: instead of asserting that

    xpath=//div[0]/span[1]/ul/li[3] is 'bob'

    its far less brittle to write

    xpath=//div[@id="mainContent"]//ul[@id="userList"]/li[text() == 'bob']

    In cases where list order is important then using the list index is of value, but often it can cause more trouble than it’s worth to use indexes.

  • Use storeExpression to store and re-use Xpaths which are repeated often in a test (the benefit being when you do have to change the Xpath you change one place not 15)
  • Use the Selenium IDE in record mode more as a guide than as an absolute way to build up tests; IDE xpaths are inflexible and can’t handle changes as well as xpaths defined with resilience in mind
  • Lastly, but not least, remember IE compatibility for your Selenium RC tests

January 22, 2009
by j pimmel
0 comments

Morning market..

Whilst this article is clearly specific to Lean in manufacturing processes what I find pleasing is how fundamentally similar a ‘Morning Market’ is to the morning Scrum in software development.

  • Its a short morning meeting
  • It’s not a forum to attempt to solve problems or to discuss them in detail, but a place to surface them
  • Where problems are raised, time in the working day is dedicated to solving them

An adornment they made to ensure this process worked more effectively for them on the factory floor was to use a cheap Karaoke machine as a PA, which had benefits in keeping attention on a specific speaker given that a large number of people were in attendance.

Also off the newswires this week came a mention of another manufacturing company using Lean which Obama appears to be fond of.

January 15, 2009
by j pimmel
8 Comments

Open Flash Chart 101: Make it %#$@!?* work

I have recently been attempting to get my head around Open Flash Chart to, at the very least, get an equivalent ‘Hello World’ version running before I run off customising it. Should be simple right? Well yes, once you get around a real showstopping gotcha which isn’t documented out there.

The starting point, this tutorial example. As you can see, everything is well with that example. Following my usual logic, I downloaded the following relevant page items

  • json2.js
  • swfobject.js
  • open-flash-chart.swf

I created a local HTML into which I copy pasted the pertintent source from the tutorial example, changing script and page references to use same directory for the three page items above. I fully qualified the JSON data url to {“data-file” :  ”http://teethgrinder.co.uk/open-flash-chart-2/gallery/tooltip.php” } - cross site yes, but its just JSON data right?

On loading the chart into my browser offf the filesystem I didn’t get the chart expected, instead I got what is pictured below

Open Flash Chart loaded from Local HTML

Using Firebug reveals some interesting things – yes the JS files are there and loading. Given that the spinning thing is in fact the SWF file loaded into the browser that has to have loaded too and it’s running too.. well, sort of. So why no graph?

Make my data local?

Fair enough I thought, perhaps its some cross-site thing after all. I made the JSON data that is handed to the SWF local to the page; embedding JSON data in page for the graph is shown by example here and making that change was easy. But once again no joy.

Make my data served?

I couldn’t see why, but maybe serving the content over HTTP would do something for me. Taking all the same resources and uploading them to the server here was what finally delivered a working chart example of my own making, reading the JSON data from inside it’s own page.

But why?

Assuming you have visited the above links, you will have noted the alerts which come up when the browser SWF successfully drawing a graph. I reasoned that maybe a local page load wasn’t firing the Javascript onLoad event? A quick local page test of

<body onLoad="alert('hello world!')">

proved me wrong.

Just don’t cross-site the content

What is clear is that no working charts I have found make references to any SWF/JS/JSON data resources which are outside of the same domain. Thats perhaps logical, but you might also like to be notified as such – at present OFC gives you no indication, not even a hint, that you have this problem. The only instance where you get a sniff of this is revealed in Firebug when visiting this version of the chart I am serving.

Coming up short

Sadly I dont have the answer to why the chart fails to draw when you attempt to run it locally from files vs when it is served up.

I know that the SWF is executing some ActionScript which is doing the magic somewhere which ultimately leads to the invocation of the Javascript ‘ofc_ready’ method. Its not clear how those bindings are different when loaded locally vs when served, but this problem could also easily be masked by cross-site complexities. Its seems pretty evident that the browser is triggering an event in the loaded SWF plugin in one instance but not the other.

If anyone has any deeper knowledge or thoughts as to why it would be good to know the details – please feel free to comment!

UPDATE (30th March 2009): We recently found out how to toggle local loading. The reason it doesn’t comes down to flash player sandboxing

Add permission for SWF files (woot!)

January 2, 2009
by j pimmel
0 comments

Unit performance testing tactics

In my previous article on performance testing, I suggested that incremental and iterative development of performance unit tests was an essential part of your overall performance testing strategy. However, performance testing the parts of a system is vastly different from testing the whole and will require some careful thinking to avoid too much focus on the small things. Since we’re not in the habit of doing this, how to begin grappling with this?

Side-door tests

I had never heard of side-door tests until I watched a presentation given by Jonathan Kohl @ Agile Vancouver 2008. His extremely hands-on approach to his QA test role fascinated me. He reviewed developer’s code frequently and aggressively; good stuff. He wrote code to test the developers code; now that was quite novel indeed.

He spoke of how he was stuck trying to recreate a problem; a query in the database was causing a locking issue when under load. His testing record/playback tool was itself not powerful enough to generate comparable loads on the test server; even if it could his test server was a poor mans version of live, nowhere near as performing. Enter the side-door test:

Side-door test

Employing a test to generate concurrent load on the service method executing the suspect query reproduced the locking problem. The test was left in place after to verify the problem was fixed. This seemed like a perfectly sensible way to fix problems, however it recently occurred to me that this could serve as a viable approach to implement a unit performance testing suite.

Some examples might be:

  • Determine total logins per second for LoginService
  • Determine total new registrations per second for RegistrationService
  • Determine max concurrent trades per second for TradeService
  • Determine total contending logins and registrations in 10 seconds for LoginController and RegistrationController

Developers can write these tests as either unit/integration tests in the traditional sense executed locally, or additionally as tests executed within the VM of a deployed application dedicated to performance testing.

Using focused tests a developer can more methodically ‘tune-backwards‘, identifying Tier and Technical Wait-points for saturation testing and the subsequent tuning to be made.

Early visibility and growing value

In the same way that the network effect of a growing suite of unit and integration tests leads to increasing confidence in functionality, an ever expanding suite of unit performance tests increases confidence in the performance of code.

At the inception of the project unit performance tests merely record timings on each new check-in: a history of select performance characteristics (saturation point, max concurrency, throughput, even contention) per functional area is collected. Then at some point in time the test may transition from recording to triggering a failure where a performance threshold is exceeded – precisely when this transition should occur is hard to say. It might make sense to do so when the record/playback version of a test which exercises the same code is automated.

Whatever the case, setting performance thresholds is not the end-game of unit performance testing. What’s important is ownership by developers, product owner and QAs to qualify the performance criteria which are to be met and understanding the required instrumentation for collecting the right breadth and depth of data vital for later analyses. Investing development teams in performance testing is key to ensuring that performance test automation is not discontinued.

Another effect ought to be that effort-intensive, record/playback test automation can be keenly focused on the highest value aspects of a system – the preceding process of identifying performance criteria during unit performance testing in fact provides a roadmap which can be followed to this end.