Sunday, January 10, 2010

welcome 2010

Was 1990 really 20 years ago? I actually remember 1990. Eeek.

This is a continuation, 1 year later, from http://rockymountainbrett.blogspot.com/2009/01/wrapping-up-last-year-kicking-off-2009.html. My bottom 5 goals are still very relevant, and at this point I would like to add a few more.
  1. Conversational fluency in Spanish. I have a tutor for this and so far I'm headed in the right direction.
  2. Working fewer nights and weekends. This must happen.

Monday, December 28, 2009

TDD thoughts / notes after reading Kent Beck's TDD By Example

I've read James Newkirk's (the original developer of NUnit) book on TDD, been to TDD workshops (including one with James Newkirk), and consider myself to know a fair amount about TDD. I drank the kool-aid several years ago and have been trying to preach the good news ever since. I hadn't, however, read Kent Beck's Test-Driven Development By Example until today. I would honestly say that this is the best software book I've ever read, and it only took me a few hours to get through. It is simple and easy to understand, even when covering fairly complicated material. Bravo. The notes that follow are based on the book. They are not a book report, but a reminder for me and others to follow when trying to fully grok TDD.
--------
What is our programming / development style? In other words, how do we typically implement and verify business (i.e. non-UI) rules? 5 options I’ve seen / done:
  1. Modify existing function or add a new one then open a web browser, click a button, then verify on the web page
  2. Modify existing function or add a new one then open a web browser, click a button, then verify in the database (similar to using SQL Profiler)
  3. Add Response.Write, STOP, etc. statements in code, or add CSS around an element to call attention to it and go from there
  4. Write a bunch of new classes / methods / etc. in an effort to finish a task before a deadline, then come back to them weeks later and write some xUnit tests to boost code coverage from zero to x…. only to find out when writing your tests that your design / architecture is far from ideal. aka TLIE (Test Last, If Ever)
  5. Open xUnit, create an automated test, make it pass, and then change the necessary code base, cry tears of joy… aka TDD
Which of those (and others you can think of)…
  • is repeatable?
  • leaves a signpost for future developers, documenting that a certain feature exists?
  • provides an example API usage for future developers (including myself in that audience)?
  • is fast? (and therefore gives you the ability to try several implementations when you have a few options in mind and aren’t sure which not only works but is best)
  • is isolated (can happen even if everything else is broken)?
  • does not require (much, if any) human work?
  • gives us confidence when making any change, no matter the size?
Testing changes is not the same as having tests.

Why is writing the automated test important at all?
  • Automated tests help us verify that we definitely know what we think we know. Adding more helps convert “what we don’t know” to “what we know” …. err, something like that.
  • Tests provide living and up-to-date documentation in source control.
  • Especially in our code base, changing almost anything is stressful. Automated tests are stress management tools. Passing automated tests eliminate the stress of “what we don’t know” and gives us the courage to focus on our real passion, which is adding more value to our customers. [If you feel no stress at all when debating changing code in your current production codebase, please leave the room after reading the following out loud: I, _________, apologize to the entire company for the future hotfixes I am about to create a need for. I apologize to our production release team, to support, my fellow developers, and to our customers. I have stocked the kitchen with Red Bull, Tylenol, and Prozac. I will begin working on handwritten letters of apology immediately.]
  • “In TDD, the tests are a means to an end – the end being code in which we have great confidence.”
  • You tell me
2 simple tenants of TDD:
  1. Write new code only if an automated test has failed
  2. Eliminate duplication
So how do we do that?
  1. Red
    • Write the test first to tell the story of what we wish to implement,
    • how we wish our API to look (Beck calls this “the perfect interface for our operation” and tells us to “Invent the interface you wish you had.”),
    • what will cause the test to pass (assertions),
      • Write the assert statements first so you know when you are done.
    • help define clearly what is in scope and what is not.
    • This gives us a concrete measure of failure!
  2. Green
    • Fix the failing test to pass to know with certainty the given story has been completed
    • Even if it’s ugly, just focus on turning the red bar to green fast
    • This gives us a concrete measure of success!
  3. Refactor
    • Keep a tidy house and make sure the green bar still exists afterward
    • If you used constants to get a single test to pass in step 2, add another assertion and generalize the code to work for all scenarios (triangulation).
    • Change the code but not the outcome or business rules. This is a stressful and time-consuming exercise unless you have tests as a safety net to guarantee even massive code changes don’t cause a change the in code’s behavior as the end user sees it.
What other subtle thing does this mean we’re always doing?
  • Design. TDD is continual design. Design is fluid and never finished. Features (and scope) are complete when all tests pass, but design goes on like the Energizer Bunny. Do not be surprised to see your design veer wa(aaaaaa)y off course from what you originally thought you should originally end up with.
Why is writing the test first important?
  • Design is mandatory instead of an afterthought
  • You start with the world’s greatest API for the given problem and only back down from that when necessary
  • Tests are a way to identify scope boundaries and help us stay within them while we develop. We isolate a tiny low-stress situation, and only move outside of that scope when we are ready to write a new test. When we have a failing test that we need to make a passing test, we cannot ourselves to get sidetracked by, “oh yeah, I also need to implement this for this project…” and then we’re 30 minutes later before we remember what we were working on. In this way, writing tests first eliminates waste. (!!!!!)
The pattern for writing new tests
  1. Arrange – create some objects (setup your condition)
  2. Act – stimulate them (force the situation under test to execute)
  3. Assert – check the results
I have seen this called AAA Syntax. (See Rhino Mocks)

Before beginning any task, write a list of all the tests you know you will have to write. After you have Red>Green>Refactored a story off of your to-do list, select the next item from the list based on:
  • level of confidence (am I certain I can make this work?)
  • will this teach me something?
If you discover a potential problem, do not be afraid to simply add it to the to-do list instead of interrupting the current Red>Green>Refactor session.

Some things you might already know but need to reconsider:
  1. Make sure your tests are isolated. One failing test should not cause 3 others to fail. The order in which the tests run should also not matter.
  2. Change the voice inside your head from “how do I implement feature X” to “how do I test my implementation of feature X” any time you open the IDE and consider typing.
  3. You decide your velocity with TDD. If you find yourself getting annoyed at running tests after changing every single line of code that you know will not break a test (such as changing a variable name inside a 4 line c# method) then allow yourself to make bigger incremental changes before re-running tests. If you find yourself stressing over whether all your tests will pass or not, slow down. Redline the Bronco like OJ on a clear sunny day and slow down when the road gets icy.
  4. Every time you have a test fail unexpectedly, write a new test to document what was just discovered. It may mean you just found a bug.
    • Along the same lines, take the time to discover why something works when you think it shouldn’t.
    • Along the same lines, if you find a refactoring which your current tests do not demand, write another test.
  5. Your test code may actually be as many lines as the code you are adding. This is not a bad thing.
    • Doesn’t this mean my output is going down? When answering that question, be sure to take debugging time, integration, and code explanation / learning into consideration. (Just because something makes sense to you doesn’t mean it will be easy for someone else to learn… or even for you to recall in the future when adding feature Y to the codebase built for feature X. Your tests at least document your obvious-now-but-likely-to-become-confusing-later solution.)
  6. Do not be afraid to delete assertions, tests, or methods as part of refactoring; however, be confident that a test is obsolete before deleting. If the test does not give you any more confidence by existing, and it doesn’t communicate anything new to the reader of the test that they can’t learn in another test, it can be deleted.
  7. TDD does not in any way replace or eliminate a need for performance / stress / usability testing.
  8. 100% test coverage does not mean 0 bugs.
  9. Can we change the meaning of 1 line of code and then have a broken build? If not, we need another test. In other words, if we change line 873 (umm, first of all, we should never have a line 873, but that's a different discussion...) of ____.cs to say x = true instead of x = false, we should have a failing test.
Lastly, do not forget that changing code without a failing test is a violation of tenant #1 (Write new code only if an automated test has failed).

I think one of the most potentially difficult things about TDD is to let yourself solve the problem simply and then make it as pretty as you want to. When you solve it simply with passing tests, you can then change the solution to be reusable, decked out with patterns, etc. and be confident that the more complicated solution still solves the problem. In other words, don’t worry about it being pretty right out of the gate. Worry about solving the problem by making the test pass, and then let the patterns or perfection reveal itself through design changes, aka refactoring. Beck says this specifically in reference to the Template Method pattern, “Template methods are best found through experience instead of designed that way from the beginning.” but I think it applies to all (err, most?) patterns. He later states that extracting too many methods can lead to the reverse (inlining methods) when you think start off with a Template Method instead of following the above advice… so save yourself the time and let the patterns reveal themselves instead of creating patterns for the sake of patterns.

Sunday, November 8, 2009

Costa Rica bonus entry, day 9

11/1/2009 Sunday
This morning Catherine and I walked town a bit and killed more time before our taxi took us to the airport. Molly left a few hours before us. We found a little bakery to get apple pastries and cafe con leche to wake us up. A pretty nice morning.
---
The sun is presently sinking into the Gulf of Mexico. It's really pretty... warm and inviting in Miami 30,000' below.
A plane just eclipsed the sun. I'm glad I opened the window to see it because that must be rare. Sun dogs can be seen on whispy clouds to my left. I really enjoy window seats; sunsets even moreso. Tranquility. I'm back over U.S. soil now and have very mixed emotions about that. The in-flight movie was 500 days of Summer. I had mixed emotions about that too. I'm glad it had a happy ending because the rest of it was really painful to watch. I can't say that I have a ton of experience in that regard, but it resonated strongly with me. That feeling really sucks. Really. Miserable. The sunset just peaked. Brilliant. Really inspiring actually. The clouds below are putting on the display now.
Another thing I don't have mixed emotions about is the book I finished before the movie started; Compañero about Che Guevara. I didn't really know enough about him other than watching Motorcycle Diaries and Che (the ones with Benicio Del Toro) before the book. What a tremendous read. Che is a polarizing icon, so I wanted a fairly neutral and unbiased account. Compañero served well. It pointed out faults and mistakes as well as celebrating successes. (Florida is getting wider now. Chau Gulf, hello confederacy.) I find I relate to Che strongly in many aspects and very little in others. I feel bad for him that he kinda got sucked into several things in Cuba that prevented him from truly pursuing his aspirations as he may have otherwise preferred. Regardless of your opinion, this book is a good read. I think a vast majority of people with an opinion of him are mis/under-informed. Did he carry out executions? Yes, but no more than the U.S. ever has in a day. Did he do a lot of good? Yes, but perhaps not exactly as his fans would think. I really believe those who are "pro-Che" fail to recognize his faults, and those who are against him fail to recognize his achievements. Like John Kennedy, John Lennon, MLK, etc., it would have been interesting if he were still alive. If nothing else, I can better understand his point of view now.

Pasajes de Costa Rica, viaje 1, día 8

This is part of 8 posts where I will, with minor edits and omissions, put my journal from days in Costa Rica online. There is no real grammar structure, but hopefully it makes sense...
10/31/2009 Saturday
Last day of vacation. Boo. Major bummer. Need to catch up on yesterday first... Before my surf lesson at 4:00 I took my rented board and got the hang of messing around in the whitewater. Rode a few waves on my knees. Russell gave me a different board for the lesson; not made of foam, better. We spent about 15 minutes on the beach and then took to the water. The very first wave he told me to try I stood right up and rode to shore. He seemed surprised. "Most people don't do that." I was really stoked. I only rode / stood up on a couple more, but it was a ton of fun. I can easily see how people get addicted and chase waves for years. What a great sensation. (What a beautiful buzz...) It started raining really hard and got dark fast. When we had walked back to Caza Zen, the Black & White party picked up. I only had one clean black or white shirt... a long sleeve. Oh well. 4 beers and dinner were about $9. I talked to a lot of interesting people. (Earlier in the day before my lesson I talked to a couple from Columbus. We talked about the black hole that is Ohio State Buckeye football and why nobody seems to do anything but drink at social functions in Ohio.) The party went fairly late... maybe 1am. I got excited when 2 Swedish guys invited a lot of people to their room for some "Swedish water." I thought it would be a new discovery, like the aguardiente incident in Seattle. No such luck; vodka. I hate vodka.
Also, before I forget about Friday, I kept thinking English speakers I talked to were Aussies. A girl from Minnesota selling jewelry at the party sounded like that, but said it was just because she had rarely used English in the past 6 yrs. "I just decided I didn't want to live in the States anymore." Russell, my surf instructor, was from England and could pass for an Aussie too. His girlfriend definitely sounded British though. I talked to a Kiwi and recognized right away he was from New Zealand, so no error there. He re-taught me the term "seppo" for "Americans" - I had heard the term but not the origin (Yankee shortened to Yank rhymes with septic tank, shortened to seppo). He seemed surprised when I told him that if he used phrases like, "Good on you!" people from the States wouldn't understand, or that if he referred to our measurement system as the Imperial system "Americans" wouldn't know he meant weight in lbs, distance in ft/in. I honestly think most people wouldn't though. Sidenote: I find myself not liking to use the term "Americans" for people from the States, myself included. It seems wrong; arrogant. This is America too. I am not in the central USA but I am in Central America right now.

I woke up, caught the bus, the ferry, then another bus and was in Alajuela to wait to catch a taxi to the airport. Molly, Catherine and I split a room to save money and shopped a bit. I bought a hammock! Lunch at my last soda for this trip.... so filling, only 1 meal needed today, roughly translated to about $4. As the sun set we walked west to a cemetery (seemed fitting for Halloween and a nearly full moon) in town then walked back towards our hotel. It seemed like a waiting game, just killing time before we had to leave. The trip was over. We walked past the main cathedral in town... that's a nice area. After dark Molly and I walked down to Pops to get some ice cream then watched surf porn on youtube [segments of Endless Summer... I still need to rent it] on the free internet connection at the hotel. There is a very obvious police presence in Alajuela, and I did not feel in danger walking after dark.

I'm excited for the snow at home but already missing this country. I can't say for sure (obviously) yet, but I feel like this trip has yielded one of the most important weeks of my life so far. Definitely significant. Costa Rica truly is a rich country, and it gave me a lot.

Saturday, November 7, 2009

Pasajes de Costa Rica, viaje 1, día 7

This is part of 8 posts where I will, with minor edits and omissions, put my journal from days in Costa Rica online. There is no real grammar structure, but hopefully it makes sense...
10/30/2009 Friday
It's another overcast day on the Pacific. Fairly choppy water. The howler monkeys woke me up and it's been fairly low key since then. I walked to the bank to get dollars for my surfing lesson. I really want to buy a hammock but don't really have room for one in my equipaje. Next time I may bring an empty duffel bag or something like that, and take a shuttle if I fill it, although I find myself preferring the public transport. On my way back to the hotel I got a ride from a guy that works at Casa Zen. I asked him what he thought of all the construction. He spoke fairly fast, so I didn't understand all of his Spanish, but essentially he said it was terrible. A very lamentable situation. He said there are no rules, no permits, no concerns for the roads, schools, locals... the dollar prevails. It's unfortunate and I hope it changes.