Picking your tools of the trade

Over the years I've had to make a lot of choices, about what editor, programming language, frameworks and whole projects to pick to get stuff done. Think coding for university, setting up projects for work and customers, writing open source software and maintaining services for the community.

While some of the decisions were no-brainers, e.g. when the company I worked for has had already settled on a framework or there was only a single tool available, most of the times there was quite an array of options to chose from and picking the right one required some effort – and hindsight I simply didn't have at the time.

As all older people do, I assume that me writing down my lessons learned will prevent you, dear reader, from making your own mistakes. So without further ado, I introduce my 7 points of how to spot software projects that may or may not work for you.

1. Define your breaking points!

Remember: Sometimes it's okay to just say no completely. You do not have to settle for the least ugly option, especially when doing open source work. You should decide in advance how much energy your project is worth. You may then decide if it's smarter to abandon your plans or to bite the bullet and chose a sub-optimal dependency, or even fork or set up a new project to solve the unsolved.

At your work place, you might put up with much worse options than with projects you want to do in your spare time, but maybe you can take this list and convince your boss or co-workers to re-evaluate decisions.

2. How much does the project know and communicate about prior art, best practises and how they fit in there?

Did the project authors and maintainers spend the effort of building platform ports or are you required to follow a "Best viewed with Internet Explorer 6 in 1024 x 768" approach and force you to deploy precise replicas of their setups?

red flags:

  • curl | bash,
  • bashisms in Makefile or shell scripts,
  • "Windows filenames" (build breaks if filesystem is case sensitive),
  • temp files or editor backup files in distribution,
  • hard-coded credentials or certificates,
  • project builds only in Docker / github CI pipeline,
  • source code treated as second-class installation option (they really want you to install binary packages),
  • dependencies on tools or libraries in versions other than current stable release.

green flags:

  • packages for more than one platform,
  • build enables all compiler warnings and none show up during regular build,
  • build system comes prepared for cross-compilation,
  • project has open bug tracker,
  • bug tracker shows that bugs are attended to and not closed on a whim,
  • README clearly states security contact for when you find a security bug.

Are the project's devs and contributors active on other projects, maybe even some you've heard of?

Does the user and admin documentation hint at the authors following best practices? This is important because, for example as an admin, you don't want to be stuck studying the complete project and their dependencies just for trouble shooting a single problem.

Are the project's maintainers aware of trade-offs and short comings of their project?

red flag:

  • The project page is full of marketing speech and a liberal use of "awesome" words.

green flag:

  • Embracing criticism. You can only be a true fan of a project if you have at least one hour worth of rant about the warts-and-all.

3. Do you like the project's documentation?

Does the project's documentation cover the basics with some handy primers and how to grow from using a small feature set to the whole API?

Will the first google hit for a medium complexity keyword from the project – be it an API call, a config keyword or keyboard short cut – be somewhere at the project's page or on Stack Overflow?

Does the project come with some good opinionated defaults along with their respective rationales?

Are the defaults there because they are useful or for backwards compatibility?

Do you have to manually turn on vital security aspects?

Are obscure knobs documented? Older projects usually have some special functions or knobs for special cases that probably won't apply to you. The documentation should make clear which options are for obscure special cases so you don't get lost in the details when looking for a specific thing.

Do they thoroughly cover how to maintain the projects or do all the guides stop right after you installed the project? Which leads us to …

4. How much regular attention does the project require?

Good tools require cleaning and maintainance – but once you spend all your time just on your tools, you're not getting work done.

Does the project clearly understand and communicate what dependencies they bring and how to keep those up to date?

Are those dependencies well balanced? Is the same true for their recursive dependencies (this includes the programming languages chosen).

As a more specific example, is the project written in a language with a clear and complete runtime for the basics? Think libc vs. leftpad, python's batteries included approach, etc.

A good sign is a few dependencies with a guaranteed stable API.

Once you understand the dependency tree, is there another option with fewer deps? IOW: Do you need all the things provided by the project at hand, or is there a more specific tool for your problem?

Given how much time you can realistically spend on a single dependency: Can the project and its stack cope with routine maintainance intervals of one year? Does the project give guarantees not to break config or user data on updates?

Does the project have a policy and a schedule for updates vs upgrades vs security patches? Are they free without a subscription?

If the user can't chose maintainance time (e.g. on security updates), does the project guarantee that you will not be forced to upgrade to breaking changes?

How quickly are dependencies deprecated? Are you required to re-work basic functionality within less than a year?

5. Is the project there to stay?

What is the project's head count?

Is the community's size in a healthy proportion to the project's complexity?

What kind of contributors and users does the project attract? How's the tone in associated forums? Is that a good sign for you?

Where's the project hosted at? Does it run some own infrastructure or will the dependency break once you or your customers are in a sanctioned region?

Has project ownership changed hands? More than once?

6. … and if not do they help you to move on?

If the project provides migration helpers, do they only point in one direction?

Can you dump payloads, meta data and config information in a structured format that helps you inspecting and importing it elsewhere later? From my experience it is best, if the project did anticipate its obsolescence and provide these functions right from the start.

Does the project's config language require knowledge about some plumbing that you should not need to care about?

Can you see a clear path how to use a competing project or it's API should you reconsider or are you stuck to the point of requiring a rewrite or complete re-start of your project?

7. What's the extra baggage YOU leave?

If you need to hand over the project due to unforeseeable circumstances, is it easy to find replacement for you, your config, private forks or tweaks?

Does your choice of programming language or framework leave your colleagues or peers with further technical debt and fewer good options? Sometimes it's better to go with a mainstream choice so that more or more affordable peers can contribute later.

Would your own project tick all the above points to your own satisfaction?