Skip to Content »

Tech Life of Recht » archive for February, 2008

 X Driven Development

  • February 28th, 2008
  • 1:41 am

There’s a lot of xDD (x Driven Development) going around, and there has been for some time. Some are somewhat official, like Test Driven Development, but there are many others. A number of them should probably just be left alone to die, some are just plain stupid, but still… You don’t want to get caught in a conversation where you suddenly can’t give you opinion on Blog Driven Development. So, here’s the unauthoritative list of methodologies sorted by name, not relevance:

Acceptance Test Driven Development – Focus on real-life test scenarios.
Accountability Driven Development – make sure someone’s always accountable. Beware not to fall into Blame Driven Development.
Annoyance Driven Development – let your annoyances guide you. Probably best on one-man projects.
Asshole Driven Development – Let the biggest asshole make all the decisions. Also known as Jerk Driven Development.
Behavior Driven Development – Like Test Driven Development, just with better language.
Blog Driven Development – Think about how to appear smart on your blog, and implement something like that.
Budget Driven Development – Each man is allocated a maximum number of lines which can be added. A little like SCRUM, just with lines of code instead of hours.
Bug Driven Development – Implement program, release, fix bugs, repeat.
Comment Driven Development – Write code comments, then implement what you’ve described. Like Test Driven Development, just without the tests.
Configuration Driven Development – Store everything in configuration files.
Data Driven Development – Start with the data and work your way up from there.
Design Driven Development – Design is art so remember to add the right people.
Development Driven Development – Concentrate on developing instead of testing.
Dialogue Driven Development – Remember to talk to the client and ask questions.
Documentation Driven Development – Write the documentation first, then the code.
Example Driven Development – Write down examples, clear them with the client, then implement.
Feature Driven Development – Focus on developing value-adding features.
Language Driven Development – Use any language you want.
Meeting Driven Development – Don’t code before having a meeting. In fact, don’t do anything without a meeting first.
Model Driven Development – Let the developers off and give the users access to visual programming.
Muffin Driven Development – Punish developers by forcing them to give muffins when they make the builds fail.
Principle Driven Development – Go for the simple solutions.
Process Driven Development – Analyze the business processes, then model the system from that.
Proof Driven Development – Build small vertical slices of an application. Like prototypes, just the other way around.
Reality Driven Development – Take a look at what’s going on in the real world and learn from it.
Requirements Driven Development – Get a hold of your requirements and make the developers work based on them.
Resume Driven Development – Look at your resume and do whatever looks good on it.
Search Driven Development – Delegate responsibility and knowledge to Google.
SKU Driven Development – Strip down your solution to a minimal core, then make addons available.
Specification Driven Development – Add formal contracts to Test Driven Development.
Squiggly Driven Development – Write some code, check if there are any compile errors. Fix them. Proceed.
Story Driven Development – Write stories about your product before writing code.
Test Driven Development – First, write some tests, then make them run.
Wiki Driven Development – Somewhat like Documentation Driven Development, just with a Wiki.

If you want to be Scrum-compliant, add Agile to any of the titles. My own contribution to the list will be “Methodology Driven Development”, which occurs when you look at the list above, and pick one or more to implement in your project.
Of course, the list is probably nowhere near complete. If I’ve left something (un)important out then just comment on it.

 Implementing closures in Java

  • February 23rd, 2008
  • 1:40 pm

There's been a lot of discussion about how to include closures in Java7, and whether they should be included at all or not. Everybody seems to agree that Java already has the poor man's version of closures: anonymous inner classes.
Here's my proposal on how to implement "real" closures: create a folding plugin for Eclipse, Netbeans, IntelliJ which simply folds

CODE:
  1. JButton b = new JButton("press me");
  2. b.addActionListener(new ActionListener() {
  3.   public void actionPerformed(ActionEvent e) {
  4.     System.out.println(e);
  5.   }
  6. });

into

CODE:
  1. JButton b = new JButton("press me");
  2. b.addActionListener(ActionEvent e -> { System.out.println(e) });

Syntax borrowed from Groovy, but any would do. 100% backwards compatibility for free, no compiler modifications needed, support for all Java versions, just with a couple of plugins. Yes, it's cheating, but I don't care, it's been years since I wrote a line of Java code without Eclipse or something like it.

I would do it myself, but I my backlog of ideas to implement is big enough as it is, so if someone else should have the time, please go ahead.

 Keeping track of time

  • February 22nd, 2008
  • 2:01 am

For some reason, companies like to keep track of what their employees are doing, and where I work, it's no different. Keeping track of which projects you work on and for how long gets tedious pretty quickly, and I wouldn't be surprised if quite a number of people have the same experience as me: when you go to the time tracking system, you discover to some degree of horror that you've forgotten to update the system for the last 14 days. Now, what's the chance of you remembering which tasks you worked on and for how long with any kind of precision? Probably none.

This is why I've been working on a small prototype for semi-automatic time tracking. It's based on a simple concept: At regular intervals, a program pops up and asks what you're doing right now. You click one button, and the program goes away. At some point, you can get a report of which tasks you've been working on.
Obviously, this is not completely accurate, but I hope it's better than nothing. If you're interested, you can try it out yourself. Remember, it's a prototype, so there are probably plenty of bugs and missing features, but the basic functionality should be there.

The program is implemented in Java (actually mostly in Groovy), and can be launched via webstart. Java6 is required. Launch the Timesheet application here. If you do try it, please give your comments.
Should you want to reset everything, then delete the .timesheet_db file from user.home.

 String replace and regular expressions

  • February 20th, 2008
  • 11:47 pm

All Java programmers know and use String.replaceAll(), but whenever I need to do something complicated, I always have to create a small test class where I can try out the regular expressions and replacement strings. Yesterday, I finally got tired of creating these test classes, and decided to implement a String.replaceAll on the web. Fortunately, the task was small enough to complete in an hour or two, so I actually got it done.

So, for all your string replacement needs, go to the very advanced replaceall.org website.

Incidentally, this was also my first Grails project. It hardly uses all features - for example, there's no database involved, but it was fun trying anyways.

 Effective Bash

  • February 12th, 2008
  • 12:22 am

More and more people are coming into contact with Bash, primarily through Mac OSX and Ubuntu. All very nice, but most people really don't realize the full potential of the Bash shell, so here are some advices on how to use Bash effectively (note to more advanced users: yes, some of the features are due to other facilities such as readline, but that's not so interesting here). There's also a quite large topic on scripting which will not be discussed here. I recommend the Advanved Bash-Scripting Guide, and you should always be familiar with the manpage for Bash.

Configuration

Place all persistent changes in ~/.bashrc, which will be loaded every time a new shell is started. There's no need to restart the computer, just start a new shell (or type bash in an existing).

History

Use the up/down arrows to go through the recently executed commands. This is basic, these commands will make it even better:

CODE:
  1. export HISTCONTROL=ignoredups
  2. export HISTSIZE=10000
  3. export HISTFILESIZE=10000
  4.  
  5. shopt -s cmdhist

Setting these will result in two things: Repeated commands will only appear once in the history, and the number of commands in the history will be increased to 10000.

Better prompt

Especially when using ssh, it's easy to lose track of which machine you're on. Setting an appropriate prompt can help. My prompt looks something like this:

CODE:
  1. recht@challenger: /home/recht>

In other words, it contains my current username, hostname, and directory. Also, the prompt is configured to set the title of the terminal to the same:

CODE:
  1. export PS1="${TITLEBAR}\[\033[40;37;1m\]\u@\H: \[\033[37;40;0m\]\w> "

Aliases

Often used commands can be alised to a simple command. For example, the editor nano has an extremely annoying feature where lines are automatically wrapped unless nano is started with -w. An alias can make sure this is always so:

CODE:
  1. alias nano="nano -w"

Other useful aliases:

CODE:
  1. alias rm="rm -i"
  2. alias cp="cp -i"
  3. alias mv="mv -i"
  4. alias ls="ls --color=auto"
  5. alias du="du -h"
  6. alias more="less"

Auto completion

Autocompletion means entering a part of a command or filename, and then hitting TAB. If the command can be uniquely identified, the rest of the command is completed automatically, otherwise the possible completions are shown, and more characters can be entered.
By default, Bash only completes filenames, but it can actually do a lot more. This can either be hand coded, or you can use the completions which come with Bash.
The completions file is normally located in /etc/bash_completion. Use it by entering

CODE:
  1. source /etc/bash_completion

After this, almost anything can be completed: ant tasks, make targets, ssh hosts, and much more.Take a look in /etc/bash_completion for the complete list.

One other practical thing to set is this in ~/.inputrc:

CODE:
  1. set show-all-if-ambiguous on

If no unique completion is available, the possible completions are shown automatically.

Keyboard

It's possible to use the keyboard to navigate commands, history and just about anything else.
The available keyboard commands can be seen in the manpage for Bash, but here are some of the most important:

  • Ctrl-a: Go to beginning of line
  • Ctrl-e: Go to end of line
  • Alt/Meta-b: Go back one word
  • Alt/Meta-f: Go forward one word
  • Ctrl-r: Search history backwards. Press Ctrl-r and enter part of an earlier command to find it in the history. Press Ctrl-r to search again.
  • Ctrl-d: Delete character
  • Ctrl-d on an empty line: Exit the shell
  • Ctrl-s: Stop sending data to the terminal. Nothing will be changed before pressing Ctrl-q
  • Ctrl-q: Start sending data to the terminal

Beeping

Just about the most annoying thing any computer can do to me is beep or make any kind of unexpected sound - which is just about any sound not coming out of an MP3 player. The shell beeping is among the worst. Trade it with a flash by putting this in ~/.inputrc:

CODE:
  1. set bell-style visible

Changing directories

The cd command is use to change the current directory. Simple, but there's still room for improvement.

If you mistype a directory, something which actually happens pretty often when you use completion without a unique name and hit enter without choosing the correct dir, an error occurs. However, Bash can also be configured to take a best guess:

CODE:
  1. set -s cdspell

For example, if I have to directories doc and download and type "cd do", Bash will select doc for me. Of course, the correct dir is not always selected, so this option might annoy some more than others.

Typing cd with any arguments will return you to your home directory. Typing "cd -" will return you to the previous directory - nice when executing commands in two different directories.

Pager (less)

The pager is used when displaying text files. In the good old times, this was more, but the GNU alternative is less. There's usually no reason to do it, but just to be safe, do

CODE:
  1. export PAGER=less
  2. [code]
  3.  
  4. The standard configuration of less can be improved, however. My configuration looks like this:
  5. [code]
  6. export LESS='-i  -e -M -X -F -R -P%t?f%f \
  7. :stdin .?pb%pb\% :? lbLine %lb:?bbByte %bb:-...'

This basically enables case insensitive search, quit when end of file is reached, quits at once if entire content fits on the screen, and gives a nice prompt with line numbers. Look in the manpage for less for more info.

Just a few keyboard commands for less: Hit / and enter a string to search. Press n or N to search again. Enter a number and press g to go the the corresponding line number. Press q to quit.

Job control

Commands can be executed in a shell by typing in the command name and arguments. If the last character on the line is a '&', the command will be run in the background. However, when the shell is closed, all background processes are also closed, so don't rely on '&' to run your server processes.

When processes are running in the background, type 'jobs' to see the processes and their status. If you want any of them attached again, run 'fg', possibly with the job number.

An attached process can be backgrounded by pressing Ctrl-z. This will stop the process and release the terminal. If you want the program to continue running while you're doing something else, type 'bg'.

This concludes what I see as the essential features of Bash (and readline and a couple of other things). If you do use Bash on a daily basis, do yourself a favor and continue with the Bash manual to discover more keyboard shortcuts. It might also be interesting to check up on the features of your terminal. I personally use urxvt, which can run as a daemon to avoid unnecessary overhead, plus it has some other nice features such as resizing.

 Talking too much?

  • February 11th, 2008
  • 5:58 pm

Today we had a discussion about which agile practices work, and why some tasks just seem to take longer than necessary. One of the reasons seems to be that we don't really reuse concepts and components very much. Every scrum team has responsibility for meeting their goals and satisfying the customers, but nobody is focused on maintaining a somewhat common architecture, and practices, both good and bad, are not communicated reliably to other teams.
This is not necessarily bad. Most of the developers are pretty bright people, who actually work at companies like Trifork because that way they won't get some Enterprise Architecture(tm) pushed down their throat. Instead, there is an expectation that everybody will strive to do their best for the project.

The whole agile culture empowers the developers - this is one of the core ideas. The developers get to speak directly with the customer, design solutions, implement them, test them, document them - generally the developers are responsible for as much of the development as possible. A good thing, but maybe developers sometimes have a little too much to say. I don't particularly like the term architect (mostly because "whiteboard" should have been prepended), but having Scrum teams without a proper architect doesn't really seem optimal in the long run. By proper architect I mean one who has the capacity to create consistency across projects, and take decisions about key components, languages, and so on. The architect shouldn't necessarily make all the decisions, but some things are just not worth discussing again and again. Examples of this could be whether to use a coding standard or not, or whether to include a completely new and untested technology. Another classic seems to be that decisions are never final. This means that somebody might spend time in integrating a new tool or component, even though an earlier decision was made against it.
Granted, some of the decisions made on a project are just plain wrong, at least in hindsight, but it just seems that experimenting with new technologies on a project which is due to deliver a working product isn't the best idea.

As usual, the problem comes down to communication. Scrum and XP handles team communication pretty nicely. We have daily scrums, iteration meetings, retrospectives, and so on, but there are no practices to establish inter-team-communication. You could, of course, go for something like CMMI, which has almost complete focus on organization-wide communication, but that just doesn't sound very good (theoretically it should be possible, though. My master's project was about exactly this). In other words, we need some solid agile practices for enabling communication across the organization.

I wish I had some good ideas as to how this should be done. Ask Jeff Sutherland, and he'll probably begin talking about scrum of scrums, basically arranging teams hierarchically, and letting the scrum masters communicate between the teams. On the face of it, this looks like a good solution, but somehow I don't quite like it. In really large organizations, it's probably the only way, but is it appropriate when you have 50-100 developers?

My best proposal is to separate the day-to-day development from the talking and the experimenting. Development happens in scrum teams, and the teams live their own lives, but the design decisions are coordinated with what we could call architects. Maybe librarians would be a better title, because their main purpose is to know what others are doing and have done, what has worked, and what has not worked. The talking and experimenting would take place at other times. This could be the 20% time which Google employees have to spend on something else, it could be something like the JAOO meetups at Trifork, it could be video blogs. Basically anything, the important thing to somehow promote a culture where both learning and teaching is essential. Of course, this requires some ongoing investment from the organization, like the 20% time.
If this separation exists, we as developers might be able to focus better on creating actual value, and we might also become better at learning from each other. It's important to notice that the separation is there to avoid too much distraction when developing. However, everything good and bad that comes out of the talking and experimenting should be taken into consideration when making important architectural decisions - it's just a question of where the experimenting takes place, and when the results are brought back into a project. Most of the time, our projects are relatively short, so after committing to some architecture, it doesn't really pay off to change it.

I expect some of this will be addressed, for example at future JAOO and QCon conferences. In the meantime, it would be nice to hear about inter-team communication patterns - how to ensure common knowledge, and how new ideas, technologies, patterns, principles, and so on can be distributed in an organization full of independent teams.

 Updated smugup.sh script

  • February 10th, 2008
  • 11:35 pm

I got a comment that my SmugMug uploader script had broken after the last upgrade. It turned out that my XML parsing with sed wasn't exactly resistant to change, so the wrong field was printed from the returned XML.
I've changed the XML parsing to use awk instead, hopefully in a way that's a little more resistant to changes in the format (although it's not exactly perfect, but I don't want to involve a real XML parser).
The new version is 1.1, and can be downloaded here.

 Hindsgavl ‘08

  • February 9th, 2008
  • 12:36 pm

I've just returned from Javagruppens annual conference in Hindsgavl, which had "Enterprise Open Source Java" as the main theme. The agenda was dominated by how to use dynamic languages such as Groovy an (J)Ruby and how to scale systems. About 50 people attended, so the conference was in no way like the larger conferences, but the speakers were all very competent and good.
The most important outcome of the conference was that I became aware of several new possibilities with for example Groovy and JRuby. Now I just need to find some time to try them out.

 Commercial break

  • February 6th, 2008
  • 12:11 pm

I don't usually do commercials on my blog, but exceptions must exist. As some might know, I'm not the biggest fan of dynamic languages such as Ruby, but they still have their charm. Should you think the same, you really should attend the Ruby Fools conference in Copenhagen. The conference is organized by Trifork, and is the first Ruby conference in Denmark. There's a quite impressive lineup of speakers, and the most recent addition, and most exciting, is Yukihiro "Matz" Matsumoto, creator of the Ruby language.
Unfortunately, I'm scheduled to attend the... how shall I put it?... well, let's just say not quite as interesting OIO IT Architecture Conference, so no Ruby for me.

Speaking of conferences, I'll be going to Javagruppen's annual conference at Hindsgavl tomorrow. This is a pretty small conference, but I expect it to be both interesting and with a relaxed atmosphere with plenty of opportunity for (small)talking with the other participants.

And as a final word about conferences, I'll just remind that Trifork is once again organizing a trip to JavaONE in San Francisco. More information is available at trifork.com.

 Calendar and mail

  • February 4th, 2008
  • 11:23 pm

My favourite choice for mail has long been Thunderbird, but I've never really found a calendar application which I was satisfied with. This has changed, thanks to the Lightning extension for Thunderbird. This solution, together with the appropriate provider, integrates Google Calendar with Thunderbird. For some reason, I've never really found the web-based solutions usable, but integrated in Thunderbird, it's much better, and I'm actually using a calendar now - something I haven't been doing for quite a while.
Of course, this has in no way stopped me from scheduling several meetings at the same time, but now I at least find out about it a little sooner.
As an extra bonus, it's possible to find public holiday calendars, for example the Danish holidays. Sweet.