One of the most impressive talks for me at WWDC 2010 was session 306 - "Automating Use Interface Testing with Instruments". I've been wanting to check it out ever since iOS 4 was released. A couple of weeks ago, I finally had a chance to give it a test ride with "I think I spider", one of the Apps I developed.
All you need to get started is an App, Instruments and some basic JavaScript skills. Apple provides a set of JavaScript libraries, that you can use to drive your tests and simulate user interaction. Your custom test scripts are run using the Automation Instrument in Apple's Instruments App, targeting your App either in the Simulator or on an actual device.
You can test almost every aspect of user interaction, using Apple's JavaScript library. No matter if you want to test shaking, device orientation or the basics like tapping and swiping, you can do all that using basic JavaScript function calls. Apple's documentation is quite solid, as most of them are, and explains the process in detail.
For "I think I spider" I covered the basic use cases in terms of UI, to make sure it still works after adding new features. Here is a basic example of the JavaScript involved to test "opening" the book, after starting the App:
You can see that the JavaScript API is quite easy to use and yet very powerful! After setting this up in the Automation Instrument and running it, you can see the Simulator firing up and tapping the UIImageView with the accessibility label "startscreen" after it became available. It then tests, if the main screen of the App was loaded and either passes or fails the test.
In order to make our App testable, I had to set the accessibility labels on the elements we wanted to reference from the script. That was the only change I had to make in our code. Since you should take accessibility into consideration anyways, it was a reasonable effort.
Apple did an awesome job giving us developers the ability to catch regressions and make our life easier. However, there is room for improvement, which has been nicely summarized by Air Source. For us, a missing UIALogger.warn function in the JavaScript library was the biggest downside. Sometimes it's okay for a test to fail under certain conditions, but you still want to get a warning about it. I use UIALogger.logMessage for those cases as a workaround, but it's quite easy to miss those lines, since they don't stand out.
Overall, I think it's a huge improvement to have a UI testing tool for iOS Apps at hand. There is room for improvement, but the current state of UI Test Automation is already priceless!
{ by david linsin }
Showing posts with label testing. Show all posts
Showing posts with label testing. Show all posts
January 31, 2011
June 30, 2010
UI Prototyping iPhone Apps
I'm writing for the Synyx GmbH & Co. KG mobile solutions blog. From time to time, I'll cross post articles here, if I think they are of interest for you. If you'd like to read all of my other posts, subscribe to the Synyx Mobile Solutions Blog.Before flying off to WWDC last month, I watched a whole bunch of sessions from 2009. Among others a session on "Prototyping iPhone User Interfaces" by Bret Victor. If you haven't watched it and you've got access to the WWDC videos - stop right here and watch the video!
In his session, Bret shows how to prototype an interface only by interacting with screenshots! It's amazing that a simple screenshot on the device can show you so much more than by just looking at it in a document or print out. It inspired me to use his framework and the whole process for our own development.
Unfortunately, the code for the session isn't available and neither Bret nor the frameworks evangelist, mentioned in the presentation, got back to me about the code. After some digging, I found Michael Fey's blog, who was able to successfully reverse engineer the missing parts of source code, which were not shown in the presentation.
Michael's UIViewAdditions basically allow easy access to frame properties and give you a neat init method, which adds the passed UIView as a parent:
There wasn't much left to do for me. I only coded the class Root, which is the parent of all UIImageView instances. It provides a couple of methods to slide images back and forth:
With those two classes and a couple of screenshots, it is fairly easy to create an App that looks and feels almost real. I created a short demo video, which shows how easy it is to get a good feeling if your App is going to work or not:
Now don't forget those are only screenshots and the App might need to load stuff over the network or do some animation, hence it might not feel the same. However, this process of prototyping an UI is powerful enough to give you an idea, whether the workflow or the UI in general is going to "work" or needs some tweaking.
You can download the source code for the two classes, along with a sample project from github.
April 16, 2010
iPhone App Beta Testing
Last year I was working on a Nine Men's Morris mobile game called Doublemill. My job was to implement a REST-based server back-end on the Google App Engine. You might remember a couple of posts on that. My colleagues were responsible for coding the Android client. Since I'm an iPhone user and I'm not going to switch to Android anytime soon, I decided to port the game to the iPhone/iPod touch platform.I'm closing in on the first release of the paid version of Doublemill. The only thing missing is a beta test. I'm past the technical problems, which I encountered when I released a beta version of Doublemill Lite a couple of weeks ago. This is more about how to find people, willing to thoroughly and extensively test your App.
Unfortunately, I can't use Amazon's Mechanical Turk - although I'm willing to pay a small amount for people to find bugs in my App. Amazon doesn't let me use it without a US credit card, so I had to look for an alternative. I came accross iBetaTest.com. I used it for Doublemill Lite and I'm also using it for the paid version. Although the site has little flaws (it's still in beta itself), the idea is great and it works pretty well. However, there is still a problem: the people who are using the site and who are supposed to test your App.
After I added the beta for Doublemill, I received a lot of requests, mostly from testers which are not testing any other Apps or look like they have just signed up. I gave a couple of them the benefit of the doubt and let them in, only to experience, that I wasted my valuable device IDs.
At the time this blog was published, I have only received feedback from 2 of my 7 testers. The other just haven't replied. I know, that at least one has downloaded and signed up for the multiplayer feature, but hasn't provided feedback on any aspect of the App. That's just plain disappointing. After Doublemill Lite, this is the second time I wasted device IDs, it won't happen to me anymore.
After all, there's always something to learn from your mistakes: be picky on beta testers and choose people you know they'll give you valuable, honest and thorough feedback! It takes quite some time to setup a beta test and organize all device IDs, so don't neglect Q&A in your project planning.
I'm fortunate enough to have a couple of people around me, which help out with testing and give me exactly the feedback I need - although it's not always what I want to hear.
November 02, 2009
Having Fun with JDK's tools.jar
This week I had to trace a bug in a legacy application, I'm maintaining at the moment, which drove me up the wall. The application uses a class from JDK's tools.jar, to determine the JVM instances currently running. Unfortunately, there are incompatibilities between JDK versions.
Tracking down the bug took a humongous amount of time, because the fun part of working on a legacy application is that all the developers, which are responsible for the code you are maintaining, are usually no longer available. Don't even get me started on documentation! However, as a good developer, I created the following JUnit test, to isolate the problem from the rest of the code.
If you run this test with Sun's JRE 1.6 and tools.jar of Sun's JDK 1.6 on the classpath, you won't encounter an problems. However, with my current project, we need backward compatibility with other Java versions. That means, there are multiple tools.jar on the classpath, in different versions. Depending on their order, the test above fails or succeeds.
More precisely, there is a JDK 1.4 and 1.5 version of tools.jar on the classpath, in addition to the 1.6 version. 1.6 is needed, because in previous JDKs the class VirtualMachine doesn't reside in the package com.sun.tools.attach. So running the test without tools.jar in version 1.6, you'll get a NoClassDefFoundError.
So what's the problem you might ask? As long as tools.jar of JDK 1.6 is on the classpath, when running the aforementioned test, everything should be okay, right? It should be, but it isn't. As soon as tools.jar of JDK 1.5 is before the 1.6 version on the runtime classpath, the test fails. Every other combination works just fine.
Why tools.jar of JDK 1.5 causes this problem is a mystery to me. Sun's bug parade, doesn't contain any relevant information - at least I couldn't find any. Frankly, I think this problem is so absurd, that I cannot motivate myself getting to the bottom of it.
Nevertheless, the problem exists in our application and we'll have to find a solution. I guess that's the reason why it's a legacy application - I have to deal with problems that are totally outdated and nobody knows the answer to.
Tracking down the bug took a humongous amount of time, because the fun part of working on a legacy application is that all the developers, which are responsible for the code you are maintaining, are usually no longer available. Don't even get me started on documentation! However, as a good developer, I created the following JUnit test, to isolate the problem from the rest of the code.
If you run this test with Sun's JRE 1.6 and tools.jar of Sun's JDK 1.6 on the classpath, you won't encounter an problems. However, with my current project, we need backward compatibility with other Java versions. That means, there are multiple tools.jar on the classpath, in different versions. Depending on their order, the test above fails or succeeds.
More precisely, there is a JDK 1.4 and 1.5 version of tools.jar on the classpath, in addition to the 1.6 version. 1.6 is needed, because in previous JDKs the class VirtualMachine doesn't reside in the package com.sun.tools.attach. So running the test without tools.jar in version 1.6, you'll get a NoClassDefFoundError.
So what's the problem you might ask? As long as tools.jar of JDK 1.6 is on the classpath, when running the aforementioned test, everything should be okay, right? It should be, but it isn't. As soon as tools.jar of JDK 1.5 is before the 1.6 version on the runtime classpath, the test fails. Every other combination works just fine.
Why tools.jar of JDK 1.5 causes this problem is a mystery to me. Sun's bug parade, doesn't contain any relevant information - at least I couldn't find any. Frankly, I think this problem is so absurd, that I cannot motivate myself getting to the bottom of it.
Nevertheless, the problem exists in our application and we'll have to find a solution. I guess that's the reason why it's a legacy application - I have to deal with problems that are totally outdated and nobody knows the answer to.
April 27, 2009
Using Reflection in Unit Tests II
A couple of days ago, I blogged about the pros and cons of using Reflection in unit tests. Thanks to Samuel, who gave me a pointer to "PowerMock", I don't have to deal with the Reflection API anymore.
To be more precise, PowerMock takes away the annoyance of dealing with the Reflection API. In case of the example presented in my previous post, instead of this code:
you simply write this:
I like the approach of hiding the complexity of the Reflection API behind an abstraction and in case of Whitebox it's even named perfectly. But accessing private methods is not the only thing PowerMock lets you do. In addition to much more you can set private fields, invoke hidden constructors and mock static methods. A feature that I really like is mocking final classes or methods, it can be quite helpful, when you are dealing with JDK classes like java.io.File.
I think PowerMock is a great extention to EasyMock and it should go into every developer's tool box. It's definitely going straight into mine.
PowerMock is a Java framework that allows you to unit test code normally regarded as untestable.
To be more precise, PowerMock takes away the annoyance of dealing with the Reflection API. In case of the example presented in my previous post, instead of this code:
@Test
public void test_Calculate_Quote() throws Exception {
Contract classUnderTest = new Contract(1L);
Method calcMethod = getMethodOfClass(Contract.class, "calculateQuote");
BigDecimal quote = (BigDecimal) calcMethod.invoke(classUnderTest, new DateMidnight(1982, 4, 27));
assertEquals(new BigDecimal("7.79"), quote.setScale(2, RoundingMode.FLOOR));
}
private Method getMethodOfClass(Class argClass, String argMethodName) {
Method[] methods = argClass.getDeclaredMethods();
for (Method method : methods) {
if (method.getName().equals(argMethodName)) {
method.setAccessible(true);
return method;
}
}
throw new NoSuchMethodError("couldn't find " + argMethodName + " on class " + argClass);
}
you simply write this:
@Test
public void test_Calculate_Quote() throws Exception {
Contract classUnderTest = new Contract(1L);
BigDecimal quote = (BigDecimal) Whitebox.invokeMethod(classUnderTest, "calculateQuote", new DateMidnight(1982, 4, 27));
assertEquals(new BigDecimal("7.79"), quote.setScale(2, RoundingMode.FLOOR));
}
I like the approach of hiding the complexity of the Reflection API behind an abstraction and in case of Whitebox it's even named perfectly. But accessing private methods is not the only thing PowerMock lets you do. In addition to much more you can set private fields, invoke hidden constructors and mock static methods. A feature that I really like is mocking final classes or methods, it can be quite helpful, when you are dealing with JDK classes like java.io.File.
I think PowerMock is a great extention to EasyMock and it should go into every developer's tool box. It's definitely going straight into mine.
April 19, 2009
Using Reflection in Unit Tests
A couple of days ago I watched a presentation on Neal Ford's book "The Productive Programmer". He talked about 10 ways to improve your code. One thing, which I found quite innovative, was leveraging Java Reflection to test non-accessible code.
With non-accessible code, I mean private, package-private or protected methods and constructors of your domain or service classes. If you are a test addict like me, you've probably made a method public or protected every now and then, even though it shouldn't be, simply so that you could access it from your test code. Using Reflection instead, is a simple and easy solution, I have never given a thought before.
I came up with a little sample, which you can download or check out on github. Take a look at the following class:
In order to test the calculateQuote method in isolation, I would have probably introduced a QuoteCalculator class. It would be in charge of the business logic and used by the Contract class. If you need the logic at multiple places in your code, that's a great solution. If you only need it in Contract, it's quite tedious and I would have probably made calculateQuote accessible from the test class. However, I used Reflection instead to solve the problem and it works quite nicely:
As you can see the method.setAccessible(true); is doing the trick to enable access from the test to the domain object. Instead of the actual instance of Contract, we use the Method instance to invoke the private call. Everything else is plain test code, as you know it.
Of course, you could argue to make the calculateQuote method package-private or protected and put the test class into the same package. In fact Bill Venners wrote about that in one of is articles, suggesting that testing private methods is bad practice anyways. I tend to agree and I guess the example above is an exception. However, using Reflection is not necessarily limited to testing private methods. You might need access to an object to manipulate it's internal state, in order to test it thoroughly and the best tool for that job is probably Reflection.
I think it's a neat idea to use Reflection in unit tests. Used with caution, it can be really helpful and is definitely better than breaking encapsulation for testing.
With non-accessible code, I mean private, package-private or protected methods and constructors of your domain or service classes. If you are a test addict like me, you've probably made a method public or protected every now and then, even though it shouldn't be, simply so that you could access it from your test code. Using Reflection instead, is a simple and easy solution, I have never given a thought before.
I came up with a little sample, which you can download or check out on github. Take a look at the following class:
public class Contract {
private static final Double RATE = 0.3;
private final Long contractId;
private BigDecimal quote;
private Customer owner;
public Contract(Long argContractId) {
contractId = argContractId;
quote = BigDecimal.ZERO;
}
/** package */void setOwner(Customer argOwner) {
owner = argOwner;
quote = calculateQuote(argOwner.getBirthday());
}
private BigDecimal calculateQuote(DateMidnight argBirtday) {
Years ageInYears = Years.yearsBetween(argBirtday, new DateMidnight());
return new BigDecimal(RATE).multiply(new BigDecimal(ageInYears.getYears()));
}
// other stuff omitted
}
In order to test the calculateQuote method in isolation, I would have probably introduced a QuoteCalculator class. It would be in charge of the business logic and used by the Contract class. If you need the logic at multiple places in your code, that's a great solution. If you only need it in Contract, it's quite tedious and I would have probably made calculateQuote accessible from the test class. However, I used Reflection instead to solve the problem and it works quite nicely:
@Test
public void test_Calculate_Quote() throws Exception {
Contract classUnderTest = new Contract(1L);
Method calcMethod = getMethodOfClass(Contract.class, "calculateQuote");
BigDecimal quote = (BigDecimal) calcMethod.invoke(classUnderTest, new DateMidnight(1982, 4, 27));
assertEquals(new BigDecimal("7.79"), quote.setScale(2, RoundingMode.FLOOR));
}
private Method getMethodOfClass(Class argClass, String argMethodName) {
Method[] methods = argClass.getDeclaredMethods();
for (Method method : methods) {
if (method.getName().equals(argMethodName)) {
method.setAccessible(true);
return method;
}
}
throw new NoSuchMethodError("couldn't find " + argMethodName + " on class " + argClass);
}
As you can see the method.setAccessible(true); is doing the trick to enable access from the test to the domain object. Instead of the actual instance of Contract, we use the Method instance to invoke the private call. Everything else is plain test code, as you know it.
Of course, you could argue to make the calculateQuote method package-private or protected and put the test class into the same package. In fact Bill Venners wrote about that in one of is articles, suggesting that testing private methods is bad practice anyways. I tend to agree and I guess the example above is an exception. However, using Reflection is not necessarily limited to testing private methods. You might need access to an object to manipulate it's internal state, in order to test it thoroughly and the best tool for that job is probably Reflection.
I think it's a neat idea to use Reflection in unit tests. Used with caution, it can be really helpful and is definitely better than breaking encapsulation for testing.
February 02, 2009
Do You Write Unit Tests For Yourself?
A couple of days ago I listened to the stackoverflow podcast with Jeff Atwood and Joel Spolsky. They were talking about when it is appropriate to write unit tests for your code.
Joel:
Jeff:
Of course I cannot quote the whole discussion here, so this might sound very harsh on testing for you. Jeff kind of put their statements into perspective by saying that he is pro testing, but just doesn't do it on stackoverflow. However, I still have this feeling that they turned their backs on unit testing too easily.
First off, let me tell you that I love unit tests. I write a lot of them and I care about code coverage quite a bit. You might even say that I am a little religious or dogmatic about it. I only have good experience with unit testing, so I tend to believe that I am not that far off. On my current project we are about 8 people working on our code base, so you can imagine there is a lot going on. It's easy to break something and believe me we are breaking stuff all the time. Although each developer has his domain, you are constantly working with code that was not written by yourself.
Fortunately our test coverage is pretty good. In case a test fails and something seems to be broken, you are being notified by the continuous integration server. Personally that gives me the confidence to do refactorings and changes without the fear of introducing major bugs. The biggest downside, which was also mentioned by Joel, is the "bang for the bucks". You need a big investment to get to this degree of test coverage. You really need to gauge, whether it's worth the time invested to write a unit test for a piece of code.
As mentioned before there is a lot of stuff breaking during development of new features. This is mainly due to not knowing all of the code base. However, I think working with other developers, you are bound to have unit tests. At least for the parts of your code that might be extended or maintained by others. It is worth to invest in a unit test, if you want to make life easier for your fellow developers. At least they can change your code with confidence. You are basically giving them a guideline, which helps to get their work done faster and more reliable. In the long run, I think that will increase the quality of your application and hopefully leaves an impression of your code on your fellow team members.
So what if you are working on a small team or almost alone on your project? Do you still need unit tests? That's when I want to come back to the discussion Joel and Jeff had. The stackoverflow team is quite small. I think Jeff probably thinks, that if you are working alone on a project it might not be worth the investment to write unit tests.
I kind of disagree, because I've been there myself. As the only developer of an application and working on various features at the same time, I found myself breaking my own features over and over again. I started writing unit tests and setup a continuous integration server, which helped me automate my builds and improved quality dramatically. By the time a second developer started working on the project the test coverage was reasonable enough, so he could change my code without the fear of breaking anything.
Maybe I'm just not that good of a developer and I need to write unit tests for myself. However, I do think it's worth the investment, because sooner or later another developer will have to work with your code. Go and make his life a little easier and provide some unit tests.
Joel:
"Changing a parameter in some function call from 37 to a 9 is not really gonna fail or introduce a bug"
"It's great if you use TDD for your encryption library or compiler, but that's a very finite number of apps that are like that"
"For a team of good programmers the prescriptions are probably gonna be different than from a team of mediocre programmers"
Jeff:
"With stackoverflow there are very few cases where I feel like: okay I'm gonna sit down and write a unit test and this is gonna result in a measurably better experience."
Of course I cannot quote the whole discussion here, so this might sound very harsh on testing for you. Jeff kind of put their statements into perspective by saying that he is pro testing, but just doesn't do it on stackoverflow. However, I still have this feeling that they turned their backs on unit testing too easily.
First off, let me tell you that I love unit tests. I write a lot of them and I care about code coverage quite a bit. You might even say that I am a little religious or dogmatic about it. I only have good experience with unit testing, so I tend to believe that I am not that far off. On my current project we are about 8 people working on our code base, so you can imagine there is a lot going on. It's easy to break something and believe me we are breaking stuff all the time. Although each developer has his domain, you are constantly working with code that was not written by yourself.
Fortunately our test coverage is pretty good. In case a test fails and something seems to be broken, you are being notified by the continuous integration server. Personally that gives me the confidence to do refactorings and changes without the fear of introducing major bugs. The biggest downside, which was also mentioned by Joel, is the "bang for the bucks". You need a big investment to get to this degree of test coverage. You really need to gauge, whether it's worth the time invested to write a unit test for a piece of code.
As mentioned before there is a lot of stuff breaking during development of new features. This is mainly due to not knowing all of the code base. However, I think working with other developers, you are bound to have unit tests. At least for the parts of your code that might be extended or maintained by others. It is worth to invest in a unit test, if you want to make life easier for your fellow developers. At least they can change your code with confidence. You are basically giving them a guideline, which helps to get their work done faster and more reliable. In the long run, I think that will increase the quality of your application and hopefully leaves an impression of your code on your fellow team members.
So what if you are working on a small team or almost alone on your project? Do you still need unit tests? That's when I want to come back to the discussion Joel and Jeff had. The stackoverflow team is quite small. I think Jeff probably thinks, that if you are working alone on a project it might not be worth the investment to write unit tests.
I kind of disagree, because I've been there myself. As the only developer of an application and working on various features at the same time, I found myself breaking my own features over and over again. I started writing unit tests and setup a continuous integration server, which helped me automate my builds and improved quality dramatically. By the time a second developer started working on the project the test coverage was reasonable enough, so he could change my code without the fear of breaking anything.
Maybe I'm just not that good of a developer and I need to write unit tests for myself. However, I do think it's worth the investment, because sooner or later another developer will have to work with your code. Go and make his life a little easier and provide some unit tests.
September 15, 2008
How To Do Continuous Integration and TDD?
A couple of months ago I wrote about my problem of writing test cases before the actual implementation. Last week I came across a little problem, which once again, backed up my position on the broken test first approach.
In my current project there's a reasonable development infrastructure. We use maven as our build tool and AnthillPro as continuous integration server. It supports integrating local changes of developers and makes sure all parts of the system work the way they should. By the way, this is my first time working with Anthill and I have to say I'm really disappointed. The only CI server that is probably worse is CruiseControl. I've used JetBrains's TeamCity on my previous project and it is way more sophisticated than AnthillPro, but I digress...
The problem that I faced concerning TDD and CI actually sounds very trivial: when should you check in code?
Let's say you are developing the TDD way. You think about the problem and come up with a neat JUnit test for your class, which by the way doesn't exist yet. The JUnit test makes a nice specification of what needs to be implemented. Unfortunately it's almost 5pm and you want to go home. The problem is that you will be out of office for the next couple of days. One of your peers will have to code the implementation, in order to keep the project going. So are you checking in your code?
The way a CI server usually works is that it checks your version control system every x minutes and gets the changes, triggers your configured build and runs your test cases. It can do a lot more, like fire up some server for integration testing or deploy your application to various test machines, running different operating system. In our case it checks SVN every hour, fetches the change-set and triggers the maven build. That comprises compiling, packaging and running instrumented JUnit tests. Only after each step was successful it shows the comforting green bar on the status page - and that's where the problem begins.
Since Anthill relies on maven to run the JUnit tests, you only see the green light when they all succeed. Maven simply indicates failures by returning -1. You can configure maven to ignore failing JUnit tests, which means it returns 0 and Anhill will show you the nice little green status bar. That's probably not really what continuous integration was introduced for, because you would have to dig into the log files to find out if all your JUnit tests really passed.
Let's get back to our example. Going down the TDD route all you have right now is a broken JUnit test, which surely makes a nice specification, but it doesn't satisfy your CI Server. If you check in your code you are gonna break the build. Basically your are left with the following options:
All of theses options are flawed not to say broken. The lesser evil would probably be a combination of option 1 and 2. Extract an interface that you can check in without breaking the build and email the JUnit test to your fellow developer to avoid him writing his own test case. It is not a very comforting solution, but I couldn't come up with anything better. Apparently, there is a discrepancy between CI and TDD or am I missing something?
Call me a green bar fetish, but I'm going for the blue pill. As I mentioned in the beginning the TDD approach in my opinion is kinda broken, for various reasons. I'm writing my JUnit tests after or sometimes even while I'm working on the implementation and I think that works quite well.
In my current project there's a reasonable development infrastructure. We use maven as our build tool and AnthillPro as continuous integration server. It supports integrating local changes of developers and makes sure all parts of the system work the way they should. By the way, this is my first time working with Anthill and I have to say I'm really disappointed. The only CI server that is probably worse is CruiseControl. I've used JetBrains's TeamCity on my previous project and it is way more sophisticated than AnthillPro, but I digress...
The problem that I faced concerning TDD and CI actually sounds very trivial: when should you check in code?
Let's say you are developing the TDD way. You think about the problem and come up with a neat JUnit test for your class, which by the way doesn't exist yet. The JUnit test makes a nice specification of what needs to be implemented. Unfortunately it's almost 5pm and you want to go home. The problem is that you will be out of office for the next couple of days. One of your peers will have to code the implementation, in order to keep the project going. So are you checking in your code?
The way a CI server usually works is that it checks your version control system every x minutes and gets the changes, triggers your configured build and runs your test cases. It can do a lot more, like fire up some server for integration testing or deploy your application to various test machines, running different operating system. In our case it checks SVN every hour, fetches the change-set and triggers the maven build. That comprises compiling, packaging and running instrumented JUnit tests. Only after each step was successful it shows the comforting green bar on the status page - and that's where the problem begins.
Since Anthill relies on maven to run the JUnit tests, you only see the green light when they all succeed. Maven simply indicates failures by returning -1. You can configure maven to ignore failing JUnit tests, which means it returns 0 and Anhill will show you the nice little green status bar. That's probably not really what continuous integration was introduced for, because you would have to dig into the log files to find out if all your JUnit tests really passed.
Let's get back to our example. Going down the TDD route all you have right now is a broken JUnit test, which surely makes a nice specification, but it doesn't satisfy your CI Server. If you check in your code you are gonna break the build. Basically your are left with the following options:
1. You don't check in your code. Instead you could e.g. email it to your fellow developers.
2. You quickly manage to extract the interface from the test case. Your peers could program against it.
3. You can configure maven to ignore your particular JUnit test. Therefore you'd have to adopt the POM file.
4. You comment out your JUnit annotations or the content of the test methods. That way the test wouldn't fail the build.
All of theses options are flawed not to say broken. The lesser evil would probably be a combination of option 1 and 2. Extract an interface that you can check in without breaking the build and email the JUnit test to your fellow developer to avoid him writing his own test case. It is not a very comforting solution, but I couldn't come up with anything better. Apparently, there is a discrepancy between CI and TDD or am I missing something?
You take the blue pill - the story ends, you wake up in your bed and believe whatever you want to believe. You take the red pill - you stay in Wonderland and I show you how deep the rabbit-hole goes.
Call me a green bar fetish, but I'm going for the blue pill. As I mentioned in the beginning the TDD approach in my opinion is kinda broken, for various reasons. I'm writing my JUnit tests after or sometimes even while I'm working on the implementation and I think that works quite well.
June 02, 2008
Nothing wrong with TDD, right?
Have you ever heard of Test Driven Development? Wikipedia says the it is
To me it's simply writing your unit tests, before implementing your classes. It's supposed to help you think about the design and in particular the interface of your classes upfront. I like this notion a lot! Thinking before coding - that's a good thing, right? Before I start my ramblings, let's here what Cédric Beust, co-founder of the TestNG framework has to say about TDD:
The statement is taken from an interview at InfoQ, if you are interested in the verbatim version of this quote, jump to question 6.
So basically Cédric spilled out exactly what my problem is with TDD! I've tried it - really, but writing my tests before implementing my classes just doesn't work for me. Let me tell you why.
I see coding as an iterative and incremental process, Cédric calls it macro-design. You have this basic idea of what your class is supposed to do. In the first step - or iteration therefore, you give it a name, which is supposed to denote the concept of your class. Maybe you also add some javadocs to explain your brainchild. At this point you probably don't have any methods yet. You don't really know in detail how your class is going to work, thus you can't generate your test cases. Most likely you don't want any test cases at all and that's exactly where the experts disagree.
Most of the time, in my experience, a unit test of a class reflects its behavior. You can implement a black box test, but as soon as your class doesn't stand alone, you have to mock the behavior of your collaborators. I'd argue that in 90% of all cases your class collaborates with some other classes or components. So if you start coding your test cases upfront, your not only defining the interface, but also the behavior of how your implementation collaborates with dependencies. If you are working on a component with several different classes and you are starting with implementing test cases upfront, you find yourself constantly refactoring those tests as your implementation evolves. I believe that's not what you want to spend most of your time on.
It's almost a paradox: you need test cases and it's sounds reasonable to write them before your implementation, because then they actually exist and you cannot forget about them. At the same time it doesn't make sense to test something, which doesn't exist yet or you only have a rough idea of how it's actually going to look like.
I like unit tests and I try to write one for each class I put out there. Some people argue, that writing your unit tests upfront increases the quality of your code. I think it's not the unit tests, it's merely giving some thought about your design, before starting to code. However, when I'm in the middle of an "implementation spree", refactoring test cases is one of those annoying and tedious little things that you constantly have to deal with as a developer. And those little things kill the mood - big time.
... a software development technique consisting of short iterations where new test cases covering the desired improvement or new functionality are written first, then the production code necessary to pass the tests is implemented, and finally the software is refactored to accommodate changes. The availability of tests before actual development ensures rapid feedback after any change. Practitioners emphasize that test-driven development is a method of designing software, not merely a method of testing.
To me it's simply writing your unit tests, before implementing your classes. It's supposed to help you think about the design and in particular the interface of your classes upfront. I like this notion a lot! Thinking before coding - that's a good thing, right? Before I start my ramblings, let's here what Cédric Beust, co-founder of the TestNG framework has to say about TDD:
... When you do TDD you tend to promote micro-design over macro-design. Micro-design means that you are focusing heavily at a very fine level which is the method....but what I found is that after a few years programming you start getting a good feeling with intuition, right away when you're solving a problem of what these extra classes are going to be, what the architecture, the design, the inheritance, how they interact with each other. But TDD is preventing you from going too far ahead...it leads you to create things that are so small that you end up throwing them away because they are really a first iteration and then you modify them and then you rewrite your test. So to me that's micro-design. Macro-design is more when you start thinking: "I'm going to need this interface, I might as well write it now, I'm going to need this extra class, I'm going to write it now; it's going to be empty right now". And those are things that are frowned upon by test-driven development practices and that bothered me a little bit.
The statement is taken from an interview at InfoQ, if you are interested in the verbatim version of this quote, jump to question 6.
So basically Cédric spilled out exactly what my problem is with TDD! I've tried it - really, but writing my tests before implementing my classes just doesn't work for me. Let me tell you why.
I see coding as an iterative and incremental process, Cédric calls it macro-design. You have this basic idea of what your class is supposed to do. In the first step - or iteration therefore, you give it a name, which is supposed to denote the concept of your class. Maybe you also add some javadocs to explain your brainchild. At this point you probably don't have any methods yet. You don't really know in detail how your class is going to work, thus you can't generate your test cases. Most likely you don't want any test cases at all and that's exactly where the experts disagree.
Most of the time, in my experience, a unit test of a class reflects its behavior. You can implement a black box test, but as soon as your class doesn't stand alone, you have to mock the behavior of your collaborators. I'd argue that in 90% of all cases your class collaborates with some other classes or components. So if you start coding your test cases upfront, your not only defining the interface, but also the behavior of how your implementation collaborates with dependencies. If you are working on a component with several different classes and you are starting with implementing test cases upfront, you find yourself constantly refactoring those tests as your implementation evolves. I believe that's not what you want to spend most of your time on.
It's almost a paradox: you need test cases and it's sounds reasonable to write them before your implementation, because then they actually exist and you cannot forget about them. At the same time it doesn't make sense to test something, which doesn't exist yet or you only have a rough idea of how it's actually going to look like.
I like unit tests and I try to write one for each class I put out there. Some people argue, that writing your unit tests upfront increases the quality of your code. I think it's not the unit tests, it's merely giving some thought about your design, before starting to code. However, when I'm in the middle of an "implementation spree", refactoring test cases is one of those annoying and tedious little things that you constantly have to deal with as a developer. And those little things kill the mood - big time.
February 18, 2008
Quote Of The Week
-- the ultimate unit test is whether or not users want to use your application. All the other tests you write are totally irrelevant until you can get that one to pass.The Ultimate Unit Test Failure
February 11, 2008
Useful Test Method Naming
The Google Testing Blog aka Testing on the Toilette features an interesting post about the naming of your methods in test cases. It uses the so called Stroop Effect, to demonstrate how proper method naming can increase your productivity:
Quickly say all 25 colors out loud!

It's quite challenging, isn't it? It's similarly challenging as figuring out what's wrong, when one of your tests breaks and its method name and failure message don't make any sense. So here are a few tips on naming your test methods:
Quickly say all 25 colors out loud!

It's quite challenging, isn't it? It's similarly challenging as figuring out what's wrong, when one of your tests breaks and its method name and failure message don't make any sense. So here are a few tips on naming your test methods:
- When someone breaks your test – will your test name and message be useful to them?
- Opinionated test names like testMethodDoesSomething can be more helpful than testMethod.
- Great test messages not only identify the actual behavior,but also the expected behavior.
- Should is a handy word to use in messages – it clarifies what expected behavior didn't actually happen.
November 27, 2007
Profiling Follow up
InfoQ published a nice article about performance testing a couple of days ago. They argue it should be addressed the same way components are tested these days: in a continuous and automated unit test.
My strategy: don't go overboard. I wouldn't write too fine grained tests from the beginning. If your integration test highlights performance problems, you can still take apart your components and write test for units.
The article makes the same statement I did in my blog post about profiling last week: people tend to put off performance to the end, thinking of it as non functional requirement and therefore mostly address it when it's too late.
With continuous performance testing we need to focus on more granular aspects of our systems, components and frameworks. Just as is the case with unit testing, we can only expect to find certain classes of problems when we test these artifacts in isolation. A case in point is the contention between components of misuse of frameworks resulting in response times higher than expected; these are things that will only come out in a full integration test. However understanding how much CPU, memory, disk and network I/O we need, can help us predict and take preventive action (rather than apply a premature optimization).I'm not too sure what to think of this. On the one hand it makes perfect sense to test performance with a unit test, in isolation, since it'll be easier to identify potential bottlenecks. On the other hand I tend to think that an integration test makes more sense. You only know your overall response time, if you test your components together - and that's what the user will get.
My strategy: don't go overboard. I wouldn't write too fine grained tests from the beginning. If your integration test highlights performance problems, you can still take apart your components and write test for units.
The article makes the same statement I did in my blog post about profiling last week: people tend to put off performance to the end, thinking of it as non functional requirement and therefore mostly address it when it's too late.
November 22, 2007
Is Profiling not a Common Practise?

According to this poll on java.net profiling doesn't seem to be a common practise of Java developers. I think there are two possible explanations for this:
First: you don't need a profiler! Your application behaves as expected, even under heavy load or extraordinary circumstances. You always develop your code with performance in mind and everything works as you intended. Hence - no need for a profiler.
Second: you didn't think of performance at all and it came right back at you after more than one user at the same time used your app at the same time. That's when you realize that performance and profiling should have been part of your design and development lifecycle. Hence - you need a re-design.
November 21, 2007
October 09, 2007
Code reusability is hard...
... as anyone who has tried to herd the cats (developers) all together towards some form of reusability or core technology will tell you. Every developer will loudly proclaim that code must be reused. They will immediately follow this up by demanding to work in a core technology group that will produce the greatest code for sharing since sliced bread. What they’re really saying is, “Everyone should reuse code, but it has to be my code they reuse.” ... In 99 out of 100 cases, the recipient (developer) will loudly proclaim that the code is completely unusable and will have to be rewritten.I love this kind of statements, cause they are a reality check for me. I noticed that I do reuse code without any objection, if it's a small portion or a class. As soon as it's a framework or a component, I start looking for javadocs or other kinds of documentation. If there are no resources or examples to work with, I won't touch the thing. I simply don't want to spend hours looking at undocumented code, trying to understand it.
I took over the project I'm working on right now about two years ago and I guess I refactored about 90% of it since then. Notice the term "refactored" not rewritten. However, I had to rewrite portions of it. Requirements changed, use cases changed, well almost everything changed. Still, there are parts of the application which were written more than two years ago, still in production and I'm still reusing them in new code I'm implementing right now.
So I guess as long as the code doesn't exceed a certain amount of complexity, I'm willing to touch it. That doesn't mean I'm not gonna refactor it!
August 21, 2007
When is ugly code actually ugly?
In the second part of Beautiful Code in the Real World, Alberto gives hints how to bring back beauty into legacy code bases. He calls them localized actions, following the theme "Scorn Globally, Act Locally".
While reading this post, I'm wondering how to define "ugly" code?
At the moment I'm refactoring a legacy code base, partially written by myself. It works pretty well actually, the reason for refactoring is that the requirements changed and in order to serve the business use cases it needs to be refactored.
At the time of writing that code, it was actually very clever and as said before, it worked pretty well. Looking at it now, I just think it's just ugly and I have the feeling of refactoring all of it. That's not only the case for the code someone else wrote, but also for my own code.
I'm wondering: if you say something is ugly, it's kinda insulting, right? So if code worked pretty well and served it's business requirements, but it looks strange today, is it okay to call it ugly?
While reading this post, I'm wondering how to define "ugly" code?
At the moment I'm refactoring a legacy code base, partially written by myself. It works pretty well actually, the reason for refactoring is that the requirements changed and in order to serve the business use cases it needs to be refactored.
At the time of writing that code, it was actually very clever and as said before, it worked pretty well. Looking at it now, I just think it's just ugly and I have the feeling of refactoring all of it. That's not only the case for the code someone else wrote, but also for my own code.
I'm wondering: if you say something is ugly, it's kinda insulting, right? So if code worked pretty well and served it's business requirements, but it looks strange today, is it okay to call it ugly?
August 10, 2007
This is so true
It's actually sacry, but Alberto Savoia hit the nail on the head once again, describing his views on the book Beautiful Code.
I experience this everyday and sometimes I wish I could just change my profession and do something like working construction and actually build something beautiful. Nevertheless I've never stopped trying to avoid ugly hacks and stand up for the more beautiful (and hopefully) better solution. But it can be hard and frustrating sometimes...
You are a bright-eyed and bushy-tailed developer. You have just finished reading the book Beautiful Code and you are ready to create some binary beauty of your own. You can’t wait to put what you’ve learned into action. You fire up your IDE and, as the blob of code that you’ve inherited and have to work with slowly loads, the brightness in your eyes is replaced by a glazed look. A minute later your bushy tail hangs limply in defeat. Reality sets in. Beautiful Code goes back on the shelf, next to Programming Pearls and Six-Pac Abs in Seven Days.
...
The odds of finding truly beautiful code in most production systems seem to be on par with the odds of finding a well-read copy of IEEE Transactions on Software Engineering in Paris Hilton’s apartment.
I experience this everyday and sometimes I wish I could just change my profession and do something like working construction and actually build something beautiful. Nevertheless I've never stopped trying to avoid ugly hacks and stand up for the more beautiful (and hopefully) better solution. But it can be hard and frustrating sometimes...
April 09, 2007
Unitilis
Unitilis is a nice library which supports unit testing with Spring and Hibernate. The article above gives a short overview of the capabilities of Unitilis like integration with Spring, provisioning of test data and asserting results.
I think the library is nice, but actually I don't see any imperative for it! Spring offers a wide range of testing capabilities, which I think work fairly well! So the question I'm asking myself is why bring in another library? I can use Spring to test almost everything, all I have to do is extends a Spring-test-class and I'm good to go.
As for the provisioning of test data, Unitilis uses an XML file to define a set of test data which is being loaded before the unit test method is executed. One of my approaches is using the setUp() method to programatically fill POJOs with test data. Although a little tedious, the compiler would tell me immediately if something went wrong, for instance during refactoring my domain model. I believe the XML approach is suboptimal in this case.
Unitilis provides a so called "reflection assert utility" that compares all fields of an expected and actual object. This is a really nice feature and I hope you can use this without any of the other Unitilis stuff. My approach so far is asserting every field "by hand". Unititlies takes care of that for you and in addition you can specify whether it should be lenient or not, when it comes across null/0 values. Check out this example take from the article above:
It checks every field of the object in the list of results, if it matches the field of the expected object. In my opinion this is a great feature and I'm definitely gonna incorporate this into my unit tests at work.
To wrap this up, I really don't see any imperative for this library at least if you are using Spring heavily. I might be wrong and if so please drop me a line! I really like the assert feature using reflection and I think I'm gonna start using that from now on.
I think the library is nice, but actually I don't see any imperative for it! Spring offers a wide range of testing capabilities, which I think work fairly well! So the question I'm asking myself is why bring in another library? I can use Spring to test almost everything, all I have to do is extends a Spring-test-class and I'm good to go.
As for the provisioning of test data, Unitilis uses an XML file to define a set of test data which is being loaded before the unit test method is executed. One of my approaches is using the setUp() method to programatically fill POJOs with test data. Although a little tedious, the compiler would tell me immediately if something went wrong, for instance during refactoring my domain model. I believe the XML approach is suboptimal in this case.
Unitilis provides a so called "reflection assert utility" that compares all fields of an expected and actual object. This is a really nice feature and I hope you can use this without any of the other Unitilis stuff. My approach so far is asserting every field "by hand". Unititlies takes care of that for you and in addition you can specify whether it should be lenient or not, when it comes across null/0 values. Check out this example take from the article above:
ReflectionAssert.assertRefEquals(new Person("John", "Doe"), result.get(0));It checks every field of the object in the list of results, if it matches the field of the expected object. In my opinion this is a great feature and I'm definitely gonna incorporate this into my unit tests at work.
To wrap this up, I really don't see any imperative for this library at least if you are using Spring heavily. I might be wrong and if so please drop me a line! I really like the assert feature using reflection and I think I'm gonna start using that from now on.
April 06, 2007
Being a farmer
Look at this analogy taken from Alberto Savoia's Working Effectively With Characterization Tests:
Does that mean I'm a farmer, dealing with cows every day?
Trying to understand a system’s behavior by looking at a pile of code that you did not write is like trying to understand a cow’s behavior by looking at a butcher’s shelf.
Does that mean I'm a farmer, dealing with cows every day?
April 05, 2007
Testing vocabulary
Nice definition of terms used for objects used in testing:
- Test Double is a generic term for any test object that replaces a production object.
- Dummy objects are passed around but not actually used. They are usually fillers for parameter lists.
- Fakes have working implementations, but take some shortcut (e.g., InMemoryDatabase).
- Stubs provide canned answers to calls made during a test.
- Mocks have expectations which form a specification of the calls they do and do not receive.
com_channels
- mail(dlinsin@gmail.com)
- jabber(dlinsin@gmail.com)
- skype(dlinsin)
my_links
recent_postings
loading...