From f22b24cbc587a3c8a3dbbadfc5298ded26e7bbc6 Mon Sep 17 00:00:00 2001 From: fatkodima Date: Tue, 8 Oct 2019 13:06:47 +0300 Subject: [PATCH] Do not auto-plug for rails < 5 --- README.md | 9 +++++- lib/rack/attack/railtie.rb | 18 +++++------- spec/acceptance/rails_middleware_spec.rb | 37 +++++++++++++++--------- spec/rack_attack_spec.rb | 6 ++-- 4 files changed, 41 insertions(+), 29 deletions(-) diff --git a/README.md b/README.md index 7e68f89..0b4a071 100644 --- a/README.md +++ b/README.md @@ -68,7 +68,14 @@ Or install it yourself as: Then tell your ruby web application to use rack-attack as a middleware. -a) For __rails__ applications it is used by default. You can disable it permanently (like for specific environment) or temporarily (can be useful for specific test cases) by writing: +a) For __rails__ applications with versions >= 5 it is used by default. For older rails versions you should enable it explicitly: +```ruby +# In config/application.rb + +config.middleware.use Rack::Attack +``` + +You can disable it permanently (like for specific environment) or temporarily (can be useful for specific test cases) by writing: ```ruby Rack::Attack.enabled = false diff --git a/lib/rack/attack/railtie.rb b/lib/rack/attack/railtie.rb index 973bebd..59994f1 100644 --- a/lib/rack/attack/railtie.rb +++ b/lib/rack/attack/railtie.rb @@ -4,21 +4,17 @@ module Rack class Attack class Railtie < ::Rails::Railtie initializer 'rack.attack.middleware', after: :load_config_initializers, before: :build_middleware_stack do |app| - middlewares = app.config.middleware + if Gem::Version.new(::Rails::VERSION::STRING) >= Gem::Version.new("5") + middlewares = app.config.middleware + operations = middlewares.send(:operations) + middlewares.send(:delete_operations) - operations = - if Gem::Version.new(Rails::VERSION::STRING) >= Gem::Version.new("5") - middlewares.send(:operations) + middlewares.send(:delete_operations) - else - middlewares.instance_variable_get(:@operations) + use_middleware = operations.none? do |operation| + middleware = operation[1] + middleware.include?(Rack::Attack) end - use_middleware = operations.none? do |operation| - middleware = operation[1] - middleware.include?(Rack::Attack) + middlewares.use(Rack::Attack) if use_middleware end - - middlewares.use(Rack::Attack) if use_middleware end end end diff --git a/spec/acceptance/rails_middleware_spec.rb b/spec/acceptance/rails_middleware_spec.rb index c9053be..4d27c70 100644 --- a/spec/acceptance/rails_middleware_spec.rb +++ b/spec/acceptance/rails_middleware_spec.rb @@ -2,7 +2,7 @@ require_relative "../spec_helper" -if defined?(Rails) && Gem::Version.new(Rails::VERSION::STRING) >= Gem::Version.new("5") +if defined?(Rails) describe "Middleware for Rails" do before do @app = Class.new(Rails::Application) do @@ -12,21 +12,30 @@ if defined?(Rails) && Gem::Version.new(Rails::VERSION::STRING) >= Gem::Version.n end end - it "is enabled by default" do - @app.initialize! - assert_equal 1, @app.middleware.count(Rack::Attack) + if Gem::Version.new(Rails::VERSION::STRING) >= Gem::Version.new("5") + it "is used by default" do + @app.initialize! + assert_equal 1, @app.middleware.count(Rack::Attack) + end + + it "is not added when it was added explicitly" do + @app.config.middleware.use(Rack::Attack) + @app.initialize! + assert_equal 1, @app.middleware.count(Rack::Attack) + end + + it "is not added when it was explicitly deleted" do + @app.config.middleware.delete(Rack::Attack) + @app.initialize! + refute @app.middleware.include?(Rack::Attack) + end end - it "is not added when it was added explicitly" do - @app.config.middleware.use(Rack::Attack) - @app.initialize! - assert_equal 1, @app.middleware.count(Rack::Attack) - end - - it "is not added when it was explicitly deleted" do - @app.config.middleware.delete(Rack::Attack) - @app.initialize! - refute @app.middleware.include?(Rack::Attack) + if Gem::Version.new(Rails::VERSION::STRING) < Gem::Version.new("5") + it "is not used by default" do + @app.initialize! + assert_equal 0, @app.middleware.count(Rack::Attack) + end end end end diff --git a/spec/rack_attack_spec.rb b/spec/rack_attack_spec.rb index 83c3708..647a08d 100644 --- a/spec/rack_attack_spec.rb +++ b/spec/rack_attack_spec.rb @@ -79,7 +79,7 @@ describe 'Rack::Attack' do describe 'enabled' do it 'should be enabled by default' do - Rack::Attack.enabled.must_equal true + _(Rack::Attack.enabled).must_equal true end it 'should directly pass request when disabled' do @@ -87,13 +87,13 @@ describe 'Rack::Attack' do Rack::Attack.blocklist("ip #{bad_ip}") { |req| req.ip == bad_ip } get '/', {}, 'REMOTE_ADDR' => bad_ip - last_response.status.must_equal 403 + _(last_response.status).must_equal 403 prev_enabled = Rack::Attack.enabled begin Rack::Attack.enabled = false get '/', {}, 'REMOTE_ADDR' => bad_ip - last_response.status.must_equal 200 + _(last_response.status).must_equal 200 ensure Rack::Attack.enabled = prev_enabled end