Random Thoughts by Fabien Penso

Memory usage of Ruby vs Rust

I currently work at Beam, and more specifically on the server-side API allowing our users to synchronize their data on all their devices. For privacy reasons, this API is E2EE and we don’t see anything except encrypted blobs. The private keys are stored on the user’s device.

This API is currently in Ruby and called through GraphQL and REST endpoints. This API will potentially manage a lot of data, and it became clear Ruby wouldn’t fit the need. It’s very hard to stream response, and Ruby’s memory usage is usually too high. And as a Ruby coder since 2005, it pains me to say it.

I spent the last year reading about Rust (and Go) on evenings and weekends, and prototyping code to get a feeling of the language and what it promises to deliver. We recently decided it would be time to now work on it day-time and start replacing endpoints. It’s far from being over yet, but I already have some feedback.

The first endpoint I’m rewriting is fetching rows from a pgsql database, and streaming results as JSON to the HTTP client. I’m testing this for over 50,000 rows and over 200MB of data. We are currently hosted on Heroku, and the Ruby instance has the following memory metrics.

/img/ruby-vs-rust-memory-1.png

It uses up to 2GB of memory, which is expected for a Rails stack.


And now the Rust metrics.

/img/ruby-vs-rust-memory-2.png

The Rust endpoint has been done using actix, sqlx, serde, and a few others.

It uses up to 4MB… About 500x time less. The benchmarks I did shows 30% speed improvements as well, which to be honest was deceptive. But the Rust instance runs on a different Heroku dyno, with a 10x smaller cost per month. Moving the Rust instance to the same Ruby instance didn’t improve speed, I guess the bottleneck is on our pgsql instance.

Our Ruby stack is doing a lot more for now, but it’s still impressive nonetheless. I have the feeling Rust will become very popular among server-side micro-services.


Update on June 4th: after releasing this endpoint in production, as stated in this tweet I actually saw a x12 performance increase, while being on a 10x cheaper Heroku dyno instance. Memory stayed around 4MB as well. I suggest to read comments of this reddit post.