Automation on Tuist

As we continue to span Tuist’s convenience to automation, users might wonder why we are seemingly trying to do the same that Fastlane does. This thread is my attempt to describe the motivations behind bringing automation to Tuist, and how our approach differs from Fastlane.

Fastlane needs Fastfiles that act as an interpretation layer between Xcode’s domain and primitives and the terminal. In other words, developers use it to describe tasks that they can run from their terminal to interact with the project. In theory, it provides a fair level of flexibility, in practice, projects ens up with large and complex Fastfiles that are hard to maintain, and whose lanes are not deterministic.

I believe the practice is more important than theory and that users should have a limited set of commands that reflect their intents when interacting with their projects. Rather than letting them figure out the workflows they need themselves and codifying them using lanes, why not thinking about the workflows ourselves and giving them something that works every time and everywhere, without any maintenance cost on their end?

That’s what I’m aiming for in Tuist. Since we know the projects because developers describe them using the manifest files, we can leverage that information to provide a CLI whose commands:

  • Are standard: That means developers will know the interaction language that they can use with any project. Once they learn about tuist build, tuist test, and tuist run, they can use it in any directory that contains a Project.swift or Workspace.swift file.
  • Work with no arguments: Unless we’d allow developers to pass arguments like --config Debug, when not passed, we should have defaults. Unlike xcodebuild that has some required arguments, commands like tuist build would run without any argument.
  • Run deterministically: We should design the commands to be idempotent by removing side effects.
  • Use the STDOUT and STDERR consistently: Unlike Fastlane, whose lanes are not consistent in how errors are bubbled up and how they use the standard error and output (i.e. bad user experience), we should make use of Tuist internals to ensure that’s not the case here.

Thanks to this, projects that can’t have a tooling/infra team that takes care of all the automation-related code, can continue to focus on building the features in their apps, while Tuist provides them with optimized workflows that they can use for their day-to-day work. Moreover, limiting the set of workflows will allow us to introduce optimizations that otherwise wouldn’t be possible.