Skip to content

multi: add Rack::Attack rate limiting throttling and GET /v1/sismos/stats endpoint - #3

Merged
Euler-B merged 1 commit into
mainfrom
feature/rate-limiting-rack-attack
Aug 4, 2026
Merged

multi: add Rack::Attack rate limiting throttling and GET /v1/sismos/stats endpoint#3
Euler-B merged 1 commit into
mainfrom
feature/rate-limiting-rack-attack

Conversation

@Euler-B

@Euler-B Euler-B commented Aug 3, 2026

Copy link
Copy Markdown
Owner

Summary by CodeRabbit

  • New Features
    • Added an earthquake statistics endpoint covering total and recent activity, tsunami counts, maximum magnitude details, and magnitude-type breakdowns.
  • Security & Reliability
    • Added request rate limiting to help prevent excessive traffic.
    • POST report submissions now have dedicated throttling.
    • Rate-limit responses return HTTP 429 with a Retry-After indicator.
  • Tests
    • Added coverage for earthquake statistics and rate-limiting behavior, including throttling responses and retry guidance.

@Euler-B Euler-B self-assigned this Aug 3, 2026
@coderabbitai

coderabbitai Bot commented Aug 3, 2026

Copy link
Copy Markdown

Review Change Stack

Walkthrough

The API adds a /v1/sismos/stats endpoint for aggregate earthquake data. Rack::Attack adds IP-based throttling and JSON 429 responses. The release workflow now uses restricted permissions, pinned actions, SemVer validation, and controlled Docker tags. The review path filter now excludes directory-local .keep files.

Changes

Earthquake statistics endpoint

Layer / File(s) Summary
Statistics endpoint flow
config/routes.rb, app/controllers/sismos_controller.rb, test/controllers/sismos_controller_test.rb
The API exposes GET /v1/sismos/stats. The controller returns totals, recent activity, tsunami counts, maximum magnitude data, and magnitude-type groups. Tests validate the response.

Rack::Attack throttling

Layer / File(s) Summary
Middleware and throttle configuration
Gemfile, config/application.rb, config/initializers/rack_attack.rb, test/test_helper.rb
Rack::Attack uses Redis when configured and an in-memory store otherwise. It applies IP limits for general requests and POST report submissions. Exceeded limits return JSON HTTP 429 responses with Retry-After.
Rate limit integration coverage
test/integration/rate_limiting_test.rb
Integration tests cover allowed requests, general request throttling, report submission throttling, 429 payloads, and Retry-After.

Release workflow permissions and action pinning

Layer / File(s) Summary
Release workflow hardening
.github/workflows/release.yml
The workflow grants read access by default, limits write permissions to the publish job, pins actions, disables persisted checkout credentials, validates SemVer tags, and restricts the latest Docker tag to non-prerelease releases.

Review path filter

Layer / File(s) Summary
Keep-file path filter
.coderabbit.yaml
The path filter now excludes .keep files located in any directory.

Estimated code review effort: 3 (Moderate) | ~30 minutes

Sequence Diagram(s)

sequenceDiagram
  participant Client
  participant SismosController
  participant EarthquakeData
  Client->>SismosController: GET /v1/sismos/stats
  SismosController->>EarthquakeData: calculate statistics
  EarthquakeData-->>SismosController: aggregate metrics
  SismosController-->>Client: stats JSON response
Loading
sequenceDiagram
  participant Client
  participant RackAttack
  participant RailsApplication
  Client->>RackAttack: HTTP request
  RackAttack->>RailsApplication: forward request within limit
  RailsApplication-->>Client: application response
  RackAttack-->>Client: HTTP 429 and Retry-After after limit
Loading

Possibly related PRs

  • Euler-B/Telurify-API#2: Both PRs modify SismosController and its tests. This PR adds statistics, while that PR implements filtering.
🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly summarizes the two primary changes: Rack::Attack rate limiting and the sismos statistics endpoint.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feature/rate-limiting-rack-attack

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@app/controllers/sismos_controller.rb`:
- Around line 205-211: Update serialize_stats so the returned data resource
includes a stable id alongside type and attributes. Use the endpoint’s
established stable stats identifier, while preserving the existing stats_data
attributes and resource type.

In `@config/initializers/rack_attack.rb`:
- Around line 12-13: Update the reports/ip throttle matcher in the Rack::Attack
configuration to accept optional format suffixes such as .json while retaining
the existing endpoint and POST constraints. Add an integration test covering a
formatted POST report request and verifying it is subject to the 5-per-minute
report limit.
- Line 4: Replace the process-local MemoryStore assignment in the Rack::Attack
initializer with Rails.cache. Add the redis gem dependency and configure the
production cache store as redis_cache_store using the required REDIS_URL
environment variable, so Rack::Attack shares the Rails Redis-backed cache across
Puma workers.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: af266033-f2d3-44d5-bdb4-eba7f5520f2c

📥 Commits

Reviewing files that changed from the base of the PR and between e65fa7a and c263af2.

⛔ Files ignored due to path filters (1)
  • Gemfile.lock is excluded by !**/*.lock, !Gemfile.lock
📒 Files selected for processing (9)
  • .coderabbit.yaml
  • Gemfile
  • app/controllers/sismos_controller.rb
  • config/application.rb
  • config/initializers/rack_attack.rb
  • config/routes.rb
  • test/controllers/sismos_controller_test.rb
  • test/integration/rate_limiting_test.rb
  • test/test_helper.rb

Comment thread app/controllers/sismos_controller.rb
Comment thread config/initializers/rack_attack.rb Outdated
Comment thread config/initializers/rack_attack.rb Outdated
@Euler-B
Euler-B force-pushed the feature/rate-limiting-rack-attack branch from c263af2 to f3aff8b Compare August 4, 2026 11:52

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In @.github/workflows/release.yml:
- Line 96: Optionally replace the pinned softprops/action-gh-release step with
the preinstalled gh CLI, using gh release create and its --generate-notes option
to preserve automatic release-note generation and the existing release behavior.
- Around line 60-62: Add a concise explanatory comment immediately above the
permissions block in the release workflow, documenting why the release job
requires contents: write and packages: write. Keep the existing permission
values unchanged.
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: c7ffcc50-c44b-4ea1-bfc5-a3eb58364c78

📥 Commits

Reviewing files that changed from the base of the PR and between c263af2 and f3aff8b.

⛔ Files ignored due to path filters (1)
  • Gemfile.lock is excluded by !**/*.lock, !Gemfile.lock
📒 Files selected for processing (10)
  • .coderabbit.yaml
  • .github/workflows/release.yml
  • Gemfile
  • app/controllers/sismos_controller.rb
  • config/application.rb
  • config/initializers/rack_attack.rb
  • config/routes.rb
  • test/controllers/sismos_controller_test.rb
  • test/integration/rate_limiting_test.rb
  • test/test_helper.rb

Comment thread .github/workflows/release.yml
Comment thread .github/workflows/release.yml Outdated
@Euler-B
Euler-B force-pushed the feature/rate-limiting-rack-attack branch from f3aff8b to fdbf5de Compare August 4, 2026 12:55

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@config/initializers/rack_attack.rb`:
- Around line 6-16: Update the Redis configuration in the Rack::Attack cache
setup to validate that production Redis URLs use the rediss:// scheme before
constructing ActiveSupport::Cache::RedisCacheStore. Reject non-TLS URLs in
production while preserving the existing missing-URL error and non-production
MemoryStore fallback.

In `@test/controllers/sismos_controller_test.rb`:
- Line 126: Update the assertion in the stats response test to verify that
attrs['by_mag_type']['ml'] equals the fixture’s expected count of 2, rather than
only checking that the 'ml' key exists.
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: 81e1bb61-0d1f-4de2-861d-8e3591b2e3ff

📥 Commits

Reviewing files that changed from the base of the PR and between f3aff8b and fdbf5de.

⛔ Files ignored due to path filters (1)
  • Gemfile.lock is excluded by !**/*.lock, !Gemfile.lock
📒 Files selected for processing (10)
  • .coderabbit.yaml
  • .github/workflows/release.yml
  • Gemfile
  • app/controllers/sismos_controller.rb
  • config/application.rb
  • config/initializers/rack_attack.rb
  • config/routes.rb
  • test/controllers/sismos_controller_test.rb
  • test/integration/rate_limiting_test.rb
  • test/test_helper.rb

Comment thread config/initializers/rack_attack.rb
Comment thread test/controllers/sismos_controller_test.rb
@Euler-B
Euler-B merged commit 1732921 into main Aug 4, 2026
3 checks passed
@Euler-B
Euler-B deleted the feature/rate-limiting-rack-attack branch August 4, 2026 13:09
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

Successfully merging this pull request may close these issues.

1 participant