In 2023, there are many options a developer can use to write backend APIs. Possible languages include JS/TS, Python, C++, Rust, Zig, Golang, C#, Ruby, Java, PHP, Scala, Erlang, etc. The list goes on. In this article my goal is to explain why we at Zapmoto use Golang to write our backend APIs, and why I think Golang is the perfect language for fast-growing startups to write performant code quickly.
In my mind, the languages I listed can be grouped into three groups:
High level languages: This group includes JS/TS, Python, Ruby, and PHP
Enterprise grade languages: This group includes C#, Java, Scala, and Erlang
Low level languages: C++, Rust, Zig, and Golang
The high level languages listed above are great for building systems quickly. JS/TS is a great language for web developers to build backend APIs with Node.js. Instagram Engineering wrote an article in 2016 (which admittedly is dated) outlining why most of their systems are built in Python with Flask. TLDR, they chose it because they can build systems quickly. Ruby and PHP were popular at once time, but have fallen by the wayside in favor of more modern programing languages. In this category, I personally am most excited about Mojo, a programing language that is a superset of Python with an advertised 35000x the speed of Python at its best. The language is being positioned as a tool for AI developers and those working with big data, but I am curious how it can be utilized in writing performant backend code quickly.
Java is the original enterprise grade language. Paul Graham wrote an essay on it in 2001 summarizing how I feel about this category. A quote that particularly sums up my feelings:
It's designed for large organizations. Large organizations have different aims from hackers. They want languages that are (believed to be) suitable for use by large teams of mediocre programmers-- languages with features that, like the speed limiters in U-Haul trucks, prevent fools from doing too much damage. Hackers don't like a language that talks down to them. Hackers just want power.
The languages in the enterprise grade category are great for large organizations who do not really care how well their systems are engineered. They just want to throw money at a problem by hiring 10 cheap engineers. They are run by engineering leadership who care how many people they manage and how big the organization under them is. I imagine these are the type of people who show up to work in a suit. While I think Kotlin is a great programing language (built on the JVM), I have a very low opinion of the languages in this category.
The low level languages are my personal favorite languages to work with. Like a surgeon’s scalpel, they enable more precise control over what you as the programer do with the computer. As a result they are magnitudes more performant than the high level languages mentioned above. My personal favorite language to write code in is Rust. I love the exact precision I get in Rust over where in memory my objects live, or if they are on the stack or heap. I can visualize the CPU running through my code with Rust which makes me feel powerful as a developer.
Unfortunately for me writing Rust, the points made in this Medium article are more than valid. If we were talking about writing code for the Linux kernel or writing HFTC trading machines, languages such as Rust or even C are frankly sometimes not low level enough. For web APIs, especially the ones we build at Zapmoto, we are not trying to shave off milliseconds. We just do not care for the most part. That is where I think Golang is the best happy medium between the low level languages and the high level languages mentioned above.
When Golang was created, it aimed to solve the following pain points:
slow builds
uncontrolled dependencies
each programmer using a different subset of the language
poor program understanding (code hard to read, poorly documented, and so on)
duplication of effort
cost of updates
version skew
difficulty of writing automatic tools
cross-language builds
At Zapmoto, we care about: slow builds, uncontrolled dependencies, each programmer using a different subset of the language, code hard to read, and duplication of effort. It is my belief that Golang is the right balance of achieving the development speed, and code readability of the high level languages mentioned above with writing performant, quick to build/deploy code many of the low level languages mentioned achieve.
Because code readability is one of the tenants of Golang, we can return to code written weeks ago and immediately understand what it does, reducing the cost of fixing bugs and adding features to an existing API. Additionally because Go is so stylistically opinionated, there is no question as to if a developer should use a trailing comma or if strings should be wrapped in single or double quotes. Additionally Golang was written with async code in mind. Goroutines provide the ability to write async code without thinking about it with the development speed of the high level languages, but with performance on par with many of the low level languages.
Golang is not a perfect language, but as in all things there are tradeoffs. At Zapmoto, we believe that Golang made the right tradeoffs to achieve what we try to achieve with our backend development.
If you found this article interesting and would like to work with us, please reach out directly to me at hunter@zapmoto.com. We are hiring!