35

升级到 Angular 12 后,我的内容安全策略会阻止样式正确加载。

Angular 12 devkit 似乎在 index.html 中的 CSS 包引用中添加了一个新的内联事件处理程序,示例如下。

<link rel="stylesheet" href="styles.5951e4ca367b697db091.css" crossorigin="anonymous" integrity="sha384-2031E8+oC87S0N7NzRGcF8fqx777KEJOgQ3KcUN4aX6xsR3BVaV5sh4fibR5joOc" media="print" onload="this.media='all'">

错误

Refused to execute inline event handler because it violates the following Content Security Policy directive...

这似乎与这个 RFC 相关:https ://github.com/angular/angular-cli/issues/18730但我找不到更多关于如何使用严格的信息(没有'unsafe-inline' ) CSP。

4

2 回答 2

55

Angular 12 升级后我遇到了同样的问题。

我的解决方案是将工作区选项优化“inlineCritical”设置为 false。inlineCritical 选项在 Angular 12 中更改为默认 true 以改进 First Contentful Paint,请参阅https://angular.io/guide/workspace-config#styles-optimization-options

这是一个示例工作区配置

"project": {
  "architect": {
    "build": {
      "configurations": {
        "production": {
          "optimization": {
            "scripts": true,
            "styles": {
              "minify": true,
              "inlineCritical": false
            },
            "fonts": true
          }
        }
      }
    }
  }
},
于 2021-05-18T07:53:45.427 回答
11

注意力!答案已更新

更新答案(2021 年 7 月 16 日)

下面发布的原始解决方案破坏了 Safari (MacOS),因此我们不得不回滚并禁用optimization.styles.inlineCritical.

此外,正如下面masterfloda所评论的那样,在大多数情况下(如果不是所有情况),选择应该是安全而不是性能。我最初的想法是它很难被利用 ( unsafe-hashes),但我还没有对此进行彻底的 InfoSec 风险评分。

在 Angular repo - #20864上有一张票。我建议您暂时禁用optimization.styles.inlineCritical并喜欢并订阅该问题。


原始答案(2021 年 6 月 9 日)

是的,这个问题是由 Angular v12 的样式优化选项( inlineCritical: true) 引入的,它onload向主样式表的链接标记添加了一个事件处理程序,如下所示:

<link rel="stylesheet" href="styles.<hash>.css" media="all" onload="this.media='all'">

inlineCritical无需在 CSP 中禁用或启用即可解决'unsafe-inline',如下:

  • 散列onload处理程序的内容:this.media='all'
  • 报告 URI有一个方便的工具:Script And Style Hasher
  • 将哈希添加到script-srcCSP 中的指令
  • 对于 Chrome(但不适用于 FF),您还需要添加'unsafe-hashes'script-src指令中,否则它会在控制台中使用以下日志阻塞:请注意,哈希不适用于事件处理程序、样式属性和 javascript:导航,除非“不安全-哈希的关键字存在
于 2021-06-09T14:48:05.130 回答