Security Hardening
Unfold CMS includes multiple layers of security protection out of the box. This page covers the security features, packages, and best practices for keeping your site secure.
Security Headers
Unfold CMS configures security headers using the bepsvpt/secure-headers package. These headers instruct browsers to enforce security policies.
Default Headers
| Header | Value | Purpose |
|---|---|---|
| X-Frame-Options | SAMEORIGIN |
Prevents clickjacking by blocking iframe embedding |
| X-XSS-Protection | 1; mode=block |
Enables browser XSS filtering |
| X-Content-Type-Options | nosniff |
Prevents MIME type sniffing |
| Strict-Transport-Security | max-age=31536000; includeSubDomains; preload |
Forces HTTPS connections |
| Referrer-Policy | no-referrer-when-downgrade |
Controls referrer information |
Security headers can be configured in Settings > Security in the admin panel.
Content Security Policy (CSP)
spatie/laravel-csp manages Content Security Policy headers, controlling what resources the browser is allowed to load. CSP helps prevent XSS attacks, data injection, and unauthorized script execution.
How It Works
CSP is disabled by default. When enabled, the browser enforces restrictions on which domains can serve scripts, styles, images, and other resources on your site.
To enable CSP, go to Settings > Security and turn on Content Security Policy.
Policy Details
When CSP is enabled, the following policy applies:
| Directive | Allowed Sources | Purpose |
|---|---|---|
default-src |
'self' |
Fallback for unspecified directives |
script-src |
'self', 'unsafe-inline', 'unsafe-eval', https: |
JavaScript execution |
style-src |
'self', 'unsafe-inline', https: |
CSS stylesheets |
img-src |
'self', data:, blob:, https: |
Images |
font-src |
'self', data:, https: |
Web fonts |
connect-src |
'self', https: |
AJAX, WebSocket, fetch |
frame-src |
'self', https: |
Embedded iframes |
media-src |
'self', https: |
Audio and video |
object-src |
'none' |
Blocks Flash and plugins |
form-action |
'self' |
Form submission targets |
frame-ancestors |
'self' |
Who can embed your site |
The policy allows all HTTPS sources (https:) to ensure compatibility with third-party services like Google Tag Manager, Google Analytics, Meta Pixel, chat widgets, and any other scripts added via Code Snippets.
Note: CSP is disabled by default because many third-party integrations require external resources. Enable it only if you understand the implications and have tested that your site works correctly with it.
XSS Prevention
Unfold CMS uses mews/purifier (HTMLPurifier) to sanitize all user-generated HTML content before storage.
Additional Protections
| Protection | Method |
|---|---|
| CSRF tokens | All forms include @csrf tokens |
| Input escaping | Blade {{ }} syntax escapes by default |
| SQL injection prevention | Eloquent ORM uses parameterized queries |
| Mass assignment protection | Models define $fillable or $guarded |
Spam Prevention
The spatie/laravel-honeypot package protects forms from automated bots.
Honeypot protection is applied to comment forms, contact forms, newsletter subscription forms, and registration forms. Add honeypot to any form with the @honeypot Blade directive:
<form method="POST" action="/submit">
@csrf
@honeypot
<!-- form fields -->
</form>
Activity Logging
The spatie/laravel-activitylog package records user actions for audit purposes.
The activity log records user login/logout events, content changes, settings changes, role changes, and user management actions. Administrators can view the full activity log in the admin panel.
File Upload Security
File uploads are validated and secured:
| Protection | Description |
|---|---|
| Extension whitelist | Only allowed file types can be uploaded |
| File size limits | Configurable per-file size limit |
| Path traversal prevention | Upload paths are sanitized |
| Dangerous extension blocking | .php, .phtml, .sh, .exe, .phar are rejected |
| Double extension prevention | Files like file.php.jpg are blocked |
| PHP execution blocking | PHP execution is disabled in upload directories |
Upload limits and allowed file types can be configured in Settings > Media in the admin panel.
Server-Level Security
Server-level protections (primarily via .htaccess for Apache) can be configured in Settings > Security. These include directory listing prevention, sensitive file blocking, PHP execution prevention in upload directories, dotfile access blocking, server header removal, gzip compression, and expires headers.
Rate Limiting
The CMS applies rate limits to prevent abuse:
| Endpoint | Limit |
|---|---|
| Login | 5 per minute |
| Password Reset | 3 per minute |
| API Requests | 60 per minute |
| File Uploads | 10 per minute |
| Form Submissions | 5 per minute |
| Admin Panel | 30 per minute |
HTTPS Enforcement
For production sites, enable HTTPS enforcement:
- Obtain an SSL certificate (Let's Encrypt is free)
- Enable
general.force_httpsin Settings > General - The HSTS header (enabled by default) instructs browsers to always use HTTPS
Security Checklist
After deploying to production:
- [ ] Set
APP_DEBUG=falsein.env - [ ] Set
APP_ENV=productionin.env - [ ] Enable HTTPS and set
general.force_httpstotrue - [ ] Set
.envfile permissions to0600 - [ ] Change the default admin password
- [ ] Review and configure security headers
- [ ] Ensure upload directories have correct permissions
- [ ] Set up regular backups
- [ ] Review rate limiting settings
- [ ] Remove or disable the installation wizard routes
Security Packages
- mews/purifier — Sanitizes HTML to prevent XSS
- spatie/laravel-csp — Content Security Policy headers
- spatie/laravel-honeypot — Invisible form spam protection
- spatie/laravel-activitylog — Audit logging
- bepsvpt/secure-headers — Security response headers
- laravel/fortify — Authentication with 2FA
Related
- Authentication — Login, 2FA, and social login
- Roles & Permissions — Access control
- Configuration — Security settings reference