如何使用PHP CSP header()附加/覆盖.htaccess Content-Security-Policy

时间:2017-03-15 06:40:41

标签: php apache .htaccess http-headers content-security-policy

我的.htaccess文件中有一个Content-Security-Policy标头,适用于包含许多页面的整个网站。每个页面上都有内联元素,我不会(也不能)移动到单独的.js文件中,我希望CSP允许它们使用' unsafe-inline'。因此,我想使用动态生成的PHP header()将它们添加到每个页面的顶部,并设置FALSE标志。 FALSE标志(记录为here)将附加到任何现有的传入标头,而不会覆盖它。从理论上讲,这应该可以解决我的问题......但事实并非如此。

由于未知原因,我无法在HTML内容之前使用PHP标头()附加或替换.htaccess文件中的CSP集。下面是演示该问题的代码:(1)页面的.htaccess文件; (2)PHP页面本身。您应该能够轻松地重现这一点。 (我使用Chrome 57进行测试)。

sha256哈希用于下面显示的元素;更改其中的一个字符,哈希将不再对它有效。 (如果您使用某些浏览器扩展程序,Chrome可能会抱怨需要额外的哈希值;只需将它们添加到PHP标头();方便地,Chrome会为您提供CSP的每个内联<script>的正确哈希值

如果在.htaccess文件中删除CSP指令,则执行脚本。为了进一步证明它正在工作,更改哈希中的字符并在控制台打开的情况下重新加载页面;它应该报告一个错误,说CSP对脚本无效,然后报告应该使用哪个哈希来验证它(这将是原始哈希)。

但是如果你在.htaccess文件中取消了CSP指令,那么PHP header()就没有效果,也没有FALSE标志也没有效果。

问题是:当.htaccess文件有CSP标头时, PHP CSP header()无效。

我不想使用nonce,我不想在.htaccess文件中使用unsafe-inlineunsafe-eval ...我不知道#39; t想要将哈希值添加到.htaccess中,因为这是我试图绕过的行为。

我的猜测是.htaccess文件中需要一个额外的指令,允许激活PHP CSP header()。任何既可以命名该指令又可以显示包含额外CSP的方式的人都可以使用PHP标头(),但使用<meta http-equiv="Content-Security-Policy" content="script-src 'self' 'sha256-6eM329mc/AyToTIZuNqhbTD9GNw5jUJeTFszXn+hRU8='">,我更喜欢直接写入HTML而不是使用PHP标头()(但无论哪种解决方案都可以。)

以下是重现此问题的相关代码:

htaccess的:

# The CSP here is pared down for simplicity of illustration
<IfModule mod_headers.c>
    Header set Content-Security-Policy "script-src 'self';"
</IfModule>

PHP代码:

<?php
header("Content-Security-Policy: default-src 'self'; script-src 'self' 'sha256-6eM329mc/AyToTIZuNqhbTD9GNw5jUJeTFszXn+hRU8='", FALSE);
?>
<!DOCTYPE html>
<html>
<head>
    <title>Content-Security-Policy test</title>
</head>
<body>
    <p>"z = 231" should appear in the console</p>
<script>var test=function(){var x = 10.5;var y = 22;var z = x * y;console.log('z = ' + z);}; test();</script>
</body>
</html>

0 个答案:

没有答案