Here's the path that leads to K8s too early.
1. We think we need microservices
2. Look how much it will cost of we run ALL OF THESE microservices on Heroku
3. We should run it ourselves, let's use K8s
One of the big "Elixir" perks is that it bypasses this conversation and lets you run a collection of small applications under a single monolith within the same runtime...efficiently. So you can built smaller services...like a monolith...with separate dependency trees...without needing to run a cluster of multiple nodes...and still just deploy to Heroku (or Gigalixir).
Removes a lot of over-architectural hand-wringing so you can focus on getting your business problem out the door but will still allow you to separate things early enough that you don't have to worry about long term code-entanglement. And when you "need" to scale, clustering is already built in without needing to create API frontends for each application.
It solves a combination of so many short term and long term issues at the same time.
Elixir and Erlang are basically a DSL for building distributed systems. It doesn't remove all of the complications of that task, but gives you excellent, battle tested, and non-proprietary tools to solve them.
This is also true of Erlang, for those not aware that Elixir runs on the Erlang Virtual Machine (BEAM).
You do get a lot of cool things with clustered nodes though (Node monitors are terrific) and tools like Observer and Wobserver have facilities for taking advantage of your network topology to give you more information.
They are basically an OS, with containarized applications.
Thanks to them I stopped caring about the underlying OS.
Elixir has a lot in common, but it takes it to another level. You can call functions from those other applications on the server with nothing more than a Module.function(arguments). You can call a function on another node in the cluster by just sending the node + module, function and arguments.
Because of immutability and message passing, this just works everywhere. With Java, a similar implementation would have to guard against memory references and mutex locks that wouldn't behave the same way on different nodes.
You can still call the functions through the same Module.function() approach you’d use if they were in the same app.
The $30 PragDave Elixir for Programmers course actually drills in this approach the whole way through if you’re looking for a good resource.
I originally bought it at $60, and even at that price point I would buy it again.