We’ve already talked about what modularization is, and why a team might want to architect their codebase in such a way. But what are the real life advantages to having multiple units of code to work in? Lets take a look.
As touched on previously, modules that are loosely coupled to other modules in the codebase are considered highly portable (at least when moving to another Apple related project). Portability is the measure in how easily we can transfer a portion of code from one codebase to another. Meaning a highly portable module that contains a lot of logic could be bought into another project that utilizes the same logic. For example, if you’re at a company working on lots of projects, having a sharable module that contains your networking code could be a huge benefit when considering the alternative of having to rewrite your networking stack each time.
Less toe stepping
Oh the woes of merge conflicts. Merge conflicts are a big annoyance, even on smaller teams. Teams that are all working on a single codebase have felt the pain of wanting to merge your work into
main, only to be stung by having to deal with a heap of merge conflicts. These merge conflicts can add additional risk to project, with the uncertainty of knowing if you’ve resolved the merge conflicts correctly, particularly in a codebase without a reliable test suite.
Modularity in a codebase isn’t going to resolve all of the issues with merge conflicts, but it does a decent job at reducing the amount you’re impacted by them. In a project where you’re able to divide the work up in a way that means each team takes ownership of separate modules (or at least, fewer people are working in the module you’re in), you’re able to avoid stepping on the toes of others, and reduce the chances of a nasty merge conflict.
Decreases in build time
Re-compiling is quicker
This is a two fold thing. The first portion of this is that Xcode will only need to recompile the modules with changes in it when doing an incremental build. So if your piece of work only touches the settings screen, which is contained within its own module, then Xcode won’t need to build the code backing the login page.
The other, and arguably more important point is…
We’ll get onto modularization strategy in later blog posts, but for the time being, if you imagine a world where you have a module dedicated to the
login screen. Assume that
login module is very autonomous, and handles all of the use cases that a
login feature could have.
What this means is you can build a sample app that includes that
login module, allowing it to run on its own, without the cruft of the rest of the codebase having to launch, as you’re launching an entirely separate app.
This also gives you the flexibility of writing UI tests against this sample app. A complex topic that we’ll dive into more in a later post, but it is an option that opens up and may allow for less brittle UI tests.
Nicole Forsgren, Jez Humble, and Gene Kim are the trio behind the annual "The State of DevOps Report". The 2022 installment can be found here. These reports, along with their breakdown of the research in their seminal "Accelerate" book, touch on how a loosely coupled architecture can be one of the tools used to create a healthier work environment.
Their research states that a loosely coupled architecture is one of the tools that directly improves Continuous Delivery performance. Having modules with a clearly defined scope, means that making changes to those module become more manageable. More manageable changes mean there is a reduction in stress when it comes to maintaining those modules as you’re more confident in the changes you’re making. The reduction in stress that comes from being a high performing software delivery team is a tangible, measurable metric when it comes to workplace culture.
(As an aside, I put my full recommendation behind their "Accelerate" book, really incredible bit of work).
The one thing all of these things share in common is the ability to save the team time. One of the first questions around a modular codebase that is often asked is "Is it worth the effort?". And whilst there is no doubt there is a time expenditure required to work towards a modular architecture, particularly if coming from a monolithic codebase, the pay off in time saved in the long run is clear.
Plus, a potential for a reduction in stress when used with other Continuous Delivery tools, who can refuse that?