Rails handles large number of nested routes better than Sinatra

Jeremy Evans (of Roda and Sequel fame) created an interesting benchmark comparing memory and runtime performance of large number of routes (up to 10000) in various Ruby web frameworks. I was immediately interested and ran it to get the numbers.

Jeremy’s benchmark is called r10k and supports several web frameworks. Since the results are not included in the original repository I ran this benchmark on my laptop (5th gen i7 ThinkPad Carbon) to find out.

I used latest stable versions of Roda (3.16.0) and Sinatra (2.0.5) together with Rails 6 (6.0.0.beta1) all running Ruby 2.6.0. I did only small tweaks to the original benchmark by upgrading Rails and removing config.secret_token option. Here are results for initial memory taken:

And here once again as numbers:

If you are familiar with Roda you are not surprised that it performs the best, but what’s interesting is that by using large number of routes the memory gets worse for Sinatra way faster than for Rails. With 10000 routes Rails takes only 15 MB more memory than Sinatra and with even more routes Rails would win here in terms of memory used. The runtime performance is even more interesting:

And once again pure numbers:

Roda performance is again not surprising to me. It’s rock solid and fast. Rails is also pretty good. Yes, it’s slow, but it doesn’t get much worse with many routes and the performance is predictable. Unfortunately Sinatra performs poorly with 10000 routes and more. There is a real jump there and only gets worse with bigger numbers.

If we take a look on the application code generated by the benchmark we can see that it’s not just about number of routes, but nesting level. Each level of magnitude introduce more complex routes by extra directory level. This is snipped for those 10000 routes:

So this does not automatically mean that Sinatra doesn’t handle big number of routes well, but that there are performance issues given large number of more nested routes. I am not familiar with Sinatra routing internals so please share if you know more (or if this benchmark has a bug).

Finally this unfortunately still does not say much about routes in your application. As you can see these routes are not dynamic and not working with any parameters so take everything with a pinch of salt.

Join the Conversation

1 Comment

  1. Unfortunately with Sinatra routing, it really is just about the number of routes. It does a linear search through an array of routes until it finds one that matches. Roda and even Rails use tree algorithms to provide better performance when dealing with a large number of routes. There is talk that the next major release of Sinatra may include a new routing algorithm: https://github.com/sinatra/sinatra/issues/1531

Leave a comment

Your email address will not be published. Required fields are marked *