When do use envsetup.sh or a Makefile

There are many ways to automate computer operations. One I have been gravitating toward lately is an envsetup.sh script. This file is sourced (use . for a shortcut) and populates your shell environment with functions. See the Simple IoT envsetup.sh as an example. There are some nice features of this using this method:

  • simple and easy to read – forms a dual purpose of easy-to-read documentation
  • if most of your automation is running commands, shell functions work well for this
  • for Linux/MacOS, no extra tools are required
  • if you prefix your functions with a common prefix, then you can type -Tab-Tab and quickly see a list of all your functions.
  • can be used for about anything (builds, deployment, general automation, ops)
  • easy to reuse in build systems (like Yocto) and CI/CD scripts

Most modern languages like Go, Rust, Zig, and Elm have their own build tools, so there is often no need for additional build tools that provide dependency management. Additionally, languages like Go and Elm build so fast, there is little cost to running a build even when you don’t need to.

When does a Makefile or other build tool make more sense?

  • when you have complex dependency management and long-running build processes.
  • you need to build on Windows
  • you are a Make expert and others don’t need to maintain it

While Make is a very powerful tool, it can get complex and the syntax contains a lot of magic that is not very readable unless you are an expert. While it has been used very successfully in some projects like the Linux kernel and u-boot, most projects now wrap Make with other tools like Cmake, Ninja, Meson, etc. This indicates Make is likely not the best way to express automation that is readable and maintainable.