8 Steps You Can Make Before Huge Upgrade to Make it Faster, Cheaper and More Stable

Similar questions fill my personal and Rector email in the last 3 months. It's hard to give a reasonable answer without actually seeing the repository, so I reply with follow-up questions to get get more details.

Yet, I've discovered there are few repeated patterns, that make the upgrade easier and that most projects can do by themselves before migration starts.

These points make any code migration faster and easier. It also decreases the time required to understand the code by a person who sees the code for the very first time.

Based on my experience with 10+ legacy projects of size 100 k-800 k lines, these points can be applied generally.

1. PSR-4 Standard

What are the benefits of using PSR-4 standard? If you use it, all classes are unique, autoloaded and easy to relate to file path. We need that for effective coding - so we don't have to care about it - and thus also for effective migrations.

If you have PSR-4 standard applied, your composer.json looks like this:

One project took me 2 weeks to ask for SSH keys 3 different people by 7 mails, 4 callings, one VPN... I still can't run composer install.

Flawless install under 2 hours is a luxury.

If you make composer install under 2 hours,
the migration is ~5 % cheaper.

6. 70 % Code Coverage

When we come to a completely new project, we need instant feedback, if we break something. It would be nice to have 100 % code coverage, but even my open-source project rates as high as 75 %.

It's like having CTO who rose the project constantly at your side for any change you make.

We don't care if it's functional, integration or unit tests - we just need the coverage to be sure nothing is wrong with the code. Without tests, any change in the code is like shooting blindfolded in the dark without hands at a target that is both invisible, moving and Shrodinger's cat.

If you make it pass ~70 % code coverage,
the migration is ~50 % cheaper.

7. Not Versioned Vendor

I know it sounds crazy again, but it's not. Many projects we get have 2 vendor directories. One is versioned by composer.json and the other is versioned... somehow.

Why use composer patches or custom forks, if you can version packages locally. It's fast, it's healthy, it's all you wish for.

But getting packages out of local vendor is the real adventure. We need to compare every file in both directories, discover guess the version, test hope it's the right one, prevent from duplications with real vendor and so on.

If you don't version your vendor,
the migration is ~10 % cheaper.

8. Solid Gitlab CI

What if you have all the items above? When is the last time you've checked them? You don't know?

If the answer is not "at every commit", it's not good enough. You need to have CI. And I don't mean Bitbucket CI.

Why? It's not that Bitbucket CI is worse than Gitlab CI or GitHub actions. It's the ecosystem support. The Gitlab CI has the longest support for CI of a private project there is.

That means:

a lot of tutorials

a lot of people who know how to configure it

a lot of custom Docker tutorials

community support in case of troubles

As a side bonus, it's free for private projects with unlimited users and 2 000 build minutes per month (I've never reached that).

If you use Gitlab CI on every commit,
the migration is ~10 % cheaper.

Worth It?

Let's say your goal is to migrate the whole framework or switch a legacy framework for a modern one. If you had skills, time and money to do that, you'd probably be there. It takes the experience with many legacy migrations to there effectively without years of time and full-rewrite.

But... these steps above don't depend on such experience. You can implement in your in-house team. Such work will reduce work on our side and make your code solid on your side with not such a big overhead.