Ratelimiter#2309
Merged
Merged
Conversation
Implemented IP-based rate limiting to protect against CAPEC-212 (Functionality Misuse) attacks: - Added RateLimiter GenServer to track rate limits per IP address - Added IPHelper module for DRY IP extraction across the application - Integrated rate limiting into game creation workflow - Integrated rate limiting into player creation workflow - Added RateLimiter to application supervision tree - Comprehensive test suite for rate limiter functionality Rate limits (configurable via environment variables): - Game creation: 10 per hour per IP - Player creation: 20 per hour per IP - WebSocket connections: 50 per 5 minutes per IP This ensures service availability under attack while maintaining usability for legitimate users.
- Implemented rate limiting for WebSocket connections (50 per 5 minutes per IP) - Updated endpoint to pass peer_data for IP extraction - Added comprehensive tests for WebSocket rate limiting - Created SECURITY.md documenting the complete rate limiting implementation - Includes configuration, architecture details, and future enhancements This completes the full protection against CAPEC-212 attacks for all entry points.
…in previous commit) - Added IPHelper module tests covering all functions - Added game creation rate limiting integration test - Added player creation rate limiting integration test - Changed async: false for rate limiter tests to avoid conflicts - All tests verify rate limiting enforcement and error messages
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
Copilot Feedback Fixes: - Added X-Forwarded-For support for reverse proxy scenarios - Added error handling for env var parsing (prevents boot failures) - Already added logging for rate limit violations (previous commit) - Fixed markdown table formatting in SECURITY.md New Features: - IPHelper now reads X-Forwarded-For header to get real client IP - Falls back to remote_ip if header missing/invalid - Environment variable parsing validates positive integers - Logs warnings for invalid config, uses defaults gracefully Additional Tests: - CreateGameForm component tests - FormComponent (player creation) tests - Application supervision tree tests - Endpoint configuration tests - X-Forwarded-For header handling tests - Invalid environment variable handling tests Documentation Updates: - Documented X-Forwarded-For proxy support in SECURITY.md - Documented env var validation requirements - Updated all Copilot suggestions resolved
Test Setup Fixes: - Fixed LiveView test setup to provide IP addresses via connect_info - Added peer_data configuration to all LiveView test files - Resolves 'Unable to determine IP address from socket' RuntimeError New Test Files: - Added router_test.exs: Tests all routes and pipelines - Added telemetry_test.exs: Tests telemetry supervisor and metrics Enhanced Existing Tests: - rate_limiter_test.exs: Added IP normalization, cleanup, and malformed input tests - ip_helper_test.exs: Added X-Forwarded-For edge cases, IPv6, and whitespace handling Coverage improvements target 80% threshold for CI/CD pipeline success
Added new test files: - game_form_helpers_test.exs: Tests all suit formatting and edition handling functions - gettext_test.exs: Tests internationalization helpers - error_json_test.exs: Tests JSON error rendering for multiple status codes - page_html_test.exs: Tests page template embedding Enhanced existing tests: - cornucopia_logic_test.exs: Added 9 new tests for scoring logic, card filtering, vote requirements, joker/trump handling, and card aggregation functions Coverage improvements: - Tests GameFormHelpers: generate_suit_list, format_suits, display_appropriate_suits - Tests Cornucopia scoring: highest_scoring_cards, played_cards, unplayed_cards, voting - Tests error handling: 404, 500, 401, 403, 422, and custom status codes - Tests gettext: translations, interpolation, domains, plurals - Tests all edge cases: empty lists, wild cards, suit mismatches, vote thresholds These additions target untested modules and complex logic branches to exceed 80% coverage
Moved import CopiWeb.Gettext to module level so functions are available to all tests
- Simplified gettext test to only check module configuration (gettext macros are compile-time) - Updated 422 error message to 'Unprocessable Content' (Phoenix updated) - Fixed unused variable warning in form_component_test.exs
…alhost IP instead of raising exceptions when IP unavailable, add comprehensive LiveView tests for delete/broadcast scenarios
…HTML from successful form submissions
…direct assertions, API params, and endpoint config
…t patterns, and simplify UI tests
…t, redirect patterns, validation tests
…lear rate limits in all setups
Changes requested by sydseter: - Skip rate limiting for 127.0.0.1 in production to prevent self-DoS - Update default limits: game (10->20), player (20->60), connections (50->333) - Update connection window from 300s to 1s for connections/second limiting - Add production environment variables to fly.toml - Update SECURITY.md documentation with new limits The rate limiter now checks if running in production before applying limits to localhost. Warning logging for rate_limit_exceeded is in place.
Fixed issues identified by sydseter: - Use monotonic_time in cleanup to match check_rate timing - Convert window to milliseconds in cleanup filter - Remove password fallback in test config
…t/rate-limit-implementation-clean Resolved conflict in player_live_test.exs by accepting incoming test changes from master
Restores two tests that were accidentally removed during merge: - 'displays player information' test - 'handles game updates via broadcast' test These tests cover important code paths for LiveView rendering and broadcast handling, restoring coverage from 79.7% to ~81%.
The previous test just sent a message without verifying it was processed. Now using Phoenix.PubSub.broadcast with proper topic and adding assertion to verify LiveView processes the update.
Adds two new tests to cover untested code paths: - Toggle continue vote off (remove existing vote) - Handle next round event when round is open These tests cover the continue voting logic added in the master merge, pushing coverage back above 80%.
1. Fixed broadcast test to send message in correct format:
- handle_info expects map with topic/event/payload
- Was sending tuple {:game_updated, game}
- Now sends %{topic:, event:, payload:}
2. Fixed rate limiter test assertion:
- Connection window is 1 second (for 333 req/s)
- Changed assertion from >= 60 to >= 1
3. Removed redundant next round test that had same issue
Changed from accessing socket.private.connect_info directly to using Phoenix.LiveView.get_connect_info/2 which is the recommended public API. This prevents potential bugs from internal implementation changes and follows Phoenix best practices. Also added :peer_data to endpoint connect_info configuration to ensure the data is available via the public API. Addresses feedback from @sydseter
Use safe [:key] access instead of .key to avoid raising when keys don't exist. This works with both production sockets and test mocks.
Contributor
Collaborator
Author
|
npm audit is down which is why the website build fails. The website isn’t touched here. |
rewtd
approved these changes
Feb 19, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
In this pull-request: