Erlang: What's it good and not good for?
Erlang is much more than a programming language. You can't compare it to other languages based only on it's syntax or idioms. It's actually a mini operating system, running on top of another operating system, with lots of interesting and useful features (of which I'll talk later).
Erlang was born in Sweden, at Ericsson, to be the language of their phone exchanges and networking devices. It was open sourced in 1998.
It's important to keep in mind is that Erlang is not a general purpose language. It has a very special niche, where it performs extremely well – but in that niche it's towering so high above anything else that it's almost scary. Its niche is multi-server (we call them "nodes") distributed applications, and controlling a multi-node network.
So what is Erlang good and not good for?
While Erlang is great for its niche, let's be pragmatic.
Erlang is great for...
- ...for monitoring systems that oversee and coordinate thousands of virtual machines.
- ...for distributed databases (RIAK and CouchDB are success stories).
- ...for web-based dashboards that show or chart real-time data.
- ...for service oriented software architectures. (RabbitMQ is a success story.)
- ...for specialized high-performance web services like an ad server, or API endpoints.
- ...for applications that benefit from having a distributed, multi-node architecture.
- ...for soft real-time applications (video streaming is soft real-time, ballistic missiles are hard real-time).
- ...for stateful binary communications, like a protocol-aware load-balancer.
- ...for other long-running daemons and services. (As opposed to request-response based web pages, or scripts.)
But not so good for...
- ...for web applications that don't involve real-time communications (which includes most web stuff: CRUD (create/retrieve/update/delete) apps, forms, admin UIs, websites).
- ...for computation-heavy tasks.
- ...for string operations: parsers, transformations, etc.
- ...for desktop GUI applications.
(It also comes down to proportions. If your system is in 98% a very good fit to Erlang, then what the hell, do that remaining 2% in Erlang too. But also the other way around.)
Also, don't forget that Erlang programmers are usually very good programmers, and thus tend to be expensive. You want to use them for the hard stuff, not for trivialities.
(If you're interested in why I say this, my article about the concurrency crunch might be of interest to you.)
Sidenote: massive parallelism explained
Imagine that every time I've sent an email to somebody I was frozen until he sent me his reply. I could do certain tricks with lots of overhead to avoid this (i.e. hiring a secretary to be frozen instead of me), but this would be expensive. And that's how normal object orientation works (C++, Java, everything) – but not in Erlang.
In Erlang, concurrency is lightweight and cheap. You can start up hundreds of thousands of threads, which you can't do with native threads. (With native OS threads, while there is no "theoretical" limit, you're losing performance once you start up more than the number of your processor cores, and the code would be slowed to a crawl at around ~1000, if the stacks wouldn't have used up all your RAM much earlier.)
In Erlang every object in your system can have it's own thread. This means that objects are not just parlor tricks anymore, seemingly poking each other with messages, but actually mostly waiting on each other – here they really just do send messages, then go on to other things. Just like in the real world.
So why is Erlang so good?
As a software architect, these are the features that make Erlang so very valuable to me:
- It's massively parallel and distributed. Not only it's very easy to write code that utilizes multiple processor cores, it's easy to write code that can span multiple servers. Not sure which features of your software the users will like the best? No problem, when you find out, you can move those parts out to bigger, better, more servers later!
- You can look under the hood of a running system. Run-time observability. Erlang is more than a language, it's actually a small operating system, and even when your code is running, you can use a shell (even remotely), run-time debuggers, profilers, and DTrace-like instrumentation to look at your code doing its stuff. (Seriously, this is how everything should work. Once you've experienced this, you miss it from everything else.)
- You can update code on a running system, without stopping it. Hot code swapping. Although you won't use it as often as you initially think, with proper planning it's a key to minimize your downtime. Oh, and nodes can send compiled code to each other with a single command, how cool (and useful) is that?
- Your investment being protected against "bit rot". Erlang cares about backwards compatibility. I'm old enough now to know that few things are more wasteful than having to rewrite fifth of an operational application every year just to keep up with the language/framework/etc, to avoid ending up relying on an outdated and unsupported version.
- A very clean (if unusual) error handling model. Every Erlang node is like a little Death Star, with Darth Vaders (supervisors) and troopers (worker processes). When a trooper makes a mistake? BLAM, his master shots it in the head, and immediately replaces it with a clone. No my friend, your mistake will not get propagated, you won't affect the Holy Global State Of The System.
- The reporting/logging facility. It doesn't get as much press as it should, but the SASL's (System Application Support Library) logging facility and the Report Browser (rb) makes after-the-fact debugging and everyday operations just so much smoother. It's a rotating log, so you can calculate in advance how much maximum space it will take, which is useful for embedded systems.
- Global name resolution. It's one of the things you discover you need when you start writing distributed programs. With Erlang, you already have it ready.
- The Mnesia database. One feels in his gut that it's a marketing disaster to name a database "mnesia", but it is a testament to the technology's superiority in the face of marketing. It's a distributed "noSQL" database, embedded right into Erlang, which supports indexing, replication, transactions and fail-over. (And don't forget its simpler but equally useful brothers: the fast ETS in-memory, and the DETS persistent on-disk database.)
- Automatic application migration. With just simple configuration, Erlang can move your application(s) from node to node inside a cluster automatically, for example in case of a failure.
- The tons of little stuff that you don't have to sweat yourself. Did you knew that when you link two Erlang nodes together, and their clocks are out of sync, they start to "skew time" to bring the clocks slowly in sync? This gradualism is needed so timed tasks don't "skip". And there are lots of these small but important features, stuff you haven't even yet thought about – but they are already solved in there for you.
How does it feel?
You know Stargate Universe, where an expedition gets accidentally transported to an alien starship? And then they have to reverse engineer the alien computer's workings, to be able to fly the ship?
Well, Erlang feels pretty close to that. :)
If you're a programmer, and want to get a quick feel for it, head to tryerlang.org to give Erlang a spin. If you want a good and enjoyable tutorial, Learn You Some Erlang for Great Good is your best choice. The best library reference is erldocs.com. The official website is erlang.org.