It’s been a while since we published our project template back in 2018, actually, it is a lot older, I’ve found the first commit in our private repo in 2015. That’s quite some time now. We improved it a lot over those years, but that sort of stopped around the end of 2020. For various reasons, we haven’t updated since, but that period ends now. We’ll make a quick walkthrough over its evolution and then cover up the news and maybe even the future. 🔮
Good old memories
I just opened the very first commit of our template to see what it looked like. Well, it is funny. 😁 As the template was basically one of our projects that was stripped of anything that was not necessary, it was in Objective-C of course, the only dependency manager was Cocoapods. Environment switching relied on build configurations, projects were monolithic, pretty funny.
Then we moved to Swift and decided to improve our build times a bit, so we did a little research. We found out that switching build configuration when we need to switch the environment isn’t really optimal as switching build configuration requires a clean build. To address that we moved the environment switch to the build phase where it just copied the correct list file to the app and introduced build schemes named after each environment. That worked nicely even though it is quite error-prone.
After switching to Swift, improving build times became a never ending story. We need to come up with another improvement. In our case it was switching from Cocoapods to Carthage, which meant that we can compile our dependencies just once before starting to work on the project and until they are changed, there is no need to compile them again. Then we started using Rome so the whole team and CI could share artifacts compiled by Carthage. Around that time our template was published to GitHub.
The next big milestone would be the introduction of Tuist to our stack. That meant a huge leap forward towards modularization of our apps, which meant that we could improve our environment switching, simplify our project configurations. Since then we rely on it a lot. This means that we are now at the end of 2020, so let’s see what happened next.
A long hibernation 🐻
For years nothing happened in our repository, which did not mean that no development was done. It just happened that we basically created a new template when starting some of our new projects. We did not feel it was a good idea to publish it when we do not have enough experience using it. But then we were starting more and more new projects and all those project bootstraps looked like: "Take project X copy this and that and you are ready to go." That was less than comfortable so the need to update our template arose.
This got us thinking about how we could improve the template to meet our sustainability goals. ♻️ The biggest issue we had with previous template versions was that once we started a project, it was very difficult to update the code that was part of the template, in some cases it was impossible. We always had the idea that it would be great if our template could be a library, that would be easily updatable. The nature of some code was not suitable for it or we weren’t smart enough to make it suitable. But as our stack evolved those limits disappeared, the biggest game changers were Tuist and Carthage (even SPM would work nicely for us).
The stuff like shared build phases and project structure has found its place in our brand new Tuist plugin so issues we find in those build phases can be easily fixed on all (not just only our) projects easily. The next step was identifying code that actually did not belong to the template and moving it to our ACKategories library, which is designed for such things.
And finally, rewrite the code that was left in a manner that it can be used as a library. This was the most challenging part of the process because it is impossible to think about all the possible cases that you need to cover, but still, some things like networking could be generalized and reused throughout all our projects. So we did that, currently, our AckeeTemplate library has three components:
- template library itself, which contains networking code, theming code and interface of our force update feature
- push manager is the way we are handling push notifications in-app, needs to be a separate module so we can opt-out of it
- Firebase fetcher which is our implementation of force update that gets update information from Firebase Remote Config
These are the things that we considered useful so they remained in our template and are general enough so they can cover our needs throughout all our projects. The repository also contains an example project that illustrates how it can be used so it can also serve as a good starting point.
iOS template: Future
Of course during the development of the current template we were facing many situations where we were thinking that this could be done better. So we have quite a lot of ideas on how to move it forward. The next goal would be to use the scaffold feature of Tuist so the template will really become a template that is part of our Tuist plugin. This way creating a new project would mean just defining a Tuist config and calling one scaffold command. But as good as it sounds, this will hopefully be done sometime in the future. 😎