We have now completed a full modularization of our application. What used to be a single application target with 8 Swift files and many hundreds of lines of code is now 7 Swift modules, each with just one or two files, and each file under 200 lines except for our SwiftUI helpers file and UIKit files.
Previously any change to a file, no matter how small, would trigger a build of the application target, and we would just have to hope that Swift’s incremental compilation algorithm was smart enough to not build more than is necessary. Swift’s incremental compilation is really, really good, but there are still times it gets tripped up and a build will take a lot longer than you expect. Or worse, if you need to merge main into your branch to get up-to-date with what your colleagues are doing, you will most likely trigger a full re-compilation of your entire project because many things have probably changed.
Now, with feature modules, we have a lot more control over what gets built and what doesn’t. If you are deep in focus mode on just the item view, then you can choose to build only the “ItemFeature”. Then you should feel free to merge main into your branch as often as you want because, at worse, you will only trigger a rebuild of the “ItemFeature” module, which is a lot smaller than the full application. This can be a huge boon to productivity.
But, we can take this even further. Right now the “AppFeature” has a pretty significant amount of logic that spans the responsibilities of many feature modules we have just created, and that’s the deep linking functionality. The “AppFeature” is handling deep linking for the entire application, even though the only view the module holds is a tab view, and the only deep linking logic important for that view is to figure out which tab we should switch to. All the other deep linking logic just delegates to navigate(to:)
methods that are defined on the child view models.
What if we could fully modularize our deep linking logic? Not only would we move the navigate(to:)
methods to each feature’s view model, but we would even move the parsers themselves to the feature modules. That would mean we could even work on parsing and deep linking logic in complete isolation from the rest of the application, which would be pretty incredible.
Let’s give it a shot.