rack-attack 5.3.0 → 5.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/Rakefile +4 -1
- data/lib/rack/attack.rb +4 -4
- data/lib/rack/attack/store_proxy/redis_cache_store_proxy.rb +13 -8
- data/lib/rack/attack/version.rb +1 -1
- data/spec/acceptance/stores/redis_cache_store_pooled_spec.rb +40 -0
- data/spec/rack_attack_throttle_spec.rb +1 -1
- metadata +6 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f06d0fae1f4dc5d960274ca06a4da7be66a1180a3df051595c98813296e80e46
|
4
|
+
data.tar.gz: 32fa128bb61140836c8fcce73d1cd972c3987405e581a43dea2334d6ba05cfa7
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 7d7be10e1ddb908f07fb10aec414f47fcb9d23289eacd98a1a91e1f87ffa0212d63f424fff44bcfa0b0154263518d807e535bcd8791200c8dc290ea31bd4395e
|
7
|
+
data.tar.gz: c99bfe7df1e11591e80526fd17b414494ddaa797906a4cced2beca884fe51db9fe9ce9d4dd99ee92ac98921a35f87361944ca4d8895b83a86ccc442b6d5cae31
|
data/Rakefile
CHANGED
@@ -2,6 +2,9 @@ require "rubygems"
|
|
2
2
|
require "bundler/setup"
|
3
3
|
require 'bundler/gem_tasks'
|
4
4
|
require 'rake/testtask'
|
5
|
+
require "rubocop/rake_task"
|
6
|
+
|
7
|
+
RuboCop::RakeTask.new
|
5
8
|
|
6
9
|
namespace :test do
|
7
10
|
Rake::TestTask.new(:units) do |t|
|
@@ -20,4 +23,4 @@ end
|
|
20
23
|
desc 'Run tests'
|
21
24
|
task :test => %w[test:units test:integration test:acceptance]
|
22
25
|
|
23
|
-
task :default => :test
|
26
|
+
task :default => [:rubocop, :test]
|
data/lib/rack/attack.rb
CHANGED
@@ -38,15 +38,15 @@ class Rack::Attack
|
|
38
38
|
self.blocklists[name] = Blocklist.new(name, block)
|
39
39
|
end
|
40
40
|
|
41
|
-
def blocklist_ip(
|
41
|
+
def blocklist_ip(ip_address)
|
42
42
|
@ip_blocklists ||= []
|
43
|
-
ip_blocklist_proc = lambda { |request| IPAddr.new(
|
43
|
+
ip_blocklist_proc = lambda { |request| IPAddr.new(ip_address).include?(IPAddr.new(request.ip)) }
|
44
44
|
@ip_blocklists << Blocklist.new(nil, ip_blocklist_proc)
|
45
45
|
end
|
46
46
|
|
47
|
-
def safelist_ip(
|
47
|
+
def safelist_ip(ip_address)
|
48
48
|
@ip_safelists ||= []
|
49
|
-
ip_safelist_proc = lambda { |request| IPAddr.new(
|
49
|
+
ip_safelist_proc = lambda { |request| IPAddr.new(ip_address).include?(IPAddr.new(request.ip)) }
|
50
50
|
@ip_safelists << Safelist.new(nil, ip_safelist_proc)
|
51
51
|
end
|
52
52
|
|
@@ -8,21 +8,26 @@ module Rack
|
|
8
8
|
defined?(::ActiveSupport::Cache::RedisCacheStore) && store.is_a?(::ActiveSupport::Cache::RedisCacheStore)
|
9
9
|
end
|
10
10
|
|
11
|
-
def increment(name, amount, options = {})
|
12
|
-
#
|
13
|
-
|
14
|
-
|
15
|
-
|
11
|
+
def increment(name, amount = 1, options = {})
|
12
|
+
# RedisCacheStore#increment ignores options[:expires_in].
|
13
|
+
#
|
14
|
+
# So in order to workaround this we use RedisCacheStore#write (which sets expiration) to initialize
|
15
|
+
# the counter. After that we continue using the original RedisCacheStore#increment.
|
16
|
+
if options[:expires_in] && !read(name)
|
17
|
+
write(name, amount, options)
|
18
|
+
|
19
|
+
1
|
20
|
+
else
|
21
|
+
super
|
16
22
|
end
|
17
|
-
count.first
|
18
23
|
end
|
19
24
|
|
20
25
|
def read(name, options = {})
|
21
|
-
super(name, options.merge!(
|
26
|
+
super(name, options.merge!(raw: true))
|
22
27
|
end
|
23
28
|
|
24
29
|
def write(name, value, options = {})
|
25
|
-
super(name, value, options.merge!(
|
30
|
+
super(name, value, options.merge!(raw: true))
|
26
31
|
end
|
27
32
|
end
|
28
33
|
end
|
data/lib/rack/attack/version.rb
CHANGED
@@ -0,0 +1,40 @@
|
|
1
|
+
require_relative "../../spec_helper"
|
2
|
+
require_relative "../../support/cache_store_helper"
|
3
|
+
|
4
|
+
require "timecop"
|
5
|
+
|
6
|
+
if ActiveSupport.version >= Gem::Version.new("5.2.0")
|
7
|
+
describe "RedisCacheStore (pooled) as a cache backend" do
|
8
|
+
before do
|
9
|
+
Rack::Attack.cache.store = ActiveSupport::Cache::RedisCacheStore.new(pool_size: 2)
|
10
|
+
end
|
11
|
+
|
12
|
+
after do
|
13
|
+
Rack::Attack.cache.store.clear
|
14
|
+
end
|
15
|
+
|
16
|
+
it_works_for_cache_backed_features
|
17
|
+
|
18
|
+
it "doesn't leak keys" do
|
19
|
+
Rack::Attack.throttle("by ip", limit: 1, period: 1) do |request|
|
20
|
+
request.ip
|
21
|
+
end
|
22
|
+
|
23
|
+
key = nil
|
24
|
+
|
25
|
+
# Freeze time during these statement to be sure that the key used by rack attack is the same
|
26
|
+
# we pre-calculate in local variable `key`
|
27
|
+
Timecop.freeze do
|
28
|
+
key = "rack::attack:#{Time.now.to_i}:by ip:1.2.3.4"
|
29
|
+
|
30
|
+
get "/", {}, "REMOTE_ADDR" => "1.2.3.4"
|
31
|
+
end
|
32
|
+
|
33
|
+
assert Rack::Attack.cache.store.fetch(key)
|
34
|
+
|
35
|
+
sleep 2.1
|
36
|
+
|
37
|
+
assert_nil Rack::Attack.cache.store.fetch(key)
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
@@ -37,7 +37,7 @@ describe 'Rack::Attack.throttle' do
|
|
37
37
|
it 'should tag the env' do
|
38
38
|
last_request.env['rack.attack.matched'].must_equal 'ip/sec'
|
39
39
|
last_request.env['rack.attack.match_type'].must_equal :throttle
|
40
|
-
last_request.env['rack.attack.match_data'].must_equal(
|
40
|
+
last_request.env['rack.attack.match_data'].must_equal(:count => 2, :limit => 1, :period => @period)
|
41
41
|
last_request.env['rack.attack.match_discriminator'].must_equal('1.2.3.4')
|
42
42
|
end
|
43
43
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rack-attack
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 5.3.
|
4
|
+
version: 5.3.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Aaron Suggs
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-06-
|
11
|
+
date: 2018-06-20 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rack
|
@@ -212,14 +212,14 @@ dependencies:
|
|
212
212
|
requirements:
|
213
213
|
- - '='
|
214
214
|
- !ruby/object:Gem::Version
|
215
|
-
version: 0.
|
215
|
+
version: 0.57.2
|
216
216
|
type: :development
|
217
217
|
prerelease: false
|
218
218
|
version_requirements: !ruby/object:Gem::Requirement
|
219
219
|
requirements:
|
220
220
|
- - '='
|
221
221
|
- !ruby/object:Gem::Version
|
222
|
-
version: 0.
|
222
|
+
version: 0.57.2
|
223
223
|
- !ruby/object:Gem::Dependency
|
224
224
|
name: timecop
|
225
225
|
requirement: !ruby/object:Gem::Requirement
|
@@ -303,6 +303,7 @@ files:
|
|
303
303
|
- spec/acceptance/safelisting_spec.rb
|
304
304
|
- spec/acceptance/safelisting_subnet_spec.rb
|
305
305
|
- spec/acceptance/stores/mem_cache_store_spec.rb
|
306
|
+
- spec/acceptance/stores/redis_cache_store_pooled_spec.rb
|
306
307
|
- spec/acceptance/stores/redis_cache_store_spec.rb
|
307
308
|
- spec/acceptance/throttling_spec.rb
|
308
309
|
- spec/acceptance/track_spec.rb
|
@@ -367,6 +368,7 @@ test_files:
|
|
367
368
|
- spec/acceptance/fail2ban_spec.rb
|
368
369
|
- spec/acceptance/stores/mem_cache_store_spec.rb
|
369
370
|
- spec/acceptance/stores/redis_cache_store_spec.rb
|
371
|
+
- spec/acceptance/stores/redis_cache_store_pooled_spec.rb
|
370
372
|
- spec/acceptance/customizing_blocked_response_spec.rb
|
371
373
|
- spec/spec_helper.rb
|
372
374
|
- spec/allow2ban_spec.rb
|