Secure your site using a Content Security Policy header
- Content Security Policy adds a security layer to detect and mitigate the risk of Cross Site Scripting (XSS), data injection, and other vulnerabilities.
- The
csp
Drupal module is more feature-complete, but ours has a simpler interface and doesn't allow inline scripts on pages using Drupal AJAX.
This package requires PHP 7.2 and Drupal 8 or higher. It can be installed using Composer:
composer require wieni/wmcontent_security_policy drupal/multivalue_form_element:dev-3199142-drupal-9-compatibility"
For this module to work, it is necessary to patch Drupal core and the Multi-value form element module. If you manage your installation with Composer, you should use the cweagans/composer-patches package to manage and automatically apply patches. If not, please check the documentation for instructions on how to manually apply patches.
If the patches below don't apply to your package versions, you should visit the relevant issues and find older or newer patches.
// composer.json
{
"extra": {
"composer-exit-on-patch-failure": true,
"patches": {
"drupal/core": {
"#2264739: Allow multiple field widgets to not use tabledrag": "https://www.drupal.org/files/issues/2021-01-23/2264739-105.patch"
},
"drupal/multivalue_form_element": {
"#3199172 Handle default values of nested elements": "https://git.drupalcode.org/project/multivalue_form_element/-/merge_requests/2.patch",
"#3199298 Don't add an empty element when the multivalue element is disabled": "https://git.drupalcode.org/project/multivalue_form_element/-/merge_requests/3.patch",
"#3200306 Add support for non-orderable multivalue form elements": "https://git.drupalcode.org/project/multivalue_form_element/-/commit/ef4d01ae56a809fc2349d8fec8185ace3b63d15d.patch"
}
}
}
}
Using the form at /admin/config/system/content-security-policy/default-sources
, you can set default sources for the
different policy directives. These sources should be required for the website to function properly.
Sources you add there are stored in configuration, so you can export them and add them to version control.
To manage these sources, you need the administer default content security policy sources
permission.
Using the form at /admin/config/system/content-security-policy/custom-sources
, you can add custom sources to the
different policy directives.
Sources you add here are stored in the database and will not be exported with configuration. This is useful to allow content editors to add sources required for certain site content.
To manage these sources, you need the administer custom content security policy sources
permission.
If you want to include certain inline scripts (eg. a Google Analytics snippet) without allowing
script-src: 'unsafe-inline'
, you can add the hashes of these scripts to your script-src
policy (more information
here).
You can add script hashes in Twig by using the addCspHash
function:
{{ addCspHash("'sha256-n4MwUTyKKCBlMIFkvcS3dkmlRFEcqSm/V0IOhZelzA0='") }}
You can add script hashes in code by using wmcontent_security_policy.content_security_policy:addScriptHash
:
\Drupal::service('wmcontent_security_policy.content_security_policy')
->addScriptHash("'sha256-n4MwUTyKKCBlMIFkvcS3dkmlRFEcqSm/V0IOhZelzA0='");
Finally, it's also possible to add script hashes like any other source through the administration forms.
One event is provided, which allows you to dynamically add sources right before the header is built.
<?php
use Drupal\wmcontent_security_policy\ContentSecurityPolicyEvents;
use Drupal\wmcontent_security_policy\Event\SourcesAlterEvent;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
class ContentSecurityPolicySourcesSubscriber implements EventSubscriberInterface
{
public static function getSubscribedEvents(): array
{
$events[ContentSecurityPolicyEvents::SOURCES_ALTER][] = ['onSourcesAlter'];
return $events;
}
public function onSourcesAlter(SourcesAlterEvent $event): void
{
if (!empty($_ENV['S3_CNAME'])) {
$event->addSource('script-src', $_ENV['S3_CNAME']);
$event->addSource('connect-src', $_ENV['S3_CNAME']);
$event->addSource('style-src', $_ENV['S3_CNAME']);
}
}
}
All notable changes to this project will be documented in the CHANGELOG file.
If you discover any security-related issues, please email security@wieni.be instead of using the issue tracker.
Distributed under the MIT License. See the LICENSE file for more information.