It’s a common misconception that the only purpose of source control software is to enable a team of developers to work on source code without overwriting one another’s changes. While a source control system does facilitate this kind of method of working, there’s much more to the tools known as source control or version control systems.
The Elements of Source Control
In this section, we’ll review the basic features that are common to source control systems and see how they work in the software development process.
The Repository
All source control systems feature a repository where source code and other files related to the software product are stored. Developers retrieve source code from the repository, make changes, perhaps add some new files, and finally commit (or check in) those changes to the repository.
Not only does the repository store the current version of the source files, it also tracks every single change that’s made to a file as developers commit new versions of files to the repository. If you use a source control system, you can look at the entire history of any file in the repository to get a clear idea of the specific changes that have been made to it over time. Sometimes, just knowing what’s changed since yesterday can help you track down an elusive bug that appeared today.
Perhaps if an engineer had checked in the parameter file, the Titan mission would have been successful—it’s hard to say with 100% certainty, but I’m sure the chances of success would have been better. Likewise, you can dramatically decrease the risks to your software project by keeping the assets required by that project in a repository. The repository should be located on a secure machine and backed up regularly, of course.
Labeling
Labeling, also known tagging, is a feature of source control systems that allows you to apply a friendly name to a specific version of your files. It’s a good idea to label files every time a product is built—perhaps with just the name of the product and an auto-incremented build number (WhizzBang.1186, for instance). If a problem is found during a test, you can delve into the repository and identify the exact set of files that were used to build the version of the software you’re testing.
Another great time to apply a label is whenever you deliver your software to the outside world. Imagine, for example, that build 1186 of WhizzBang has passed all tests and is ready to be delivered to customers. You can apply another label to this set of files, perhaps calling it Whizz Bang 1.2 if you’ve already delivered versions 1.0 and 1.1. Now, if, in six months’ time, one of your customers calls with a severe bug report for version 1.2, you’ll know exactly what was deployed to the customer, because the files were labeled. A developer can simply retrieve all the files labeled Whizz Bang 1.2 and reproduce the problem.
Branching
The most common development workflow involves every developer always retrieving the latest version of code from the repository, making changes, and checking those changes back into the repository. If you think of your project as a source control tree, the latest version of the files represents the trunk of the tree.
Sometimes it’s necessary to branch away from the trunk to perform parallel development on the product. Fortunately, source control also provides the ability to branch your project. For instance, suppose you’ve identified the problem in Whizz Bang 1.2, and now you need to get a fix to the customer. You could apply the fix to the latest version of the code (the trunk), but the rest of the product may not be ready for deployment. Perhaps you’re already one month into a three-month project plan for version 2.0, and many new features are still incomplete. You can’t send an incomplete version to the customer, so you can’t build the latest version as a fix.
In this scenario, it would be prudent to apply the change to the stable version of the product labeled as version 1.2. Source control will allow you to branch the main tree at the version 1.2 label. While some developers begin to work on delivering version 1.2.1 from the branch, the rest of the team can continue working on the main trunk to finish the version 2.0 features. A good source control system will automatically merge changes made on a branch back into the trunk, in effect adding the fix to version 2.0 also.
The scenario above is just one example of branching in action. Branching is a powerful feature and there are many different ways to use branching to meet the style of your development, so make yourself familiar with the capabilities of the versioning system you choose.
Who Should Use Source Control?
Obviously, source control is valuable for teams of developers, and those working in a professional capacity for paying clients. Perhaps you’re a solo software developer, or just experimenting at home with some code. If you’ve read this far, hopefully you’ve already realized that source control isn’t just for big development teams. How many times have you started to make massive changes to a code base, but after an hour, decided that you don’t like the new approach, and wished you could roll back to what was working before? Well, if you use source control, that wish is easily granted.
It’s also advantageous to use a repository for storing all of your code, and to perform backups of this repository regularly. Tracking history, versioning, and labeling are all there to help you manage your code—even if you’re “just tinkering!”
Source Control Tools
Source control products are available to fit every project and budget. If you’re not using source control today, I hope we have convinced you to start using it tomorrow. Once you’ve embraced source control, you’ll find it to be just like oxygen—you won’t notice once you have it in place, but you’ll be acutely aware of how much you rely on it once it’s gone.
TortoiseSVN is popular because it integrates well with the Windows Explorer shell, but many other options—open source and commercial—are available.