Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feature request: testing helpers #645

Open
fatkodima opened this issue Dec 30, 2023 · 1 comment
Open

Feature request: testing helpers #645

fatkodima opened this issue Dec 30, 2023 · 1 comment

Comments

@fatkodima
Copy link
Contributor

Currently, to test rack-attack's behavior we need to use something like:

context "number of requests is lower than the limit" do
  it "does not change the request status" do
    1000.times do
      get "/", {}, "REMOTE_ADDR" => "1.2.3.4"
      expect(last_response.status).to_not eq(429)
    end
  end
end

to perform a lot of unneeded requests (depending on the throttling configuration) or use some internals from the gem like:

def emulate_previous_requests(key, count:, period:)
  # Go to the rack-attack's internals to make tests faster.
  key, expires_in = Rack::Attack.cache.send(:key_and_expiry, key, period)
  Rack::Attack.cache.store.write(key, count, expires_in: expires_in)
end

# and use the `emulate_previous_requests` helper in tests

This can be also solved by using some constants in the rack-attack configuration block and then assign some smaller numbers to these constants in the testing environment, but this is ugly if we have a lot of different constants.

It would be nice to have some test helpers to simplify write the tests.
I can help with this, but needs to figure out the API.

@RobsonKing
Copy link

This request help me work around a related problem... We found that some of our tests can fail if they happen to run during the time rack attack has chosen as the expiry.... Since it seems like the expiry is chosen based on a modulus of time...

def sleep_if_required(interval)
  # rack attack uses a modulus of time to choose when to rest things...
  # https://github.com/rack/rack-attack/blob/d7a7a8bda5cba232d8d5d300b95cef79d40cc528/lib/rack/attack/cache.rb#L69

  # so if we are running when the reset is going to happen... our test can fail :(
  # so if it looks like we are going to be close... sleep until the start of the new period

  mod = Time.now.to_i % interval
  dif = interval - mod
  if dif < 2
    puts "sleeping till new rack attack period #{(dif + 1)}"
    sleep((dif + 1).seconds)
  end
end

Its not a great solution, and i would love some other test helper that could help work around this...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants