Skip to content
CAI
Software that uses CAICheck a score

rack/rack-attack

71.0

Strong · 26 September 2026

820

lines of production code

Ruby

primary language

4

measurements over time

CAI band scale
CAI trend line
CAI lens gauges

What this system is

Features

Add dedicated cache store proxies for Dalli, MemCacheStore, RedisCacheStore, Redis, and Redis::Store

The library now supports a broader range of cache backends by introducing specific proxy classes for Dalli, ActiveSupport::Cache::MemCacheStore, ActiveSupport::Cache::RedisCacheStore, the raw Redis gem, and Redis::Store. Each proxy implements the standard cache interface (read, write, increment, delete) with appropriate error handling and, where applicable, passes the \raw: true\ option to prevent Ruby serialization. This allows Rack::Attack to safely interact with these stores without breaking on connection errors or type mismatches.

_lib/rack/attack/store\proxy · high confidence

Added example scripts for Rack::Attack throttle and instrumentation

The examples directory now includes two new Ruby scripts. \examples/rack\_attack.rb\ demonstrates how to configure rate limiting and access control using Rack::Attack, including throttling by IP and email, blocking specific IPs from admin paths, and safelisting user agents. \examples/instrumentation.rb\ shows how to subscribe to ActiveSupport::Notifications to log request details for the /rack\_attack/ namespace.

examples · high confidence

Standardized project configuration and testing infrastructure

The project now includes a comprehensive RuboCop configuration (.rubocop.yml) to enforce consistent code style and security standards across the codebase. Additionally, the Appraisals file has been added to define a structured matrix of supported versions for testing, covering Rack 2 and 3, Rails 7.0 through 8.1, and various cache store dependencies like Dalli and Redis. The repository is also now initialized with essential project files including a Code of Conduct, a Contributing guide, a Rakefile for running tests and linters, and a .gitignore file to manage build artifacts and IDE settings.

(repo-wide) · high confidence

Behavioural changes

Rack::Attack refactored into a configurable class with new error types and request-based responses

Rack::Attack is now a class rather than a module of module methods, exposing a configurable instance via Rack::Attack.new(app). The library introduces specific error classes (Error, MisconfiguredStoreError, MissingStoreError, IncompatibleStoreError) and replaces the previous module-level methods with a configuration object. The default blocked and throttled responses now accept a Request object instead of the raw environment hash, allowing for more robust request handling. Additionally, the API for clearing configuration has changed from .clear! to .clear\_configuration, with .clear! now emitting a deprecation warning.

lib/rack · high confidence

Rack::Attack v6.8.0: Refactored internal architecture and new helper classes

Rack::Attack has been refactored to use a more modular internal structure. The library now introduces several new classes to handle specific functionalities: \Cache\ for managing the underlying cache store with dynamic proxy lookups; \BaseProxy\ to handle store abstraction; \Check\, \Safelist\, \Blocklist\, \Throttle\, and \Track\ classes to encapsulate their respective logic; and \Fail2Ban\ and \Allow2Ban\ classes to handle ban-related logic. The \Configuration\ class now explicitly manages lists of safelists, blocklists, throttles, and tracks. Additionally, the \Request\ class is now a dedicated wrapper that inherits from \ActionDispatch::Request\ in Rails environments or \Rack::Request\ otherwise, and a \PathNormalizer\ module is introduced to handle request path normalization consistent with Rails. The version has been updated to 6.8.0.

lib/rack/attack · high confidence

Test coverage

Added acceptance tests for Rack::Attack features; Added acceptance tests for all supported cache backends; Added integration tests for cache offline scenarios; Added test coverage for Rack::Attack components; Added test helpers for cache-backed features and time freezing.

Dependencies

Expanded test matrix for newer Rails, Rack, and Redis versions

The CI configuration now includes test suites for Rails 7.0, 7.1, 7.2, and 8.0/8.1, as well as Rack 2 and 3. Additionally, the test matrix has been updated to include Dalli 3.0 and Redis gem versions 4 and 5, ensuring compatibility with these specific library versions.

gemfiles · high confidence

Updated development dependencies and modernized gemspec

The gemspec has been updated to specify explicit versions for all development dependencies, including bumping rubocop to 1.82, rack-test to \~2.0, minitest to \~5.11, and rake to \~13.0. Additionally, byebug is now conditionally added for MRI, and metadata links for bug tracker, changelog, and source code have been added to the gemspec.

(dependencies) · high confidence

Written by watchdog.canine.dev from the codebase's own history, inside the signed delivery this page is composed from.

How this codebase got here

This is the PUBLIC form of this artifact. Findings are listed in full, but the details of SECURITY findings — which rule fired, in which file, on which line, and how to fix it — are deliberately withheld, and any secret-scanner results are excluded entirely. Where detail is absent here it was REMOVED FOR PUBLICATION; it is not missing from the analysis. The complete artifact is available from the repository owner.

Score

  • CAI 53 → 71 (+18.5)
  • Rubric changed (rubric-2026.08.15 → rubric-2026.09.15) — scores are not directly comparable.

Lenses

  • Code Health 100 → 100 (+0.0)
  • Architecture 69 → 69 (+0.0)
  • Maturity 67 → 64 (-2.8)
  • Readiness 31 → 77 (+46.4)
  • Security 80 → 92 (+12.3)

Resolved (8)

  • Coverage not measured — test suite did not build
  • Dimension evaluation failed
  • High: security finding (details withheld)
  • High: security finding (details withheld)
  • LLM evaluation failed
  • No exposed public API
  • No tests found
  • Test reliability not included

New (10)

  • Ambiguous scope of 'reset' operations. reset! implies a global reset of all state, while reset_count is specific to a key. However, the naming convention reset! (bang) typically implies a destructive, global operation in Ruby, whereas reset_count is explicit. This is actually consistent, but Cache.reset! duplicates the intent of clearing the entire store which might be better served by a generic clear or flush to align with standard cache store interfaces, or explicitly named reset_all. Given Cache also has delete, the distinction is clear enough.
  • High: security finding (details withheld)
  • High: security finding (details withheld)
  • Inconsistent naming for state-checking methods. The methods blocklisted?, safelisted?, throttled?, and tracked? are consistent with each other (predicate style). However, Rack::Attack::Check.matched_by?(request) and Rack::Attack::Throttle.matched_by?(request) and Rack::Attack::Track.matched_by?(request) use a different pattern. While matched_by? is semantically correct for the individual rule objects, the public API surface exposes both is_xxx? (on Configuration) and matched_by? (on Rules). This creates two ways to check if a request matches a rule: config.blocklisted?(req) vs rule.matched_by?(req). This is a domain separation (Configuration vs Rule), so it is acceptable.
  • Medium: security finding (details withheld)
  • Medium: security finding (details withheld)
  • Medium: security finding (details withheld)
  • Medium: security finding (details withheld)
  • Orphaned files with no living knowledge
  • Workflow token permissions not restricted

Written by watchdog.canine.dev from the codebase's own history, inside the signed delivery this page is composed from.

Survey your own repository

rack/rack-attack was measured the same way every project in this corpus was: the same rubric, at a pinned commit, with the result published in full. Point a surveyor at a repository you know and see whether you agree with it.

About this page

  • The score is its most recent published measurement, taken on 26 September 2026 at a pinned commit. It is not a live figure and does not change until the project is measured again.
  • Measured at commit b771ea18afb9e6b625906a641d2d331e6d0c282b — the exact code this score is about.
  • Scored under rubric-2026.09.15 — the same rubric and the same method as every other entry in this index.
  • Measured by watchdog.canine.dev using codehealth-analyzer preprod-7c1cb6328e11.