Content Security Policy

Content Security Policy 简称 CSP,可用于应对跨站脚本攻击(XSS 攻击)及数据包嗅探攻击

在不指定 Content Security Policy 的情况下,浏览器会使用默认的同源策略

Content Security Policy 语法

通常是通过 Content-Security-Policy 响应头指定

1
Content-Security-Policy: <policy>

或者通过 <meta> 标签指定

1
<meta http-equiv="Content-Security-Policy" content="<policy>" />

使用 Content-Security-Policy-Report-Only 响应头可以指定仅报告但不阻碍执行的规则,该响应头需要与 report-to 指定同时使用,并且该响应头会继承 Content-Security-Policy 响应头的规则(除 sandbox 之外)

Content Security Policy 指令

Directive name Directive description
default-src 作为其他 fetch 相关指令的来源的后备值
child-src 限制 Worker 脚本资源和内嵌浏览上下文来源
worker-src 限制 Worker 脚本资源来源
frame-src 限制内嵌浏览上下文来源
script-src 限制 JavaScript 脚本和 WebAssembly 来源
script-src-elem 限制 JavaScript 的 <script> 标签来源
script-src-attr 限制 JavaScript 脚本在行内事件回调方法来源
style-src 限制样式表来源
style-src-elem 限制样式表在 <style> 标签和 <link rel="stylesheet"> 来源
style-src-attr 限制样式表在内联样式中来源
manifest-src 限制应用 manifest 文件来源
img-src 限制 image 和 favicon 来源
media-src 限制 <audio> <video> <track> 的媒体资源来源
object-src 限制 <object> <embed> 的资源来源
font-src 限制 @font-face 加载的字体资源来源
connect-src 限制脚本加载的资源来源
base-uri 限制 <base> 标签的内容
sandbox 设置沙箱策略(类似 <iframe> 标签的 sandbox 属性)
form-action 限制表单提交后允许的提交目标
frame-ancestors 限制允许内嵌 <frame> <iframe> <object> <embed> 的浏览上下文
report-to 允许在违反 CSP 事件发生时向指定源发送报告
require-trusted-types-for 强制使用 Trusted Types 应对 XSS 攻击
trusted-types 指定 Trusted Types 的允许指令列表
upgrade-insecure-requests 强制将不安全链接升级为安全链接对待

Content Security Policy 值

Value name Value description
none 不允许任何源的资源
self 允许当前源的资源
strict-dynamic 限制当前资源的规则应同时适用于其加载的资源
report-sample 要求在报告中包含样例代码
inline-speculation-rules 允许使用 speculation rules 脚本规则
unsafe-eval 允许使用 eval 等动态执行代码方法
wasm-unsafe-eval 允许使用加载执行 WebAssembly 模块(避免直接指定 unsafe-eval
unsafe-hashes 允许使用特定的内联事件处理方法
unsafe-inline 允许使用内联资源
nonce-<base64-value> 允许 nonce 属性指定的标识符限制的资源
<hash-algorithm>-<base64-value> 允许指定哈希算法(sha256 sha384 sha512)生成的标识符限制的资源
<host-source> 允许给定的域的资源
<scheme-source> 允许给定协议的资源

Content Security Policy 示例

1
2
3
4
5
Content-Security-Policy: default-src 'self'
Content-Security-Policy: default-src 'self' example.com *.example.com
Content-Security-Policy: default-src 'self'; img-src *; media-src example.org example.net; script-src userscripts.example.com
Content-Security-Policy: default-src https://onlinebanking.example.com
Content-Security-Policy: default-src 'self' *.example.com; img-src *

链接

Permissions Policy

Permissions Policy 允许开发者定义在网页中控制功能的可用性,从而增加应用的安全性和隐私性

Permissions Policy 与 Content Security Policy 类似,但其专注于控制功能特性而非内容

需要注意的是 Permissions Policy 曾经被称为 Feature Policy,但其现在已重命名

指定 Permissions Policy

可以利用 Permissions-Policy 请求头来指定 Permissions Policy,或使用与之等价的 <meta> 标签

可以利用 <iframe> 标签的 allow 属性给内嵌网页指定 Permissions Policy

指定单个 Permissions Policy 时通常包含与之对应的一条指令与允许列表

检测 Permissions Policy

可以通过 Document 接口的 featurePolicy 属性或 HTMLIFrameElement 接口的 featurePolicy 属性暴露的 FeaturePolicy 实例检测 Permissions Policy 的状态

注意:标准已将 FeaturePolicy 接口重命名为 PermissionsPolicy 接口, featurePolicy 属性重命名为 permissionsPolicy 属性

FeaturePolicy 接口的 allowedFeatures() 方法获取当前用户代理在当前浏览上下文允许使用的所有特性

FeaturePolicy 接口的 allowsFeature() 方法检测指定特性在指定的域下是否可用

FeaturePolicy 接口的 features() 方法获取当前用户代理支持的所有特性

FeaturePolicy 接口的 allowedFeatures() 方法列举当前用户代理设置的特性策略中指定特性允许使用的域

Permissions Policy 与 Permissions API 的联系

Permissions Policy 允许开发者设置权限的策略,而 Permissions API 允许用户授予权限

Permissions Policy 指令

Directive name Directive description
accelerometer Accelerometer
ambient-light-sensor AmbientLightSensor
autoplay HTMLMediaElement.play() <audio> & <video> autoplay
battery Battery Status API - Navigator.getBattery()
camera video input devices MediaDevices.getUserMedia()
display-capture MediaDevices.getDisplayMedia()
document-domain set document.domain
encrypted-media Encrypted Media Extensions API - Navigator.requestMediaKeySystemAccess()
execution-while-not-rendered script execution of renderer status
execution-while-out-of-viewport script execution of viewport status
fullscreen Element.requestFullscreen()
gamepad Gamepad API - Navigator.getGamepads() Window:gamepadconnected Window:gamepaddisconnected
geolocation Geolocation API - Geolocation.getCurrentPosition() Geolocation.watchPosition()
gyroscope Gyroscope
hid WebHID API
identity-credentials-get FedCM API
idle-detection Idle Detection API
local-fonts Local Font Access API - Window.queryLocalFonts()
magnetometer Magnetometer
microphone audio input devices MediaDevices.getUserMedia()
midi Web MIDI API - Navigator.requestMIDIAccess()
otp-credentials WebOTP API
payment Payment Request API - PaymentRequest
picture-in-picture Picture In Picture API
publickey-credentials-create Web Authentication API
publickey-credentials-get Web Authentication API
screen-wake-lock Screen Wake Lock API
serial Web Serial API
speaker-selection Audio Output Devices API
storage-access Storage Access API
usb WebUSB API
web-share Web Share API - Navigator.share()
window-management Window Management API
xr-spatial-tracking WebXR Device API

Permissions Policy 允许列表

  • * 允许在顶层浏览上下文及其嵌入浏览上下文中使用
  • () 禁止在顶层浏览上下文及其嵌入浏览上下文中使用,在 <iframe> 标签的 allow 属性的值为 none
  • self 允许在顶层浏览上下文及其同源的嵌入浏览上下文中使用,禁止在嵌入的跨域的嵌入浏览上下文中使用
  • src 仅限在 <iframe> 标签的 allow 属性中使用,允许在当前嵌入浏览上下文中使用
  • <origin> 允许在指定源的浏览上下文中使用
1
2
3
4
5
6
7
8
9
*
()
(self)
(src)
("https://a.example.com")
("https://a.example.com" "https://b.example.com")
(self "https://a.example.com" "https://b.example.com")
(src "https://a.example.com" "https://b.example.com")
("https://*.example.com")

Permissions-Policy 响应头语法

基本语法

1
Permissions-Policy: <directive>=<allowlist>

示例

1
2
3
Permissions-Policy: geolocation=()
Permissions-Policy: geolocation=(self "https://a.example.com" "https://b.example.com")
Permissions-Policy: picture-in-picture=(), geolocation=(self https://example.com), camera=*;

另外值得注意的是,该响应头无法被编程式修改

<iframe> 标签 allow 属性语法

一般建议在 Permissions-Policy 响应头中指定相对宽泛的 Permissions Policy,并在对应内嵌浏览上下文中通过 <iframe> 标签 allow 属性指定更加严格的 Permissions Policy

基本语法

1
<iframe src="<origin>" allow="<directive> <allowlist>"></iframe>

示例

1
2
3
<iframe src="https://example.com" allow="geolocation 'none'"></iframe>
<iframe src="https://example.com" allow="geolocation 'self' https://a.example.com https://b.example.com"></iframe>
<iframe src="https://example.com" allow="geolocation 'self' https://a.example.com https://b.example.com; fullscreen 'none'"></iframe>

链接


:D 一言句子获取中...