Why Do You Hire Programmers?

Why do you hire programmers? Seriously, why? Think about it for a minute.

If your answer is “to write code”, then think about it some more. I don’t know what your reason is, but I’m pretty sure that’s not it. Writing code is merely a means to an end, not an end in itself.

Do you want to create internal systems that keep your company running? Or are you looking to produce a product for sale to customers? Maybe you’re doing something else entirely?

I’ve seen this question presented from the marketing side a few times, usually in terms of “features” vs. “benefits”1, but the same principle applies here. Just as you need to present a benefit to your customers when selling to them, you also need to consider the benefit that you want to obtain when you’re buying.

Probably the most common issues I see in this area are companies looking for a programmer who knows a specific language, or uses a specific database, or has experience with some other particular tool rather than focusing on the actual objective of the project: the functionality that they require.

This is not to say that you should never look for someone who can use specific tools. If you’re adding on to an existing Java application or if you have an existing team of Java developers that you mean to add to, then you’re probably going to want someone who can work with Java, and for good reason.

If you’re building something new, though, then you’re likely to be better served by finding someone with broad experience and the ability to create what you’re looking for, then asking him what the most appropriate tools would be. Since you’re hiring an expert, use his expertise. Any genuine expert should be able to clearly explain the advantages and disadvantages of different options to you in terms you can understand, no matter how technical or non-technical those terms may be.

Just don’t be surprised if the best option ends up not being the one that you would have chosen if you had started by picking the tool.

What have you hired programmers for in the past and what would you want to hire one for today?

 


1 Basically, the concept is that you don’t want to sell the feature “our product has X”, but instead you should sell the benefit that “our product allows you to do Y”.

     

Case Study: CyberPenguin

In late 2007, I ran across a guy who was preparing to open a Linux-based internet cafe named “CyberPenguin” in the Philippines. After discussing his needs, he asked me to write a custom billing and workstation management system for the cafe’s use. In 2008, he came to me again to request some additional features, which I was quite happy to help him with. With that expansion complete, he has prepared a case study on the project, which is now available in both online (HTML) and printable (PDF) versions.

Looking back over it, I have to say that I really enjoyed this project. Not only was CyberPenguin’s owner great to work with and provided some of the best specs I’ve seen from any of my clients, but he was also always willing to discuss their content and to consider any suggestions I had for improving on his design.

Features

The case study itself provides fairly complete lists of the original functionality and what was added in the expansion project. The only thing that stands out as missing was the one part that I was least sure of being able to work in smoothly: Promotions.

The original spec called for an extremely flexible promotions structure, allowing operators to define various combinations of times of day, days of the week/month, minimum purchase amounts, etc. under which a user receives either a flat bonus amount or a percentage bonus to purchases of credit on his account.

Previous experience with calendars and scheduling software gave me a pretty good idea of how to handle the infrastructure behind the promotions functionality, and even to make it more flexible, allowing the criteria for promotion eligibility to be mixed and matched in any way desired rather than only the specified combinations. But I expected designing an interface to control this flexibility without overwhelming the user to be a somewhat more daunting task.

In the end, I was able to come up with a clear, simple way for users to specify a promotion to be, say, “Top up account by P10.00 and get 15% extra from midnight until 6:00 every 4th Monday, Wednesday, Friday.” And, yes, the interface is also able to describe the promotion details in English - that sentence was copied and pasted directly from it.

Technology

CyberPenguin runs on Ubuntu, which is derived from Debian GNU/Linux - my preferred operating system - so I was already very familiar with the server environment that I’d be working with. The workstations also run Ubuntu, under the control of DRBL (”Diskless Remote Boot in Linux”), which was new to me, but I was already familiar with other Linux-based thin client and diskless workstation setups, so it didn’t present any issues.

In addition to the Linux operating system, the rest of the application was built on Apache 2, MySQL 5, and Perl 5.8, making up a standard LAMP (Linux/Apache/MySQL/Perl) environment. In addition to LAMP for the web interface, the application makes use of Perl programs run as scheduled tasks (by cron) each minute and each day to handle the billing and accounting details.

     

Why Save Partial Data?

In Minimize Data Requirements, I talked a bit about allowing users to save incomplete data because there’s no reason to insist that all data must be provided before any of it is accepted.

While that may be a good negative reason (”there’s no reason not to”), there are also positive reasons for allowing this:

It makes your users’ lives easier.

Are you perfectly organized at all times? I know I’m not.

Requiring that saved data must be complete and valid (or at least valid-looking) at all times demands perfect organization from your users. It makes them collect all of the information you want up front and have it all available at the same time when they enter it. Removing that requirement means that they can enter as much as they know right now, then find the rest and come back later to finish.

It provides a record of user actions which were started, but not completed.

Suppose you have an online store for which users go through a series of three pages in the course of placing an order. Do you persistently store the partial data at each stage of the process or do you just keep it in the active session and write it all to the database at once when the final form is complete?

If you’re smart, you’ll make a permanent record of it at each stage. This information about what items a user started the purchase process for, but didn’t actually buy, can provide valuable insight into buying habits. If you’re using a recommendation engine (”people who bought X also liked Y”), then information about what users almost bought is almost as valuable as information about what they actually bought.

More importantly, though, this incomplete transaction data can highlight issues with your site’s effectiveness. If 90% of your users are starting a transaction, but abandoning it after the second step, then perhaps you should take a hard look at the third step (and, while you’re at it, make sure that the server is completing step two in a timely fashion) to determine why they’re not continuing at that point.

Incomplete or invalid data can show what mistakes your users are making.

Users will make mistakes and they will submit invalid data. That’s as inevitable as death and taxes.

Most software ignores invalid submissions, beyond throwing it back at the user along with an error message.

If yours saves it anyhow, though, then these invalid submissions give you a window into your users’ experience that will show you what mistakes they’re making. Once you know what mistakes are being made, you can attempt to determine the cause of the mistakes and make it easier for the users to get it right the first time instead of just scolding them for doing it wrong.

Like the data I’ve been talking about, I’m sure that this post is also incomplete. What other benefits or drawbacks are there to saving partial or incorrect data instead of rejecting it?

     

The Temptation of the Untried

The technology industry, by and large, is inhabited by early adopters. It’s how most of us got here, after all. You learn to work with “high-tech” equipment by doing it and you do it because you want to play with the latest shiny new toys.

But the latest, of course, is also the least stable. The most likely to have problems. The biggest risk.

Staying on top of the latest-and-greatest tech works out well on your own time, at least for those of us who like to tinker and don’t mind doing a bit of troubleshooting when the inevitable problems arise. As a professional, though, that’s rarely what’s best for clients.

On the other hand, stagnation isn’t good for anyone. Newer technology is needed to take advantage of the improved tools and techniques which are constantly being developed. Fifty-year-old mainframes running code in languages just as old are not a strong target for new development today, no matter how stable they may be.

This creates a constant tension between the desire to make use of the new and the need to retain the reliability of the not-so-new. It’s a tricky balance to get right and I see a lot of software developers who give in to the lure of the latest version, only to get burned when it crashes.

I even succumbed recently myself…

About two months ago, I was debating with myself whether to clean up the web application framework that has grown up out of several projects I’ve done and continue using it or to switch over to an existing framework. (I had previously looked at the major existing frameworks and found them wanting, but I make a habit of checking in on them once or twice a year to see if either they or I have changed enough that I’d want to use them.) As it turned out, I found that there was a new framework in town, created by a well-known developer with experience in such things, which avoided many of the pitfalls of the existing frameworks, so I decided to pitch in and help out with development and debugging.

It turned out to be much less complete than I had initially believed and, a month later - practically to the day - it pretty much disappeared.

During the time I was initially evaluating it, I had also been discussing a project with a potential new client and had mentioned it to her. She also thought it sounded great and was very interested in having me base her project on this new framework. Fortunately for me, the project ultimately didn’t happen, because, if I had committed myself to build it based on this shiny new framework, I would not have been able to do so without having to invest far more work than expected into completing the framework first.

How do you prefer to maintain a balance between the latest-and-greatest and the tried-and-true? Have you ever been bitten by this preference?

     

Minimize Required Data

There’s a long-standing tendency for software to enforce completeness and consistency in stored data. It has never truly been necessary in the real world and it has become something of a monster with the rise of the internet as websites seem to be constantly outdoing each other to collect every conceivable piece of information about anything of interest (usually, but not always, their users) and make every item “required”, refusing to accept any data until all data is provided.

This is the wrong approach. As application designers and developers, we should be minimizing the effort we require from our users, not adding to it.

I recently encountered a blog post on Rethinking the Comment Form which, among other things, suggested that there’s no reason for a blog comment form to require - or even request, really - an email address unless the user requests to be notified of additional comments. This is a step in the right direction and provides my first principle for minimizing requirements:

If you will never use the information, don’t request it.

In most cases, that can be expanded slightly to “if you will never use the information for the user’s benefit“. If your only use for the information is to sell it to spammers or “marketing partners”, that doesn’t count.

The second principle expands slightly on the first:

If you won’t use the information immediately, don’t require it.

The first was pretty conventional, at least if you’re not talking to marketers. The second is a bit bigger of a step. It means that, if you’re not going to be sending someone postal mail today, then it’s perfectly OK for them to enter an address with no ZIP code. Or a phone number with no area code.

Yes, yes, I know… “What about data integrity?!?”

Which is a good question. What about data integrity? If you’re not going to use the information yet, then why does it matter? Sure, you definitely do need to get that ZIP code before sending them a letter, but, until you have a letter to send? So what if you don’t have it?

This then leads to:

Even if you do need the information, accept its omission.

Let the user leave it blank. Really. You can remind them each time they log in about important information that needs to be completed, but there is no excuse for refusing to let users enter partial information now and then come back and finish it up later.

The only potential exceptions are a username and either a password or an email address (so you can send them a password). This is sufficient to allow them to return and provide whatever other information may be needed at a later time.

Of course, if you use the email address as their username, then that leaves exactly one piece of required information. You can’t get much more minimal than that.

Do you have any other suggestions for good ways to minimize the load on your users of providing information?