如何在script-src CSP策略头中正确配置哈希解决内联脚本执行错误?
我尝试将哈希与CSP(内容安全策略)配合使用,已在Content-Security-Policy响应头和HTML页面中插入哈希。仅使用SRI(子资源完整性)、禁用CSP时一切正常,但添加script-src的CSP策略后,Chrome浏览器抛出如下错误:
Refused to execute inline script because it violates the following Content Security Policy directive: "script-src 'sha256-cvJx6uIB/hezB9Id6V6UQb10F5C0UObHct9tTMRui5U=' 'sha256-UUbtebSGy54c3N14FM0irnjnDOsw+ga0zZoWzxIbyeY=' 'sha256-8yR2yvIzNS0+QPsGcVGJVn5d06RPcs8TV6Ny3279nf8=' 'sha256-QO3bR06NL/j72WhWlHyvu47i/SrvRDaWHA7U8HP6Two=' 'sha256-k4UFrjnb0AyNfASCTlDeGuBCoCJ4IL/B0rQP2DomUAc=' 'sha256-v3bKmDDl6mxqq2F4tCjHylp8pT2P0NdUP3MPra29T5k=' 'sha256-jkMEwVZP9kW4VP5jLYBwU62KvWrWpZ6fuHK/DNp4ZE8=' 'sha256-o5loTPhKNiVqKQKXvwLE8I9APGislZX/iMhTEezzVQc='". Either the 'unsafe-inline' keyword, a hash ('sha256-cIGnnX7yXorLi3D0wmUGgGkBybL4BvM1zE+hvY7xUOU='), or a nonce ('nonce-...') is required to enable inline execution.
我怀疑问题出在哈希顺序或遗漏配置上,附上HTML文件和CSP头配置:
HTML文件
<!DOCTYPE html><html lang="fr"><head> <meta charset="utf-8"> <link rel="icon" href="/favicon.png" integrity="sha256-UUbtebSGy54c3N14FM0irnjnDOsw+ga0zZoWzxIbyeY=" crossorigin="anonymous"> <meta name="viewport" content="width=device-width, initial-scale=1"> <link rel="modulepreload" href="/build/_app/immutable/entry/start.DR8Pycmd.js" integrity="sha256-aIRMijzrzWGVYJTfjmEtAPaEm24jzcHHQiNkgs3Guas=" crossorigin="anonymous"> <link rel="modulepreload" href="/build/_app/immutable/chunks/entry.DSJM-aT6.js" integrity="sha256-jde0N5ZZaY8e82ieuEEda3tRNs9LjMvb4OtiYW+tuCE=" crossorigin="anonymous"> <link rel="modulepreload" href="/build/_app/immutable/chunks/scheduler.C9xG8wYf.js" integrity="sha256-k4UFrjnb0AyNfASCTlDeGuBCoCJ4IL/B0rQP2DomUAc=" crossorigin="anonymous"> <link rel="modulepreload" href="/build/_app/immutable/chunks/index.U-Bm33l8.js" integrity="sha256-v3bKmDDl6mxqq2F4tCjHylp8pT2P0NdUP3MPra29T5k=" crossorigin="anonymous"> <link rel="modulepreload" href="/build/_app/immutable/entry/app.Cq3Hk0Ou.js" integrity="sha256-ic0wynRWQ14Wc/ZYDneyT3gneELpoerSpJj6lGlOnQc=" crossorigin="anonymous"> <link rel="modulepreload" href="/build/_app/immutable/chunks/index.5DIR6ws4.js" integrity="sha256-o5loTPhKNiVqKQKXvwLE8I9APGislZX/iMhTEezzVQc=" crossorigin="anonymous"> </head> <body data-sveltekit-preload-data="hover" data-theme="skeleton"> <div style="display: contents" class="h-full overflow-hidden"> <script integrity="sha256-ibdP2bv/vvTnwBU46XvO8XtDmRj/aNmtfo80zhnD5yU=" crossorigin="anonymous"> { __sveltekit_1myy8zg = { base: "" }; const element = document.currentScript.parentElement; Promise.all([ import("/build/_app/immutable/entry/start.DR8Pycmd.js"), import("/build/_app/immutable/entry/app.Cq3Hk0Ou.js") ]).then(([kit, app]) => { kit.start(app, element); }); } </script> </div> </body></html>
CSP头配置
Content-Security-Policy: base-uri 'self';connect-src 'self';default-src 'self';form-action 'self';img-src 'self';media-src 'self';object-src 'none';script-src 'sha256-cvJx6uIB/hezB9Id6V6UQb10F5C0UObHct9tTMRui5U=' 'sha256-UUbtebSGy54c3N14FM0irnjnDOsw+ga0zZoWzxIbyeY=' 'sha256-8yR2yvIzNS0+QPsGcVGJVn5d06RPcs8TV6Ny3279nf8=' 'sha256-QO3bR06NL/j72WhWlHyvu47i/SrvRDaWHA7U8HP6Two=' 'sha256-k4UFrjnb0AyNfASCTlDeGuBCoCJ4IL/B0rQP2DomUAc=' 'sha256-v3bKmDDl6mxqq2F4tCjHylp8pT2P0NdUP3MPra29T5k=' 'sha256-jkMEwVZP9kW4VP5jLYBwU62KvWrWpZ6fuHK/DNp4ZE8=' 'sha256-o5loTPhKNiVqKQKXvwLE8I9APGislZX/iMhTEezzVQc=';style-src 'unsafe-inline'
问题根源
错误提示里明确指出,需要添加哈希sha256-cIGnnX7yXorLi3D0wmUGgGkBybL4BvM1zE+hvY7xUOU=到script-src中——这个哈希对应HTML里的内联脚本内容,你当前CSP里的哈希都是预加载资源的SRI哈希,没有包含内联脚本的正确哈希。
另外要注意:HTML中给<script>标签加的integrity属性是SRI(子资源完整性)校验,和CSP的哈希策略完全无关。SRI用来验证外部脚本的完整性,而CSP的哈希是用来允许特定内联脚本执行的,两者不能混用。
修复步骤
添加内联脚本哈希到CSP:
将错误提示里给出的sha256-cIGnnX7yXorLi3D0wmUGgGkBybL4BvM1zE+hvY7xUOU=添加到script-src的哈希列表中,修改后的CSP头如下:Content-Security-Policy: base-uri 'self';connect-src 'self';default-src 'self';form-action 'self';img-src 'self';media-src 'self';object-src 'none';script-src 'sha256-cvJx6uIB/hezB9Id6V6UQb10F5C0UObHct9tTMRui5U=' 'sha256-UUbtebSGy54c3N14FM0irnjnDOsw+ga0zZoWzxIbyeY=' 'sha256-8yR2yvIzNS0+QPsGcVGJVn5d06RPcs8TV6Ny3279nf8=' 'sha256-QO3bR06NL/j72WhWlHyvu47i/SrvRDaWHA7U8HP6Two=' 'sha256-k4UFrjnb0AyNfASCTlDeGuBCoCJ4IL/B0rQP2DomUAc=' 'sha256-v3bKmDDl6mxqq2F4tCjHylp8pT2P0NdUP3MPra29T5k=' 'sha256-jkMEwVZP9kW4VP5jLYBwU62KvWrWpZ6fuHK/DNp4ZE8=' 'sha256-o5loTPhKNiVqKQKXvwLE8I9APGislZX/iMhTEezzVQc=' 'sha256-cIGnnX7yXorLi3D0wmUGgGkBybL4BvM1zE+hvY7xUOU=';style-src 'unsafe-inline'清理无效属性:
内联脚本的integrity属性没有作用,因为SRI只针对外部脚本,所以可以删掉<script>标签里的integrity="sha256-ibdP2bv/vvTnwBU46XvO8XtDmRj/aNmtfo80zhnD5yU=" crossorigin="anonymous"。
额外注意事项
- CSP哈希的顺序不影响生效,只要包含正确的哈希即可。
- 内联脚本内容不能有任何修改,否则哈希会失效,需要重新计算更新CSP。
- 如果后续还有其他内联脚本,都需要计算对应的哈希并添加到
script-src中。
内容的提问来源于stack exchange,提问作者t1m0th33

