News for hackers. Stuff that matters.
Re:A first naïve look at Truffle Ruby by TomK32 on Friday February 02, 2018 @05:02PM (#16294559)
What kind of speed are you looking for? Speed of the application in production, or the speed at which a developer can implement it? What will cost you more, a few more servers or a few more programmers?
Re:A first naïve look at Truffle Ruby by rrdharan on Friday February 02, 2018 @05:26PM (#16294703)
You can't always add a few more servers. For example, let's say you have a per-request processing budget of 100ms.

The efficiency of the generated code for your language of choice effectively limits the amount of (non-concurrent, single threaded) code you can run while processing said request.

It's exactly this limit that eventually leads engineering teams at your Dropboxes, Facebooks, Twitters, Tumblrs, etc. to start investigating alternatives or alternative implementations of their favorite dynamic languages (PHP/Python/Ruby -> HHVM/Pyston/?).

Re:A first naïve look at Truffle Ruby by jashmatthews on Friday February 02, 2018 @06:38PM (#16295133)
I work for a company exploring Rust and Go at the moment and it turns out there's little to be gained in moving away from Ruby for web app performance. Go + Gin is only about 2x faster than a modern Ruby + Sinatra + at "serialize some stuff to JSON and respond over HTTP" and JRuby closes the gap even further https://www.techempower.com/benchmarks/previews/round15/#sec...

There are cases where Ruby is obviously very slow compared to Go or an AOT langauge like Rust but serving dynamic web requests isn't really one of them.

This wasn't true when Twitter moved away from Ruby 1.8 but a huge amount of work has gone into Ruby since then. For example: totally new VM, GC, threading system and there's currently an open PR to add a basic JIT compiler.

Re:A first naïve look at Truffle Ruby by ehsanu1 on Friday February 02, 2018 @07:02PM (#16295242)
Those Sinatra numbers look a lot better than I remember them being!

But I wouldn't give that much credence to that, there's barely anything happening in those benchmarks and it seems to be testing things that have had a lot of optimization effort thrown at them. Try adding session management, user permissions, large data models, some business logic, all without putting a lot of effort into optimizing (ie like most work environments) and try again. Also, yeah, use some heavy (extremely popular) gems like ActiveRecord.

And God forbid you actually do something computationally intensive anywhere. Serialization (even with drivers written in C) is also very slow if you have a lot of data. And if you have enough traffic, even a 2x performance difference can be pretty important in terms of cost.

AR and similar libraries are the killer of performance in the Ruby eco-system. It's not the bare web framework itself, but the entire eco-system is generally not too worried about performance compared to other languages (partially because it's harder to optimize in Ruby, partially due to the culture).

That said, the language has gotten a lot faster since the 1.8 days, eg GC has seen a lot of improvement, but it's still damn slow.

Re:A first naïve look at Truffle Ruby by jashmatthews on Friday February 02, 2018 @08:20PM (#16295559)
Until recently none of the Ruby setups in the TechEmpower benchmark were configured even vaguely correctly. Previously they were comparing Sinatra running on 8 cores to Go running on 40 cores.

At my day job have an a prod analytics service with all the stuff you mention written in Rust + PG, and the Rust bit which handles data ingestion via HTTP and JSON is only about 5x faster than the equivalent Ruby code. Obviously, that was a big disappoitment to me.

Serialization performance in the default Rails setup is horrific but calling Oj explicitly on an ActiveModelSerializer instead of the Rails "render :json, @model" brings it much closer to "fast" languages than you'd expect, improving performance about 74x. I wish I was joking.

If the perf difference simply means buying 2x the servers then as a company you have to be pretty big before it's worth throwing out the entire Ruby/Rails ecosystem and getting stuck with far less mature libraries in newer, less widely used languages like Go or Rust.

There are tons of major sites using Ruby/Python for their web layer. Instagram, Stripe, Airbnb, Shopify, HotelTonight, GitHub, and even part of Netflix is powered by Rails.

If you look at the work Aaron Patterson and Shaun Griffin have done and are doing on AR, or what Peter Ohler has done with Oj, I don't think it's fair to say that either the Rails or Ruby ecosystem doesn't care about performance. They just don't put it before usability by default.

Compared to other scripting languages, even performance focused ones like Lua, Ruby's performance is very good, and will only continue to improve with MJIT coming to MRI Ruby, and an entire new high performance alternative implementation coming with TruffleRuby.

Re:A first naïve look at Truffle Ruby by ehsanu1 on Friday February 02, 2018 @11:19PM (#16296146)
At my day job have an a prod analytics service with all the stuff you mention written in Rust + PG, and the Rust bit which handles data ingestion via HTTP and JSON is only about 5x faster than the equivalent Ruby code. Obviously, that was a big disappoitment to me.

5x isn't too shabby for something potentially somewhat IO-bound. Presumably the effort wasn't 5x to build and maintain that, so if that's a very hot inner loop of something that's great.

What I've found is that using Ruby (mainly gems) idiomatically can just lead to way slower performance. Eg I use time libraries a lot for my day job, and the idiomatic way to write the code had tons of hidden costs and was basically impossible to optimize.

So I wrote a ruby extension in rust, and got a 30x speedup on that code - it was pretty computationally intensive, so a perfect fit for this. Part of it was that I was forced to use more primitive types, but in Rust-land I was able to add types all over the primitives and abstract away to my heart's content, without any overhead. That's just something that's impossible in Ruby - each abstraction always has a cost and there's no way around it.

If you look at the work Aaron Patterson and Shaun Griffin have done and are doing on AR, or what Peter Ohler has done with Oj, I don't think it's fair to say that either the Rails or Ruby ecosystem doesn't care about performance. They just don't put it before usability by default.

Right I wouldn't say nobody cares about performance, some people care a lot and they've been doing great work and helping raise the bar. But overall, the bar is pretty low in the Ruby world.

Chris Seaton (one of TruffleRuby's main authors) has a talk where he shows some of the batshit insane code you see in gems, which they had to figure out how to optimize in TruffleRuby/Graal. Code like allocating a new array and calling the `min` method in order to find the smaller of two values! And that was being called in a hot inner loop! In a gem with otherwise great functionality, a nice website and thousands of users. That's the kind of thing you only see in Ruby-land.

Also, using method_missing (gotta have that pretty DSL, performance and greppability/discoverability be damned) and monkey-patching/alias-chaining/etc is still common unfortunately (though a smart JIT, ie Graal, can apparently handle that).

I am really excited about TruffleRuby and it does really amazing things to optimize crazy Ruby code, so I'm looking forward to Ruby being as fast as say JS in the future. Can't wait for the day I can turn on TruffleRuby in production and halve the AWS bill.

Re:A first naïve look at Truffle Ruby by jashmatthews on Saturday February 03, 2018 @09:11AM (#16297673)
Both are CPU bound on de-serialization. It’s basically DB replication over HTTP plus some business logic at either end. The Sinatra version is built in a weekend which is 5x slower has authentication and does use ActiveRecord.

Building an entire web app, with background job processing, in Rust with the ecosystem how it is at the moment is very, very slow compared to Ruby, Sinatra and Sidekiq.

When we started Diesel couldn’t join to more than one table. Probably approaching 5x in development time. It’s just not mature enough yet. We’re still experiencing stuck threads which don’t timeout.

Sounds like you found a great case for a native extension!

Re:A first naïve look at Truffle Ruby by ehsanu1 on Saturday February 03, 2018 @07:43PM (#16300577)
Agreed, I wouldn't do a production web service purely in Rust yet, the ecosystem is still way too immature.
Re:A first naïve look at Truffle Ruby by NoPiece on Friday February 02, 2018 @05:59PM (#16294937)
It's exactly this limit that eventually leads engineering teams at your Dropboxes, Facebooks, Twitters, Tumblrs

True, but those are such extreme edge cases. 99.9999% of projects will never see that kind of demand for scale and speed. Facebook shouldn't switch to Ruby, but that doesn't inform whether Ruby would be viable for many (most) projects.

Re:A first naïve look at Truffle Ruby by nirvdrum on Friday February 02, 2018 @06:19PM (#16295049)
I don't think it's that much of an edge case. If Rails and its ecosystem lead to 300ms render times without load, but your objective is 100ms, you're going to have a problem. I don't think either number here is extreme and I've encountered that sort of situation on previous projects. It's not easily solvable by throwing more machines at it, unfortunately.
Re:A first naïve look at Truffle Ruby by tomc1985 on Friday February 02, 2018 @06:45PM (#16295157)
If Rails and your ecosystem are pushing 300ms renders you have bigger problems on your plate
Re:A first naïve look at Truffle Ruby by nirvdrum on Friday February 02, 2018 @07:39PM (#16295405)
I don't think it's uncommon. But the point is it usually has little to do with load and isn't easily solved by scaling horizontally. Sure, you might be able to gain some efficiencies with distributed caches and such, but that still requires a fair bit of effort (the developer time we're trying to minimize).

You're right though. And I managed to sidetrack myself a bit. My intention in participating in the thread was to point out that you can't always optimize for developer speed and think you can get out of it "cheaply" with more hardware. And it's not just a problem when you're big enough for it to be a good problem to have. In those cases you're going to need to find a way to make the application faster.

Maybe it's aggressive in-app caching; maybe it's sitting there analyzing application profiles; maybe it's a rewrite in another language or another framework. Our goal is to provide a fast enough runtime where you don't have to make that decision.

Re:A first naïve look at Truffle Ruby by tomc1985 on Friday February 02, 2018 @07:50PM (#16295446)
> the point is it usually has little to do with load and isn't easily solved by scaling horizontally.

My point exactly. Unless you're getting slammed with traffic, there's too much going on in a page load if it takes 300ms to spit out.

Re:A first naïve look at Truffle Ruby by nirvdrum on Saturday February 03, 2018 @11:57AM (#16298358)
If you can achieve the same rendered output much faster with a different runtime or with a rewrite or with a different framework, I don't think you're looking at a fundamental design flaw with the page. I'm happy to agree to disagree. Maybe there is too much going on with the page. But it's a common problem with Rails apps and is ideally solved without a rewrite. I think a faster runtime would be the ideal solution here.
Re:A first naïve look at Truffle Ruby by kuschku on Saturday February 03, 2018 @01:34AM (#16296521)
At my day job we've seen load times for pages > 5 seconds in rails. There's no way to do it faster because the data has to be dynamically generated and loaded, and that's the bottleneck.

It's not uncommon to see this in rails applications — GitLab had the same issues.

Re:A first naïve look at Truffle Ruby by jashmatthews on Saturday February 03, 2018 @04:56PM (#16299902)
In GitLab's case, a lot of their issues are just the classic self inflicted N+1 queries and poor planning of how to represent events in a way that could be quickly queried for display.

OTOH, the background job memory issues were completely not their fault. Glibc malloc trades high memory usage for keeping both high throughput and simplicity. With Sidekiq or puma this causes much higher memory usage than necessary. Switching to jemalloc, which they did, can reduce memory usage by 50-75%.

What does your app do that takes 5 seconds? Is this because hundreds of DB calls are required, or you need to serialize thousands of objects?

Re:A first naïve look at Truffle Ruby by jashmatthews on Friday February 02, 2018 @08:24PM (#16295573)
Out of pure curiosity what took 300ms? Image composition? Huge JSON payload serialization?
Re:A first naïve look at Truffle Ruby by ehsanu1 on Friday February 02, 2018 @11:23PM (#16296161)
I've seen numerous big rails apps with times as long or longer, even after decent effort has been put in to optimize. Generally a case of having a lot of things on a page and rendering it all into html server-side (the classic/old rails way of doing things).
Re:A first naïve look at Truffle Ruby by jashmatthews on Saturday February 03, 2018 @08:36AM (#16297559)
300ms from server side rendering requires something self inflicted. Even bulk JSON endpoints should be faster than that.

27ms is the average dynamic response time for Basecamp, which is server side rendered HTML done the classic way.

I worked on a high performance Rails API serving dynamically generated map tiles and our response times were actually lower than that.

Re:A first naïve look at Truffle Ruby by nirvdrum on Saturday February 03, 2018 @11:49AM (#16298314)
Doesn't basecamp do a ton of caching to achieve response times like that? There are certainly techniques to get there, but how long does it take to populate the caches? That's what you're going to see out of a stock Rails app.

Self-inflicted, sure. But in my experience it's the result of picking developer-friendly tools to optimize for developer time. Erubis is much faster than HAML, but a lot of developers prefer the latter. Those sorts of decisions accumulate.

Re:A first naïve look at Truffle Ruby by jashmatthews on Saturday February 03, 2018 @01:36PM (#16298832)
No more than Match.com do, who run on .NET. Basecamp just uses the standard Rails caching AFAIK.

Templating just isn't the issue now that it was in the days of 1.8. HAML is slower than ERB, but usually neither have a meaningful impact on response time on modern Ruby. ERB is approaching Erubis performance now.

Re:A first naïve look at Truffle Ruby by ehsanu1 on Saturday February 03, 2018 @07:41PM (#16300569)
I worked on a high performance Rails API serving dynamically generated map tiles and our response times were actually lower than that.

Sounds like an ideal case for fast response times honestly. I've seen rails endpoints like that aplenty. But there also exists a lot of stuff taking hundreds of ms on a cold cache, and it's the kind of thing where the same effort done in the same way using another language ecosystem would just be 10x as fast.

If you've never seen this, perhaps you've never worked with a large monolithic rails app with a few years of legacy code built up? Brand new API endpoints can be a lot faster of course.

Re:A first naïve look at Truffle Ruby by jashmatthews on Sunday February 04, 2018 @02:07PM (#16304239)
10x faster in, say, Go? Are you sure? Have you benchmarked it? You might be surprised.

Lets pick a weakness of Ruby: tight loops and lots of math. Take 16,000 GPS points and calculate the geographical distance to another point.

On my machine it takes 12-14ms in Ruby and 4-6ms in Go. That's only a little bit more than twice as fast! Almost certainy not worth re-writing your entire app for.

I've worked with a bunch of large, legacy Rails apps. In between a couple of Rails jobs, I worked on a large .NET app, which didn't have much better performance. One service I helped migrate from Rails to Spring/Java for an enterprisey client actually got slower overall, despite moving to the JVM.

Re:A first naïve look at Truffle Ruby by jashmatthews on Sunday February 04, 2018 @07:35AM (#16302495)
These are the response times for Discourse, a complex open-source Rails app. Even the slowest endpoint has an average response time of 46ms.

Percentile: repsonse time (ms) categories_admin: 50: 17 75: 18 90: 22 99: 29 home_admin: 50: 21 75: 21 90: 27 99: 40 topic_admin: 50: 17 75: 18 90: 22 99: 32 categories: 50: 35 75: 41 90: 43 99: 77 home: 50: 39 75: 46 90: 49 99: 95 topic: 50: 46 75: 52 90: 56 99: 101

Re:A first naïve look at Truffle Ruby by chrisseaton on Friday February 02, 2018 @05:40PM (#16294797)
Well the idea of TruffleRuby is you get the same speed of development, but also get high speed of the application in production as well. So you don't have to pay more for either.
Re:A first naïve look at Truffle Ruby by stewbrew on Saturday February 03, 2018 @01:20AM (#16296471)
You should also add: speed of maintenance, fixing bugs, refactoring. But these aspects are not part of the Ruby propaganda of course (which I myself believed in for too long).