The point of reevaluating how I write my code with tests is to come up with a system that works the best for me. In order to figure out what I need I’m going to first step back and figure out why high order objectives are most important to me. This is the order of preferences.
The context of my testing will be for Rails apps and the team is assumed to be one person only, me.
I became interested in test driven development after reading an interview with Alan Cooper in which he remarked that the then still nascent (2001?) movement of both agile and test driven development represented something new and interesting in the world of software development. Thus began my long standing curiosity about what was so new and interesting about things such as extreme programming, scrum, and their contrast against waterfall. I initially began TDD with NUnit during the time when I was a .NET developer. I remember those days as being a struggle to learn what TDD really was amongst wrestling with the technical complexities of configuring NUnit to work with web apps. For a .NET web application I was able to test the business layer of my app but when it came to the views and html levels, there was a lot of work involved to get testing on that level and at the time I didn’t have a strong enough grasp on it to be able to do it comfortably.
Then I discovered RubyonRails and within an afternoon found not only a framework that gracefully solved the problems I wrestled with in .NET as far as MVC separation and freedom from a compiler, but also unit testing was baked right into the framework and it was easy to use. Having a strong conviction that TDD would make me a better developer I resolved not to write any ruby code without testing first, and it’s a conviction that I carry with me to this day. Finally, I was able to use TDD on a whole application and see how it supported the entire life cycle of the application from development to maintenance.
I started out as a devotee of Test Unit, I wrote code that checked final states and I used fixtures to simulate test conditions. Enter in my first testing pains. My tests were riddled with dependencies where making a change to one my models would cause breakage among a whole host of tests in both my unit tests and my functional tests. Fixtures were driving me insane in much the same way and I felt like I spent more time maintaining my fixtures than I did my code.
Then along comes Rspec and the pendulum swings in the other direction. Okay so to this day I really don’t see the distinction between TDD and BDD, to me it still feels like the same thing and the distinction in testing semantics is a bit lost on me. I don’t see Rspec as being a dramatically different testing paradigm than Test Unit but rather it provides conveniences that address some of the problems discovered with classic unit testing. What changed most for me was the adoption of mocks and stubs. Mock objects were something that I had a hard time learning until I discovered Rspec and it’s mockist way of doing things. So I did what most developers do when given a new shiny toy, I way over did it. I mocked and stubbed the shit out of everything, I had some amazing 10 line stubs on multiple objects and the nightmare of maintenance that went along with them. I finally freed myself of dependent tests by isolating my controller and model layers, my specs ran much faster than fixture laden tests and I now had a new set headaches in the form of brittle tests that were caused by way to much implementation mocking.
This is the background of how I got to where I am today. I’m reevaluating my whole approach to testing, I know the right way for me to test is going to be created by me. In in a quest to find the method of testing that gives me better design for my classes, visibility into the state of my application, speed of execution, and least amount of grief. Testing is complicated there is a time for state based testing and there is a time for interaction based testing. You have to pick your poison carefully. I’m going to develop a system that works for me and I have the advantage of having written a lot of tests in my time, in the back of my head though I want to create a system that is simple enough to teach to others. I’m going to find a way…
I’ve been watching a lot of chef shows lately splitting my time between Anthony Bourdain’s “No Reservations” and Gordon Ramsay’s “Kitchen Nightmares”. With the latter I’ve only watched the first three episodes from the first season and in each there is one recurring theme. “Kitchen Nightmares” is a show where 3 star chef Gordon Ramsay arrives at someone’s failing restaurant and beats the mediocrity out of the place. At the start of each episode he visits the restaurant and orders from the menu to see how bad things really are. I’ve noticed in each episode he makes the same comment regarding the menus. All of the menus were offering a huge selection of dishes, one of the solutions for fixing a failed restaurant is to trim down the menu and focus the food towards a tighter concentration. If you are an indian restaurant there is no point to offering buffalo wings.
In Brazil you always know when the local soccer team just scored an important goal when all of sudden the entire neighborhood erupts in ecstatic cheers, cars honk their horns, and fireworks explode dangerously close to you.
I adopted ruby as my preferred programming language a couple of years ago and one of the things I did during the switch (from .NET) was to become a TDD developer. I started writing tests from the very first moments when I adopted the language. Part of the motivation to learn Rails came after I saw how easy it was to unit test with the baked in support that Rails provides. After years of writing tests I can confidently state the following:
Why I love code with tests:
What I recognize about Unit Testing:
In my experience Object-Oriented programming is something everyone says they do but very few seem to get it. I’m not even sure if I even get it but I work on it all the time because what little I’ve managed to learn so far has made such a big difference in how I design software. I recently discovered a great idea in the recently published Thoughtworks Anthology, called Object Calisthenics by Jeff Bay. Object Calisthenics are 9 rules that you use to develop a program in a more object oriented manner. One of the rules is “Don’t use the else keyword” another is “Use only one dot per line”. The point of this exercise is to push towards smaller more collaborative class designs which seems like a worthwhile task and I hope to follow through on it with a project built using the rules.
Brazilians are great people, and there is no shortage of excitement here because of them. For the most part I spend my time just trying to learn this culture and understand a new way of living. Every now and then something makes me scratch my head and ask, “You sure this a good idea?”.
Brazilian priest missing after balloon lift-off
…and maybe it is? As much as 37Signals has a huge following you don’t see very many people in the startup world replicating their model of self-funded small apps that make a profit. Everybody seems to go the VC-funded route. David does make some good arguments:
The Secret to Making Money Online
“When I look back at the bugs I, acting as a programmer, fail to prevent and then fail to catch, an awful lot of the time their root cause wasn’t my knowledge. It’s that I have a compulsive personality and also habitually overcommit. As a result, there’s a lot of pressure to get done. The problem isn’t that I can’t flip into an adequate tester mindset, it’s that I don’t step back and take the time.”
— Brain Marick, from blog article Security Mindset
Me too.
…It’s actually only closer to 80%. The really common things are really easy. The less common things, aren’t as easy. And the rare things, well, those you have to do manually more often than not.
It’s a feature of rails. An intentional design decision. If you’re fortunate enough to have your apps all fall in that 80% category, good for you. That’s wonderful. But don’t expect that.
— Jamis Buck, from comments on blog article Don’t be afraid of harnessing SQL
Every now and then you see a new technology take the developer world by storm, Git recently has exploded in it’s adoption. There are a couple of interesting things to note about the widespread, fast switch to Git.
I love writing even more than I love programming, and this space will be where the two will come together. This blog and the engine that runs it was created by me using RubyonRails. Having read Geoffrey Grosenbach’s screed that a “beginning Rails developer should write their own blog software”, I figure this advice applies to me too and I should go ahead and eat my own dog food. My terribly naive implementation of a blog clcks in at a svelte 25 lines of code… If you don’t count that teensy weensy ruby web framework that it’s sitting on.