CSRF Protection
Cross-Site Request Forgery (CSRF) protection is offered with every Trongate form. You won't configure it, you won't opt in - it will just work. This page describes the CSRF protection that is built into the validation module.
How It Works
Three automatic steps protect every form:
- generates and injects a hidden CSRF token
- Token is stored in
$_SESSION['csrf_token'] - validates the token on submission
CSRF Protection is Automatic: CSRF protection is automatically integrated into the method. No additional code is required - the framework handles token validation transparently.
What Happens Behind the Scenes
Step 1: Token Generation
When you call :
Trongate generates this HTML:
The token is a cryptographically secure random string generated with bin2hex(random_bytes(32)). This ensures each session has a unique, unpredictable token. Token generation is already implemented in .
Step 2: Token Storage
The token is automatically stored in the user's session:
This session-based approach ensures each user has their own token, preventing cross-user attacks. Token storage is already implemented in .
Step 3: Token Validation
When you call , CSRF protection automatically validates the token:
The framework will automatically:
- Retrieve the submitted token from POST data
- Compare it with the session token using
hash_equals()(timing-safe comparison) - Block the request if tokens don't match or are missing
Timing-Safe Comparison: The framework uses hash_equals() to compare tokens. This prevents timing attacks where an attacker could guess a token by measuring response times.
What Gets Blocked
CSRF protection rejects requests if:
- No CSRF token in the POST data
- CSRF token is not a string
- Token doesn't match the session token
- No session exists
Blocked Request Behavior
When CSRF validation fails:
- Standard forms: The request will be blocked and the user will be redirected
- API/AJAX requests: The request will return HTTP 403 Forbidden
Important: When a CSRF check fails, the user is redirected away from the form. They cannot proceed until they resubmit with a valid token.
Complete Example
Here's a complete form submission flow with automatic CSRF protection:
The View (create.php)
The Controller (Users.php)
CSRF validation is transparent - you don't need to write any special code. The framework handles it entirely within the method.
CSRF Tokens for All Forms: Trongate includes a CSRF token in every form closed with , regardless of whether the form uses POST or GET. The token is harmless for GET forms and provides consistent protection without requiring you to think about it.
Manual Forms (Without Helpers)
If you write HTML forms manually without using and , you must include the token yourself:
However, this is exactly why you should use and - they handle the token automatically and consistently.
Best Practice: Always use the Trongate form helpers. They ensure CSRF tokens are present and correctly formatted with zero effort on your part.
AJAX Requests
For AJAX requests, include the token in the request headers or data:
Or include it in the POST data:
Session Requirements
CSRF protection requires an active session. Ensure:
- Sessions are enabled (PHP's
session_start()is called) - User has a valid session ID (cookie or URL)
- Session doesn't expire during form completion
If a user's session expires while filling out a form, CSRF validation will fail when they submit. They'll need to refresh the page to get a new token.
What You Won't Need to Do
- ✗ Configure CSRF settings
- ✗ Enable CSRF protection
- ✗ Regenerate tokens manually
- ✗ Check tokens in your controllers
- ✗ Write middleware or filters
What You Will Do
- ✓ Use to open forms
- ✓ Use to close forms (generates token)
- ✓ Call to validate submissions (validates token)
- ✓ Use POST requests for state-changing operations
Security Benefits
CSRF protection prevents attackers from:
- Tricking users into performing unwanted actions on your site
- Creating accounts with malicious data
- Transferring funds or resources
- Changing user settings or passwords
- Deleting user data
Example Attack Prevented: An attacker can't trick a logged-in user into submitting a hidden form that transfers money or deletes an account. Even if the form is submitted, the missing or invalid CSRF token blocks the request.
Common Questions
Q: Can I disable CSRF protection?
No, CSRF protection is always enabled for all forms submitted via the form helpers. automatically injects a CSRF token for both GET and POST forms. This is intentional - it's a security feature that should never be disabled.
Q: What if I forget the CSRF token?
If you use the form helpers correctly, you can't forget it. automatically includes the token. If you write manual HTML, the validation will fail and you'll need to add the token.
Q: Do I need CSRF protection for API endpoints?
Yes. API endpoints that modify data (POST, PUT, DELETE) should validate CSRF tokens unless they use alternative authentication methods like OAuth 2.0 or API keys.
Q: What happens after validation fails due to CSRF?
The user is redirected to the home page (BASE_URL). For API requests, a 403 status code is returned. In both cases, the action is not performed.
Q: Are tokens regenerated after each request?
No, tokens are generated once per session and reused. This reduces overhead while maintaining security. The token changes if the session is destroyed and recreated.
Performance Impact
CSRF protection has minimal performance impact:
- Token generation: ~1ms (only happens once per session)
- Token validation: <1ms (timing-safe comparison)
- Storage: ~64 bytes in the session
The security benefits vastly outweigh the negligible performance cost.
CSRF protection in Trongate: It is automatic, secure, and zero configuration. Just use the form helpers and validation - the framework handles the rest.
What's Next
CSRF protection is one part of Trongate's security foundation. Explore related validation topics:
- Form Validation Introduction - Getting started with validation basics
- Validation Rules Reference - Complete list of all built-in validation rules
- Custom Validation Rules - Create your own validation logic with callbacks
We're continually improving the Trongate documentation. If anything is incorrect, unclear, incomplete, or could be better, we'd genuinely appreciate your input.
Share your thoughts in the Documentation Feedback.