---
title: Using rails built-in rate limit feature
url: https://calvin.my/posts/using-rails-built-in-rate-limit-feature
published: 2025-04-06
updated: 2026-09-16
category: Development
tags:
- Rails
- Security
- rate limit
summary: The post demonstrates Rails 8’s built-in rate limiting across three common scenarios. A route can share one limit for all traffic, useful for protecting costly endpoints such as OTP requests. Limits can also be keyed to a user identifier, preserving restrictions across devices or IP addresses. Finally, multiple named rules can enforce both short-term and daily quotas on the same route; distinct names prevent counters from overlapping.
---

# Using rails built-in rate limit feature

## Our goals

Rails 8 includes a built-in rate limit feature. In this article, we try to implement several use cases.

- Implementing a rate limit applicable to all traffic
- Implementing a rate limit based on user
- Implementing multiple rate limits for the same route

* * *

## Use case #1

We try to set a limit like below.

```ruby
class HomeController < ApplicationController
  rate_limit to: 2, within: 1.minute, only: %i[index]

  def index
  end
end
```

This limits the visits to 2 per minute. If we try to access the 3rd time, our access will fail.

![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/46aeb921-e53e-4be5-b1e9-a6298335e9ef.png)

Such a setting is generally useful when you want to protect a specific route with the same limits for everyone. For example, you could use this to slow down the request for OTP which would be expensive if mis-used.

* * *

## Use case #2

What if you want to limit the route based on the user, regardless of whether they access it from different IPs or devices?

Let's modify the code to:

```ruby
class HomeController < ApplicationController
  rate_limit to: 2, within: 1.minute, only: %i[index], by: -> { user_id }

  def index
  end

  def user_id
    "1"
  end
end
```

Now, if we access as user ID 1, we get a successful response up to 2 times before it fails. If we change to user ID 2, we can immediately succeed.

![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/ef6d7ec3-b032-4786-b8d0-950b70cd73db.png)

* * *

## Use case #3

Consider a condition where users can submit a request twice per minute and not more than four daily. To implement this, we have to set up two rate limit rules.

```ruby
class HomeController < ApplicationController
  rate_limit to: 2, within: 1.minute, only: %i[our_test], name: "rate1"
  rate_limit to: 4, within: 1.day, only: %i[our_test], name: "rate2"

  def our_test
  end
end
```

In our test, we can access 2 in the first minute and another 2 in the second minute. Then, our daily quota is finished.

![](https://camy-pub.s3.ap-southeast-1.amazonaws.com/72fc1a2b-a824-4eea-a3ad-ee2a490e86c2.png)

Note: A name must be given to each rule to avoid repetitive counting.
