What it isn’t
According to Dictionary.com, Legacy, used as an adjective in the term Legacy Software, the definition is:
leg·a·cy | /le-gə-sē/ – of or relating to old or outdated computer hardware, software, or data that, while still functional, does not work well with up-to-date systems.
The key to this definition is the “while” clause. We know that old software doesn’t have to be called out as ‘legacy software. As an example, what about Linux? The Linux kernel is an old piece of software, but no one would classify that code as a piece of legacy software. Why is that? There are some key aspects of the software that have made it continually relevant over the years. There is an argument that it is the most relevant it has ever been.
Linux began in 1991 as a personal project by Finnish student Linus Torvalds: to create a new free operating system kernel. The resulting Linux kernel has been marked by constant growth throughout its history. Since the initial release of its source code in 1991, it has grown from a small number of C files under a license prohibiting commercial distribution to the 4.15 version in 2018 with more than 23.3 million lines of source code. (History of Linux)
Why isn’t Linux an example of Legacy Software? I believe we can identify some key things that lead to non-Legacy Software.
- Strong leadership – Linus Torvalds has been involved from the beginning of the development effort and has implemented tools and processes that have established good software practices throughout the years, while still allowing other developers to contribute the software.
- Build Tools – Using traditional build tools the software build is automated so that anyone can download the software, build and deploy it on pretty much any off-the-shelf Intel compatible desktop.
- Well Tested – Through Linus’ strong leadership and his attention to delivery details, each release is fully tested. The focus of this testing is automated testing, as might be expected from the size of the project, manual testing is not an option.
- Relevant – The software is probably more relevant today than it was in 1991 because of the user involvement in the software.
- Documented – It is expected that as changes are made to the kernel they are fully documented, peer reviewed and the pull request accepted by Linus Torvalds.
- Good Developers – Because of its good leadership, testing and continued relevance, many developers are interested in continuing the development effort in order to improve the software.
- Culture – Linus and the Linux community have built a culture that creates complete, relevant and quality software releases.
These key attributes of the development history allow for a legacy of relevant software, not legacy software.
What is it
According to Re-Engineering Legacy Software by Chris Birchall, the definition of Legacy Software is:
” A software project that is difficult to maintain or extend. “
– Re-Engineering Legacy Software by Chris Birchall
This definition is more straightforward and relevant than the previous one and it helps us understand why it is such an important topic. Software is used by businesses to help them be more successful. Most software helps companies become more efficient or effective, ultimately making them more productive and thus more profitable.
An effectivity gain would allow a company to do more with the same, an efficiency gain would allow a company to do the same with less. In either case, there is no magic, the software is automating what people are or could be doing, but doing it more consistently and/or at a larger scale. Therefore, it is critical to understand that software should first be successful in providing this value to a company but also, and importantly, must be written in such a way that it can be maintained and changed so that this value can continually exist or even improve as the company changes.
This is such an important aspect of understanding why legacy software is an important topic for information technology organizations. With this in mind, there are some key aspects of legacy software that exist and can be identified:
- Old – the software, its language, and its libraries are old. This by itself isn’t a problem, but as hardware, networking and other integration software is either added and/or changed, this can cause issues that must be addressed through library or other types upgrades. As in the discussion of Linux above, the software and development staff has to put in the work to make this a non-issue.
- Large – Not all software is large, but oftentimes software that is important to a company and that is a legacy software concern, tends to be on a larger scale.
- Important – Along with large, if the software is a topic of legacy software within a company it is most likely important to the company and often crosses many parts of the organization or is a key aspect of the organization.
- Inherited – Legacy software is often inherited and not created by the current set of developers. In the absence of documentation, automated testing and build tools changes can be brittle, not easily tested, ignored or avoided at all costs by the development group.
- Untested – Legacy software does not have automated tests.
- No builds – Legacy software does not have automated builds.
- Brittle – Legacy software is brittle so that a change in the software may lead to unexpected failures, many times in areas of the software not related to the change.
- Technical debt – Technical debt is code that was baked into the software knowing it needed to be changed, but never was.
- Fear – Because of all the prior attributes, developers tend to shy away from making any kind of change to the software that doesn’t need to be done. So rather than hearing and understanding the user, the developer will only do the minimum to get done.
The outcome of these attributes is a software product that becomes very difficult to hire and keep developers to maintain. In tight labor markets, the lack of talent to maintain legacy software is one of the, if not the most important obstacle to maintaining and extending legacy software.
Assuming legacy software exists within your organization, what are your options? On the continuum of options that can be done to address legacy software, the two ends of the spectrum are:
- Keep the software,
- Rewrite the software.
This may seem overly simplistic, but any option is somewhere on the continuum of these two options. Oftentimes, keeping the software is the option only until it can be rewritten, or it may be that you completely rewrite a portion of the software.
Keep the Software
How can keeping the software be a solution to Legacy Software? Remembering that old doesn’t necessarily mean legacy, but rather the fact that it was not maintainable or extensible. If we address the reasons software is not maintainable and extensible, then it stops being a legacy software product.
I am going to recommend the books, “Working Effectively with Legacy Code”, by Michael Feathers and “Beyond Legacy Code: Nine Practices to Extend the Life (and Value) of Your Software”, by David Scott Bernstein which both provide key ideas on how to work with and extend legacy software. However, rather than getting too detailed discussion, important straightforward steps must be taken to make these books useful to any of your efforts.
- Create a build that implements the “Return Test”. The return test is a term that I have used to describe a build and deployment process that requires a developer to type “build” and hit RETURN. If this cannot be done, the software cannot be maintained or extended. Software development is difficult but to also require the development to assume a fluid deployment, development becomes nearly impossible.
- Create repeatable independent software tests that can be executed each time the software is changed. This is a very important step to maintaining and extending legacy software. This step may seem a little like building a car while driving it and it kind of is since the software is actively changing. However, one way to accomplish this is to implement the tests in the areas of the software that is currently changing. As an example, let’s assume some work needs to be done with an Invoice, build in the time to create unit and integration tests for the Invoicing module, ensure the tests succeed with the current code and then make your changes and use the tests to confirm the module still works properly.
- Identify seams in the software and then replace those areas that are appendages to the core software. An easy example of this is a 3rd party integration or a user interface upgrade using a RESTful integration layer. These can be replaced while not replacing core business or database layer logic.
The following is a list of common work that is required for successfully maintaining and extending your legacy software within your company.
- Automate the testing and builds
- Make incremental changes with the end in mind and release
- Create good documentation into and out of a release cycle
- Provide good leadership and talent
- Extend with the user in mind
- Fix technical debt as it is found
Rewrite the software
A rewrite of working software that provides value to a company is a major decision for any organization to make. This type of decision usually involves company management and would include a budget outside of existing maintenance. For this reason, a complete rewrite is rare.
However, many times a complete rewrite can be a long term objective so that the maintenance and extension of the software is done in such a way that over time the software is rewritten.
A “complete rewrite” decision is most likely made when there are substantial changes that are needed to the existing software because of business requirements or technological realities.
A new business opportunity is a great example of a business reason. Another good example may be business growth or decline. These business drivers many times create a need that just cannot be handled with the legacy software and to change the software would be too heavy of a lift.
The Windows 7 ‘end of life’ is an example of a technological reason. We worked with a company that had a Windows 7 embedded system that had to be rewritten. In addition to this technical driver, there were many features that had to be addressed in order to handle customer needs. The rewrite effort moved the software from Windows 7 to Linux. Although this was a major rewrite, we were able to use core sections of the business logic. This was an important part of the architecture discovery phase. It was still a major undertaking, but we didn’t have to recreate logic that had been around for 30 years.
No matter how you decide to handle your Legacy Software, automating the testing and building of the software is a requirement. Whether keeping legacy software or rewriting legacy software much of the work is the same, however the objectives do change. The work being performed (keep the legacy software or replace the legacy software) is determined by the end goal. If the ultimate objective is to keep the legacy software, decisions made while architecting the solutions will most likely drive to different conclusions than if the objective is a rewrite.