0

I am trying to throttle some bots trying to brute force authentication on our production server.

This is a Rails 4 app with rack attack 6.3 and i have configured it like this:

config/initializers/rack_attack.rb

class Rack::Attack

  # Throttle all requests by IP (60rpm)
  #
  # Key: "rack::attack:#{Time.now.to_i/:period}:req/ip:#{req.ip}"
  throttle('req/ip', limit: 300, period: 5.minutes) do |req|
    unless req.path.start_with?('/assets')
      Rails.logger.error("Rack::Attack Too many requests from IP: #{req.ip}")
      req.ip
    end
  end

  ### Prevent Brute-Force Attacks ###

  # Throttle any POST requests by IP address
  #
  # Key: "rack::attack:#{Time.now.to_i/:period}:pink/posts/ip:#{req.ip}"
  throttle('pink/posts/ip', limit: 1, period: 2.seconds) do |req|
    if req.post?
      Rails.logger.error("Rack::Attack Too many POSTS from IP: #{req.ip}")
      req.ip
    end
  end

end

and yet i keep getting millions of requests from the same IP, am i missing something?

The docs say that rails apps use it by default so this should be the only configuration necessary to enable throttling.

Julien
  • 2,217
  • 2
  • 28
  • 49

2 Answers2

2

So in the end both syntax like what I had and what @wscourge suggested work, the problem is that even though the official docs say that rails apps use it by default, you still need to add the following to application.rb, at least in Rails 4:

config.middleware.use Rack::Attack
Julien
  • 2,217
  • 2
  • 28
  • 49
1

From what I see in the throttling documentation syntax, the right way to do it is to execute the class method in the initializer, and not to execute it in the class definition:

config/initializers/rack_attack.rb

# Throttle all requests by IP (60rpm)
#
# Key: "rack::attack:#{Time.now.to_i/:period}:req/ip:#{req.ip}"
Rack::Attack.throttle('req/ip', limit: 300, period: 5.minutes) do |req|
  unless req.path.start_with?('/assets')
    Rails.logger.error("Rack::Attack Too many requests from IP: #{req.ip}")
    req.ip
  end
end

### Prevent Brute-Force Attacks ###

# Throttle any POST requests by IP address
#
# Key: "rack::attack:#{Time.now.to_i/:period}:pink/posts/ip:#{req.ip}"
Rack::Attack.throttle('pink/posts/ip', limit: 1, period: 2.seconds) do |req|
  if req.post?
    Rails.logger.error("Rack::Attack Too many POSTS from IP: #{req.ip}")
    req.ip
  end
end
wscourge
  • 10,657
  • 14
  • 59
  • 80