轻松为您的项目添加和更新Content-Security-Policy头部

v3.0.1 2024-05-08 13:05 UTC

README

Build Status Psalm Status Latest Stable Version Latest Unstable Version License Downloads

轻松将Content-Security-Policy头部集成到您的Web应用程序中,无论是从JSON配置文件还是通过编程方式。

CSP Builder是由Paragon Initiative Enterprises创建的,作为我们鼓励更好的应用程序安全实践的一部分。

也请查看我们的其他开源项目

还有一个CSP中间件可用,它使用这个库。

安装

首先,获取Composer,然后运行

composer require paragonie/csp-builder

从JSON配置文件构建Content Security Policy头部

<?php

use ParagonIE\CSPBuilder\CSPBuilder;

$csp = CSPBuilder::fromFile('/path/to/source.json');
$csp->sendCSPHeader();

您也可以从JSON字符串加载配置,如下所示

<?php

use ParagonIE\CSPBuilder\CSPBuilder;

$configuration = file_get_contents('/path/to/source.json');
if (!is_string($configuration)) {
    throw new Error('Could not read configuration file!');
}
$csp = CSPBuilder::fromData($configuration);
$csp->sendCSPHeader();

最后,您只需将一个数组传递给构造函数的第一个参数

<?php

use ParagonIE\CSPBuilder\CSPBuilder;

$configuration = file_get_contents('/path/to/source.json');
if (!is_string($configuration)) {
    throw new Error('Could not read configuration file!');
}
$decoded = json_decode($configuration, true);
if (!is_array($decoded)) {
  throw new Error('Could not parse configuration!');
}
$csp = new CSPBuilder($decoded);
$csp->sendCSPHeader();

示例

{
    "report-only": false,
    "report-to": "PolicyName",
    "report-uri": "/csp_violation_reporting_endpoint",
    "base-uri": [],
    "default-src": [],    
    "child-src": {
        "allow": [
            "https://www.youtube.com",
            "https://www.youtube-nocookie.com"
        ],
        "self": false
    },
    "connect-src": [],
    "font-src": {
        "self": true
    },
    "form-action": {
        "allow": [
            "https://example.com"
        ],
        "self": true
    },
    "frame-ancestors": [],
    "img-src": {
        "blob": true,
        "self": true,
        "data": true
    },
    "media-src": [],
    "object-src": [],
    "plugin-types": [],
    "script-src": {
        "allow": [
            "https://www.google-analytics.com"
        ],
        "self": true,
        "unsafe-inline": false,
        "unsafe-eval": false
    },
    "style-src": {
        "self": true
    },
    "upgrade-insecure-requests": true
}

通过编程方式构建Content Security Policy

<?php

use ParagonIE\CSPBuilder\CSPBuilder;

$csp = CSPBuilder::fromFile('/path/to/source.json');

// Let's add a nonce for inline JS
$nonce = $csp->nonce('script-src');
$body .= "<script nonce={$nonce}>";
    $body .= $desiredJavascriptCode;
$body .= "</script>";

// Let's add a hash to the CSP header for $someScript
$hash = $csp->hash('script-src', $someScript, 'sha256');

// Add a new source domain to the whitelist
$csp->addSource('image', 'https://ytimg.com');

// Set the Report URI
$csp->setReportUri('https://example.com/csp_report.php');

// Let's turn on HTTPS enforcement
$csp->addDirective('upgrade-insecure-requests', true);

$csp->sendCSPHeader();

请注意,许多这些方法可以串联在一起

$csp = CSPBuilder::fromFile('/path/to/source.json');
$csp->addSource('image', 'https://ytimg.com')
    ->addSource('frame', 'https://youtube.com')
    ->addDirective('upgrade-insecure-requests', true)
    ->sendCSPHeader();
  • addSource()
  • addDirective()
  • disableOldBrowserSupport()
  • enableOldBrowserSupport()
  • hash()
  • preHash()
  • setDirective()
  • setBlobAllowed()
  • setDataAllowed()
  • setFileSystemAllowed()
  • setMediaStreamAllowed()
  • setReportUri()
  • setSelfAllowed()
  • setAllowUnsafeEval()
  • setAllowUnsafeInline()

将CSP头部注入到PSR-7消息中

您可以通过调用以下方式,将头部注入到您的PSR-7消息对象中,而不是调用sendCSPHeader()

/**
 * $yourMessageHere is an instance of an object that implements 
 * \Psr\Http\Message\MessageInterface
 *
 * Typically, this will be a Response object that implements 
 * \Psr\Http\Message\ResponseInterface
 *
 * @ref https://github.com/guzzle/psr7/blob/master/src/Response.php
 */
$csp->injectCSPHeader($yourMessageHere);

为配置Apache/nginx保存CSP头部

您可以在每次请求上调用sendCSPHeader(),而不是构建CSP一次并将其保存到片段中,以便在服务器配置中包含

$policy = CSPBuilder::fromFile('/path/to/source.json');
$policy->saveSnippet(
    '/etc/nginx/snippets/my-csp.conf',
    CSPBuilder::FORMAT_NGINX
);

确保之后重新加载您的Web服务器。

通过钩子处理输出,然后再保存到磁盘

$policy = CSPBuilder::fromFile('/path/to/source.json');
$policy->saveSnippet(
    '/etc/nginx/snippets/my-csp.conf',
    CSPBuilder::FORMAT_NGINX
    fn ($output) =>  \str_replace('bar','foo',$output)
);

在保存到文件之前,输出将发生变化

支持合同

如果您的公司在他们的产品或服务中使用此库,您可能对从Paragon Initiative Enterprises购买支持合同感兴趣。