版权所有 © 2019 W3C® (MIT, ERCIM, 庆应义塾大学, 北京航空航天大学)。适用 W3C 的免责声明、商标和文档使用规则。
本规范定义了 DNT 请求首部字段,作为一种表达用户跟踪偏好的 HTTP 机制;定义了一个 HTML DOM 属性以供脚本读取该偏好;并定义了允许脚本注册用户所授予例外的 API。它还定义了网站传达其是否以及如何尊重所接收偏好的机制,包括用于检索预检跟踪状态的知名资源、用于表示跟踪状态信息的媒体类型,以及用于确认跟踪状态的 Tk
响应首部字段。
本节描述了本文档在发布时的状态。其他文档可能会取代本文档。当前的 W3C 出版物列表和本技术报告的最新版本可以在 W3C 技术报告索引(https://w3org.cn/TR/)中找到。
本笔记是“跟踪保护工作组”针对各种被称为 DNT、Do Not Track(禁止跟踪)或“跟踪保护表达”的 HTTP 扩展进行标准化流程的最终结果。
自其作为候选推荐标准(Candidate Recommendation)发布以来,这些扩展(按定义)尚未获得足够的部署以证明进一步发展的必要性,在用户代理、第三方及整个生态系统中也没有表现出计划中的支持。因此,工作组决定结束其工作,并将最终产品作为本笔记重新发布,未来任何补充说明将另行发布。
本文档由 跟踪保护工作组 作为工作组笔记发布。
欢迎对本文档提出意见。请将其发送至 GitHub 仓库 或 public-tracking@w3.org (存档)。
作为工作组笔记发布并不意味着得到 W3C 会员的认可。这是一份最终文档,可能随时会被替换。以非“最终笔记”的形式引用本文档是不合适的,未来任何补充说明将另行发布。
本文档由遵循W3C 专利政策运作的团队发布。
本文档受 2018 年 2 月 1 日版 W3C 流程文档管辖。
万维网由数十亿个通过超文本互连的资源组成。超文本提供了一种简单的、以页面为导向的资源信息视图,用户可以通过选择链接、操作控件以及通过表单和搜索对话框提供数据来浏览这些资源。
网页通常由初始资源请求之外的许多信息源组成,包括对样式表、内联图像、JavaScript 和其他可能作为该页面定义的部分被自动请求的元素的嵌入引用。用户的体验是无缝的,即使页面是由与多个服务器的许多网络交互结果组合而成的。从用户的角度来看,他们只是在访问并与单个网站进行交互:用于组合页面以表示该站点的所有技术细节和协议机制都隐藏在幕后。
网站所有者经常出于各种目的收集有关其网站使用情况的数据,包括引导用户访问网站的原因(引荐来源)、用户在网站内的体验效果如何(网络分析),以及谁在使用该网站(受众细分)。在某些情况下,收集的数据用于动态调整内容(个性化)或向用户展示的广告(定向广告)。数据收集通常通过在每个页面上插入嵌入式元素发生,从而产生连接用户跨多个页面活动的数据流。有关这些技术及其隐私影响的调查,请参见 [KnowPrivacy]。
用户需要一种机制来表达他们自己的跟踪偏好,这种机制既易于配置,又在实现时高效。然而,仅仅表达偏好并不意味着所有接收方都会遵守。在某些情况下,服务器可能依赖某些形式的跟踪,并且不愿意或无法将其关闭。在其他情况下,服务器可能仅执行大多数用户都能接受的有限形式的跟踪。因此,服务器需要机制来传达其自身的跟踪行为、请求同意,并在用户做出知情选择后存储用户授予的例外。
本规范扩展了超文本传输协议 (HTTP) 语义 [RFC7231],以传达用户的跟踪偏好(如有)以及源服务器的跟踪行为。DNT 请求首部字段用于传达用户对目标资源的跟踪偏好。定义了一个用于跟踪状态资源的知名 URI 和 Tk 响应首部字段,用于传达服务器的跟踪行为。此外,还定义了 JavaScript API,以便脚本确定 DNT 状态并注册用户授予的例外。
本规范不定义接收方必须做什么才能遵守用户的跟踪偏好,除了传达该合规性的方式之外。相反,跟踪状态提供了识别服务器声明遵守的一组合规制度的能力,假设每个制度都定义了其自身的合规行为要求。例如,[TCS] 是一项正在进行的工作,旨在定义此类合规制度。
下列术语的使用遵循 HTTP/1.1 语法 [RFC7230] 和语义 [RFC7231] 的定义:客户端、服务器、源服务器、用户代理、发送方、接收方、请求、响应、消息、中间方、代理、缓存、URI 主机、权威、首部字段、目标资源、资源 和 表现形式。
下列术语的使用遵循 HTML [HTML51] 的定义:活动文档、document.domain、有效脚本源、责任文档、浏览上下文、嵌套浏览上下文 和 顶级浏览上下文。
跟踪是指收集有关特定用户跨多个不同上下文的活动数据,以及在数据产生的上下文之外保留、使用或共享从该活动中派生的数据。上下文是指由同一方控制或由多方共同控制的一组资源。
网络交互是指单一的 HTTP 请求及其相应的响应:零个或多个中间 (1xx) 响应和单个最终 (2xx-5xx) 响应。
用户操作是指用户通过配置、调用或选择有意发起的网络交互。选择链接、提交表单和重新加载页面是用户操作的示例。用户活动是指任何此类用户操作的集合。
用户是指正在使用或曾经使用网络的自然人。
方是指自然人、法人实体,或共享共同所有者、共同管理者且用户易于发现其群体身份的一组法人实体。共同品牌或通过描述 DNT 做法的资源链接提供的附属机构列表是提供这种可发现性的示例。
就特定用户操作而言,第一方是指用户打算通过一次或多次网络交互与之进行交互的方。仅仅悬停、静音、暂停或关闭特定内容并不构成用户与另一方交互的意图。
在某些情况下,网络上的资源将由两个或多个不同方共同控制。如果用户在访问该资源时有理由期望与所有方进行沟通,则每一方均被视为第一方。例如,资源上显著的联合品牌可能会导致用户预期多个方对内容或功能负责。
对于因用户操作导致的单次或多次网络交互而收集的任何数据,第三方是指除该用户、该用户操作的第一方或代表该用户或该第一方行事的服务提供商之外的任何方。
对网络资源的访问通常涉及多个方,这些方可能会处理在网络交互中接收到的数据。例如,域名服务、网络接入点、内容分发网络、负载均衡服务、安全过滤器、云平台和软件即服务提供商可能是特定网络交互的一方,因为他们由用户或资源所有者签约以提供通信机制。同样,网络交互之后可能涉及其他方,例如使用服务或承包商进行专门的数据分析或记录保留时。
对于在给定网络交互中接收到的数据,如果服务提供商具备以下条件,则被视为与其受托方同一方:
如果在网络交互完成后数据仍处于该方的控制之下,则该方即收集了网络交互中接收到的数据。
如果该方处理数据的目的并非仅仅为了存储或转发给其他方,则该方即使用了数据。
如果该方将数据传输或提供副本给任何其他方,则该方即共享了数据。
当存在高度信任认为数据主体无法被直接或间接(例如,通过与标识符、用户代理或设备关联)识别时,即认为数据已永久去标识化。
本规范中的关键词 must(必须)、must not(不得)、required(必需)、should(应该)、should not(不应该)、recommended(推荐)、may(可以)和 optional(可选)应根据 [RFC2119] 中的描述进行解释。
本规范使用 [RFC5234] 的扩充巴科斯-诺尔范式 (ABNF) 来定义网络协议语法,并使用 WebIDL [WebIDL-20161215] 来定义脚本 API。关于错误处理的一致性标准和考虑因素在 [RFC7230] 的第 2.5 节中定义。
如何抛出 DOMException,以及命名为 "InvalidStateError"、"SecurityError" 和 "SyntaxError" 的 例外,均在 [WebIDL-20161215] 中定义。
Promise 对象 在 [ECMASCRIPT] 中定义;短语 promise-call、resolve promise、reject promise、upon fulfillment 和 upon rejection 按照 [PromiseGuide] 使用。
本协议的目标是允许用户向其通过 HTTP 进行通信的每个服务器和网络应用表达其关于跟踪的个人偏好,从而使偏好的接收方能够相应地调整跟踪行为,或与用户达成满足各方的单独协议。
该表达概念的关键在于,发送的信号 必须 反映用户的偏好,而不是某些供应商、机构、站点或用户控制之外的网络强制机制的选择;这同样适用于一般偏好和例外。基本原则是,跟踪偏好表达仅在反映用户审慎选择时才进行传输。在没有用户选择的情况下,不表达跟踪偏好(参见 第 10.1 节 为什么 DNT:1 默认不预先配置)。
用户代理 必须 为“禁止跟踪”偏好提供至少两种备选选择:unset(未设置)或 DNT:1。用户代理 可以 提供第三种备选选择:DNT:0。
如果用户的选择是 DNT:1 或 DNT:0,则跟踪偏好已启用;否则,跟踪偏好未启用。
用户代理的默认跟踪偏好 必须 为 unset(未启用),除非用户决定使用该代理时暗含了特定的跟踪偏好。例如,通用浏览器以“SuperFred”模式正常调用时不会暗含跟踪偏好,但如果以“SuperDoNotTrack”或“UltraPrivacyFred”模式调用,则可能暗含某种偏好。
不受用户控制的 HTTP 实现 不得 添加、删除或修改跟踪偏好。某些受控网络环境(例如公共访问终端或管理的内部企业网)可能会对已安装用户代理的使用或配置施加限制,使得用户可能只能访问已启用预定偏好的用户代理。然而,如果用户携带自己的联网设备前往提供无线互联网接入的图书馆或咖啡馆,预期的情况是其选择的用户代理和关于网站行为的个人偏好不会被网络环境改变(除了对可通过该网络访问哪些资源进行全面限制之外)。
HTTP 中间方 不得 添加、删除或修改在通过该中间方转发的请求中的跟踪偏好表达,除非该中间方是经由发出请求的用户专门安装或配置的。例如,互联网服务提供商 不得 代表所有未表达偏好的用户注入 DNT:1。
用户代理通常包含用户可安装的扩展(也称为插件或附加组件),它们能够修改配置并发出网络请求。从用户的角度来看,这些扩展被视为用户代理的一部分,并且应当尊重用户对跟踪偏好的配置。用户代理作为一个整体有责任在可能范围内确保符合本协议,这意味着用户代理核心和每个扩展共同负责合规。然而,扩展接口尚无单一标准。允许此类扩展的用户代理 应该 为扩展提供一种适当的机制来确定用户的跟踪偏好。
除非安装和启用该扩展的行为是用户对该跟踪偏好的明确选择,或者扩展本身遵守本协议对用户代理提出的所有要求,否则用户代理扩展 不得 修改跟踪偏好表达或其关联配置。
同样,用户代理之外的软件可能会过滤网络流量或导致用户代理配置被更改。修改用户代理配置的软件 必须 遵守上述对用户代理扩展的要求。过滤网络流量的软件 必须 遵守上述对 HTTP 中间方的要求。
除了上述要求外,我们未指定如何向用户提供跟踪偏好选择,也未指定如何启用偏好:每个实现均有责任确定启用跟踪偏好的用户体验。
例如,用户可以在其用户代理配置中选择一个复选框,安装一个专门设计用于添加跟踪偏好表达的扩展,或者做出一个隐私选择,其中隐含了跟踪偏好(例如,“隐私设置:高”)。用户代理可能会在启动时询问用户的偏好,或许是在首次使用时,或是在更新添加了跟踪保护功能之后。同样,用户可以安装或配置代理,将其自身的 outgoing 请求添加该表达。
当用户启用了跟踪偏好时,该偏好需要向所有可能执行或发起跟踪的机制进行表达。
当启用时,跟踪偏好表达为以下二者之一:
| DNT | 含义 |
|---|---|
| 1 | 该用户在此请求中不希望被跟踪。 |
| 0 | 该用户在此请求中希望允许跟踪。 |
如果跟踪偏好未启用,用户代理 不得 发送跟踪偏好表达。这意味着在以下每种情况下,都不会发送任何表达:
在缺乏监管、法律或其他要求的情况下,服务器 可以 根据其认为最适合给定用户的方式来解释未表达跟踪偏好的情况,特别是在考虑到用户的隐私期望和文化环境时。同样,服务器可能会使用本协议范围之外的其他偏好信息,例如特定于站点的用户偏好或第三方注册服务,以在其未通过本协议表达明确偏好时告知或调整其行为。
DNT 首部字段是在 HTTP 请求中表达用户跟踪偏好的机制 ([RFC7230])。在一个有效请求中最多只能出现一个 DNT 首部字段。
DNT-field-name = "DNT" DNT-field-value = ( "0" / "1" ) *DNT-extension
如果用户的跟踪偏好未启用,用户代理 不得 生成 DNT 首部字段。
如果用户的跟踪偏好已启用,其偏好为 DNT:1,且未针对目标资源授予例外(参见 第 6. 节 用户授予的例外),则用户代理 必须 生成一个字段值以数字字符“1”开头的 DNT 首部字段。
如果用户的跟踪偏好已启用且其偏好为 DNT:0,或者如果已针对目标资源授予例外,则用户代理 必须 生成一个字段值以数字字符“0”开头的 DNT 首部字段。
代理 不得 生成 DNT 首部字段,除非它是经由发出请求的用户专门安装或配置的,并如同用户代理一样遵守上述要求。
GET /something/here HTTP/1.1
Host: example.com
DNT: 1
DNT 字段值在起始字符之后的部分保留用于未来扩展。DNT 扩展仅可在跟踪偏好已启用时传输。扩展语法限制为可见的 ASCII 字符,这些字符可以在 HTTP 中被解析为单个单词,并可在无需进一步编码的情况下安全地嵌入 JSON 字符串中(第 7.5 节 跟踪状态表示)。
DNT-extension = %x21 / %x23-2B / %x2D-5B / %x5D-7E
; excludes CTL, SP, DQUOTE, comma, backslash
例如,额外的字符可能指示对第一个数字所表达的主偏好的修饰,使得如果接收方不理解该扩展,主偏好仍然可以被理解。因此,字段值 "1xyz" 可以理解为“不跟踪,但如果你理解 x、y 或 z 定义的细化,请根据这些细化调整我的偏好”。
未实现 DNT 扩展的用户代理 不得 在 DNT 字段值中发送 DNT 扩展字符。未实现 DNT 扩展的服务器 应该 忽略首字符之后的任何内容。
此 DNT 扩展功能属于推测性功能,因为尚未定义任何已知扩展;未阅读本规范的实现者很可能会认为 DNT 只有 "0" 或 "1" 的固定值。此外,鉴于扩展信息可以使用单独的请求首部字段提供,该机制的潜在好处尚不明确。对 "1" 值的不当扩展可能会导致用户的请求更容易被指纹识别。
Navigator.doNotTrack 属性使具有对 Navigator 对象 [HTML51] 读权限的客户端脚本能够确定在考虑到用户的一般偏好(如有)以及当被活动文档的顶级浏览上下文引用时适用于目标域的用户授予例外的情况下,会向有效脚本源发送什么样的 DNT 首部字段值。
如果不会发送任何 DNT 首部字段(例如,因为跟踪偏好未启用且没有适用的用户授予例外),则该值为 null;否则,该值为以 "0" 或 "1" 开头的字符串,后面可能跟着 DNT 扩展字符。
具体来说,对于给定脚本,Navigator.doNotTrack 的值要么是 null,要么是如果对位于有效脚本源(脚本的责任文档的当前 document.domain)的目标资源的请求(当该请求是由于来自本站点的嵌入引用时)会作为 DNT 字段值(第 5.2 节 HTTP 请求的 DNT 首部字段)发送的字符串值(本站点即顶级浏览上下文的活动文档的 document.domain)。
理想情况下,Navigator.doNotTrack 的值应当反映在读取该属性时生效的当前用户授予例外集。然而在实践中,该值可能仅反映脚本启动时生效的值。
用户的跟踪偏好旨在普遍适用,无论用于互联网通信的协议如何。然而,定义如何通过 HTTP 以外的协议传达用户的跟踪偏好已超出本规范的范围。
内容提供商可能希望在用户启用“禁止跟踪”设置到达时,提示访问者“选择加入”以进行行为广告或类似目的的跟踪。然而,在一个上下文中授予例外(例如,在浏览新闻网站时)并不意味着该例外适用于其他上下文(例如,浏览不相关的医疗网站)。此外,用户可能希望在单一、一致的用户界面中查看或编辑他们授予的所有例外,而不是在每个内容提供商或跟踪者的隐私页面上以不同的方式管理偏好。
用户授予的例外是用户决定授予对来自给定站点的未来请求进行跟踪(DNT:0)同意的记录,作用域为一组目标域。站点和目标的作用域均由域限定,类似于现有的 Cookie 域作用域([HTML51] 的 5.3.1 节),以避免提示用户每一个站点的子域和每一个可能被引用的目标资源。
客户端数据库可用于用户授予例外的持久存储,使得站点能够获得发送 DNT:0 的权限并将其通过 JavaScript API 存储。然而,我们仅定义了 API(如下);存储机制的选择留给每个实现。与使用 Cookie 管理同意相比,例外数据库和 API 提供了更高的透明度和更好的用户控制,同时也为站点提供了更好的例外持久性。
处理用户授予的例外涉及三个域概念:
如果例外仅限于嵌入在给定站点域中或由其引用的请求,则用户授予的例外是特定于站点的;否则,例外是全网有效的,因为它适用于该目标域,而不管引用的站点如何。例如,用户可能希望为了跨多个站点进行受众衡量而授予某个目标域全网有效的例外,或许是为了换取某种激励。
在请求记录特定于站点的例外的同意时,站点可能会就其所引用的已知第三方行为和动作的限制做出一些声明。这样的站点可能希望将其特定于站点的例外仅限制为已验证过这些声明的目标域。(例如,考虑一个同时拥有受信任的广告商和分析提供商,以及一些可能引用其他站点的不可靠的“混搭”内容的站点的困境)。因此,特定于站点的例外可以限制为脚本域、限制为一组命名的目标域,或适用于任何目标域 ("*")。
预期站点会在其在线内容中向用户解释对例外的需求以及授予或拒绝该例外的后果。在收到用户的知情同意后,在站点页面上运行的脚本应使用与用户授予的同意一致的参数来 promise-call Navigator.storeTrackingException API。
站点 必须 确保调用存储例外反映了用户在调用时授予例外的意图。确定记录例外的调用是否反映了用户在调用时的知情同意,是该站点的全部责任。
希望接收用户授予例外的第三方目标域通常无法在页面上调用交互式 JavaScript(例如,仅提供图像或“跟踪像素”的域)。在这种情况下,他们无法请求例外,要么因为需要脚本来进行 API 调用,要么是因为它需要交互以确保用户知情并接收其同意的指示。总的来说,这种通知、获取同意并调用 API 的过程,在调用此类跟踪器的页面元素中是不被预期的。
第一方站点的页面(顶级浏览上下文)可用于获取多方的同意;例如,使用多个包含可以传达关于每方策略的信息并获取每方特定同意的脚本的 iframe 元素。在这种情况下,有效脚本源可能与被授予同意的站点不同。
或者,第三方可能会鼓励用户直接访问其自身站点,以便参与同意对话框并使用 API 来存储全网有效的例外。
即使用户的通用偏好未启用,站点也可以请求存储例外。这允许仅对希望表达偏好的目标资源发送 DNT。如果用户以后选择配置通用跟踪偏好,存储的例外可能会影响传输的偏好。
用户代理可能不会立即存储例外,可能是因为它允许用户进行确认。尽管站点在调用存储 API 之前已经获得了用户的知情同意,但用户仍可能改变主意,允许存储例外但随后又将其移除,或者通过事先配置拒绝存储。尽管如此,在调用时,站点已经获得了用户的同意,无论用户代理是否已存储例外,站点都可以据此继续进行。
站点可以 promise-call Navigator.trackingExceptionExists API 来查询用户代理中是否已授予并存在一组例外。如果 promise 解析为 false(表明例外集已过期、已删除或尚未存储),则可以再次询问用户以获取同意。
用户代理应在请求时查询例外数据库,以确定发送什么样的值(如有)作为用户的跟踪偏好。
二元组对 [A,B] 和 [X,Y] 匹配,如果 A 匹配 X 且 B 匹配 Y。一对值 A 和 X 匹配,当且仅当满足以下条件之一:
例如,用户可能授予 metrics.example.net 一个例外,以跟踪其在 news.example.com 和 weather.example.com 上的活动,但不在 medical.example.org 上跟踪。如果位于 http://news.example.com/news/story/2098373.html 的文档具有对 http://metrics.example.net/1x1.gif 和 http://weather.example.com/widget.js 的嵌入引用,则这些引用的站点域为 news.example.com,目标域分别为 metrics.example.net 和 weather.example.com。
用户代理 可以 选择在目标资源没有具有有效跟踪状态表示的对应跟踪状态资源时忽略用户授予的例外,因为这意味着该目标资源不符合本规范。
存储例外的站点也应能够撤销这些例外。脚本可以通过 promise-call Navigator.removeTrackingException API 来移除适用于该站点的所有例外。
站点 可以 监控其用户授予的例外的变更。如果用户通过删除例外撤销了同意,则该站点 必须 尊重该撤销,尽管它 可以 再次请求新的例外。换句话说,站点 不得 在未先与用户交互并获得新同意的情况下恢复已删除的例外。
当站点已获得用户授予的例外的同意后,在该站点活动的浏览上下文或嵌套浏览上下文内运行的脚本可以 promise-call Navigator.storeTrackingException 来存储一个或多个跟踪例外。一个 TrackingExData 对象作为参数提供,以定义例外的作用域(涵盖所授予例外的 [站点, 目标] 二元组集)以及为该例外存储的可选信息。该调用返回一个 promise,其要么解析为 TrackingExResult,要么因标识失败原因的 DOMException 而被拒绝。
dictionaryTrackingExData{ DOMString?site; sequence<DOMString>?targets; DOMString?name; DOMString?explanation; DOMString?details; long?maxAge; }; dictionaryTrackingExResult{ booleanisSiteWide; };
Navigator.storeTrackingException 传递一个 TrackingExData 对象。用户代理 必须 忽略 TrackingExData 对象的未知属性(以便未来扩展)。定义了以下 可选 属性:
站点targetsnamename 是一个用户可读的命名例外的字符串,通常描述目标或其用于此站点的预期目的,编码为 UTF-8,并适用于用于告知例外同意的自然语言。解释explanation 是一个用户可读的关于所授予例外的简短说明,编码为 UTF-8,并使用与告知例外同意相同的自然语言。detailsdetails 是一个 URI 引用,在该处可以找到关于所授予例外的更多信息 [RFC3986]。maxAgemaxAge 是一个正数,以秒为单位指示授予的最长有效期。maxAge 且不为 null、空或负数,则用户代理 必须 在存储后不超过指定秒数的时间内移除存储的例外。maxAge,则用户代理 可以 无限期保留存储的授予。属性 name、explanation 和 details 由调用者提供,目的是供潜在的用户界面使用。如果用户代理向用户展示这些属性,则应清楚它们仅提供信息价值,其重要性低于例外的技术效应。
除了上述数据外,用户代理还可以存储关于该调用的环境信息,例如与顶级浏览上下文关联的 URI、有效脚本源、当前时间戳,或其他可能从适用的跟踪状态资源中获取的信息。
调用脚本域 必须 拥有一个具有有效跟踪状态表示的全站跟踪状态资源,该资源包含一个 policy 属性。这允许用户代理在授予例外时获取并可能存储关于调用者的控制者和跟踪策略的额外信息。
如果无法确定有效脚本源,或者与该源对应的站点没有具有有效跟踪状态表示的全站跟踪状态资源,则用户代理 可以 以命名为 "InvalidStateError" 的 DOMException 拒绝该 promise。
对于每个正在存储的特定于站点的例外,如果脚本无法按照 Cookie 域规则 [RFC6265] 在该二元组的引荐域作用域上设置 Cookie,则用户代理 不得 存储该二元组,并 必须 以命名为 "SecurityError" 的 DOMException 拒绝该 promise。
例如,www.foo.bar.example.com 上的脚本可以将 site 设置为 "bar.example.com" 或 "example.com",但不能设置为 "something.else.example.com" 或 "com"。
对于每个正在存储的全网有效例外,如果脚本无法按照 Cookie 域规则 [RFC6265] 在该目标域上设置 Cookie,则用户代理 不得 存储该二元组,并 必须 以命名为 "SecurityError" 的 DOMException 拒绝该 promise。这限制了全网有效例外的存储,仅限于与例外目标共享相同域作用域的脚本,但允许此类脚本嵌入在通用同意门户的 iframe 内。
对于任何其他失败,例如 TrackingExData 中的格式不正确的参数,用户代理 不得 在数据库中存储任何目标二元组,并 必须 以命名为 "SyntaxError" 的 DOMException 拒绝该 promise。
履行后,用户代理已在其本地数据库中添加了一个或多个 [站点, 目标] 站点对二元组,每个都指示来自该站点域到目标域的请求将包含 DNT:0,而不管用户的一般跟踪偏好如何。履行的 promise 对象包含以下 TrackingExResult 属性:
isSiteWidetrue;否则为 false。当为特定于站点的例外提供 targets 列表时,如果用户代理通过将返回的 promise 的 isSiteWide 属性设置为 true 来指示该结果,则其 可以 忽略该列表,转而存储针对所有域的特定于站点的例外 ([site, *])。
即使当 Navigator.doNotTrack 为 null 时,用户代理 可以 实例化 Navigator.storeTrackingException。脚本 应该 在调用该方法之前测试 Navigator.storeTrackingException 是否存在。
这里存在一些安全顾虑,涉及到一个与某一站点有效脚本源匹配的脚本,是否有能力持久化其他(目标)站点上资源接收到的 DNT 值。特别是,此功能可能被滥用来设置/取消设置一组异常(类似于一组位值),并通过向这些域(可能都指向同一个互联网主机)嵌入请求来将其“读取”为持久标识符。然而,我们预计这会在用户代理上留下明显的痕迹,这与其他指纹识别来源不同。
同样,允许在另一个站点的页面 iframe 中存储异常可能会导致滥用,除非调用脚本确保它是在一个它期望收集用户同意的页面内运行,并且该同意的上下文与所存储的异常是一致的。
此设计符合以下事实:即站点在未事先获得用户知情同意的情况下调用 API 没有技术上的限制。我们假设社会和监管环境足以惩罚那些可能滥用 API 或滥用存储异常范围的行为者。当 API 要求时,用户代理可以通过检查全站跟踪状态资源来进一步降低此类风险。
当站点决定(或已收到用户指令)撤销用户授予的异常时,在该站点的活动浏览上下文或嵌套浏览上下文内运行的脚本可以Promise 调用 Navigator.removeTrackingException 来删除一个或多个跟踪异常。提供一个 TrackingExData 对象作为参数来标识要删除哪些异常。该调用返回一个 Promise,它要么解析以表示成功,要么被拒绝,并附带一个标识失败原因的 DOMException。
Navigator.removeTrackingException 传递一个 TrackingExData 对象。用户代理 必须 忽略 TrackingExData 对象的未知属性(为了未来的可扩展性)。定义了以下 可选 属性
站点targets对于每个正在被删除的特定站点异常,如果脚本无法按照 Cookie 域规则 [RFC6265] 在该二元组的引用域范围内设置 Cookie,则用户代理 不得 删除这些二元组,并 必须 使用名为 "SecurityError" 的 DOMException 拒绝该 Promise。
对于每个正在被删除的全网异常,如果脚本无法按照 Cookie 域规则 [RFC6265] 在该目标域上设置 Cookie,则用户代理 不得 删除这些二元组,并 必须 使用名为 "SecurityError" 的 DOMException 拒绝该 Promise。
任何处理失败(例如 TrackingExData 中参数格式不正确)将导致没有任何二元组从存储的授权数据库中被删除,并使返回的 Promise 被名为 "SyntaxError" 的 DOMException 拒绝。
如果在调用该方法时,存储的授权数据库中没有匹配的二元组,则此操作除了解析 Promise 外不执行任何其他操作。
履行时,用户代理 必须 已删除所有匹配所标识二元组的存储异常。
当站点希望确认该站点可能引用的目标域集合是否存在用户授予的异常时,在该站点的活动浏览上下文或嵌套浏览上下文内运行的脚本可以Promise 调用 Navigator.trackingExceptionExists,并提供一个 TrackingExData 对象作为参数来标识要确认的异常集合。该调用返回一个 Promise,它要么解析为 true 或 false,要么被拒绝并附带一个标识失败原因的 DOMException。
Navigator.trackingExceptionExists 传递一个 TrackingExData 对象。用户代理 必须 忽略 TrackingExData 对象的未知属性(为了未来的可扩展性)。定义了以下 可选 属性
站点targets对于每个正在被确认的特定站点异常,如果脚本无法按照 Cookie 域规则 [RFC6265] 在该二元组的引用域范围内设置 Cookie,则用户代理 必须 使用名为 "SecurityError" 的 DOMException 拒绝该 Promise。
对于每个正在被确认的全网异常,如果脚本无法按照 Cookie 域规则 [RFC6265] 在该目标域上设置 Cookie,则用户代理 必须 使用名为 "SecurityError" 的 DOMException 拒绝该 Promise。
任何处理失败(例如 TrackingExData 中参数格式不正确)将导致返回的 Promise 被名为 "SyntaxError" 的 DOMException 拒绝。
如果上述所有标识的二元组都存在当前(未过期)的匹配异常,则用户代理 必须 以值 true 履行 Promise;如果任何标识的二元组没有匹配的异常,则履行值为 false。
由于数据库可能随时发生更改(通过其他窗口或额外的用户界面),API 的特定响应可能仅在 Promise 被履行时准确。
对于用户代理授予异常的行为,没有强制要求的用户界面;用户代理 可以 选择不提供任何界面。或者,用户代理 可以
当通过 API 提供明确的目标域列表时,它们的名字对用户来说可能意义不大。例如,用户可能会被告知在某某站点上有一组特定的目标存储了异常,而不是按名称列出它们;或者用户代理可能会决定存储一个全目标异常,实际上忽略任何目标列表。
相反,如果为目标使用了通配符,则用户可能会被告知,对于该站点嵌入的所有第三方,都有一个存储的异常。
选择在跟踪异常适用时进行高亮显示的用户代理可能会提供一个界面,例如状态栏中可选的图标,该图标可以将用户引导至有关该异常以及如何撤销它的更多信息。
在某些用户代理实现中,授予异常的决定可能是过去做出的(且此后已被遗忘),或者是该设备的其他用户做出的。因此,异常并不总是代表用户的当前偏好。一些用户代理可能会选择提供环境通知,说明用户选择的跟踪正在进行,或提供查看和控制这些偏好的简便方法。用户也可能希望在单独的用户界面内编辑异常,这将允许用户在不访问目标站点的情况下修改其存储的异常。
用户代理 必须 将由单个 storeTrackingException 调用存储的每组异常二元组作为一个“单元”处理,完整地授予并维护这些二元组,否则就完全不处理。用户代理 不得 向站点指示它已在数据库中为目标 {a, b, c} 存储了异常,随后又仅从其逻辑存储授权数据库中删除了 {a, b, c} 中的一两个。这保证了站点所需的运营完整性的目标域集合被视为一个整体。
除了表达用户关于跟踪的偏好外,该协议还使服务器能够传达关于其自身跟踪行为的机器可读声明。由于每次响应都包含个性化跟踪状态会禁用缓存,因此定义了一系列响应机制,允许在发出可跟踪请求之前以及在不必使每个响应都动态化的情况下传达跟踪状态。
一个 跟踪状态值 (TSV) 是对用户关于通过指定资源收集的数据的跟踪偏好的单字符响应。对于全站跟踪状态资源,指定资源是同一源服务器上的任何资源。对于 Tk 响应头字段,对应请求的 目标资源 是该指定资源,对于 Tk 字段值引用的任何后续特定于请求的跟踪状态资源,该资源保持不变。
跟踪状态值区分大小写,由以下 ABNF 正式定义。
TSV = %x21 ; "!" — under construction
/ %x3F ; "?" — dynamic
/ %x47 ; "G" — gateway to multiple parties
/ %x4E ; "N" — not tracking
/ %x54 ; "T" — tracking
/ %x43 ; "C" — tracking with consent
/ %x50 ; "P" — tracking only if consented
/ %x44 ; "D" — disregarding DNT
/ %x55 ; "U" — updated
/ TSV-extension
跟踪状态值 ! 意味着源服务器当前正在测试其跟踪状态的传达。提供 ! 值是为了在合规性测试的初始阶段,以及由于未来的协议更改或监管约束变化导致的调整期间,简化生产系统上的测试和部署。请注意,此值并不表明用户的偏好将被忽略,也不表明访问指定资源会导致跟踪。
跟踪状态值 ? 意味着源服务器需要更多信息来确定跟踪状态,通常是因为 指定资源 根据请求中的信息动态调整行为。
如果全站跟踪状态中存在 ?,则源服务器 必须 在所有针对指定资源的请求响应中发送 Tk 头字段。如果 Tk 头字段中存在 ?,则更多信息将由 status-id 引用的特定于请求的跟踪状态资源提供。源服务器 不得 在特定于请求的跟踪状态资源的表示中发送 ? 作为跟踪状态值。
跟踪状态值 G 意味着服务器充当涉及多方的交换网关。如果对指定资源的响应涉及自动选择过程(例如动态竞价),且被选中的方决定如何根据所表达的跟踪偏好处理请求数据时,可能会发生这种情况。与 ? 值类似,G TSV 表明实际的跟踪状态是动态的,并将通过响应消息的 Tk 头字段提供,大概是使用从选中方转发的信息。
此跟踪状态值仅作为全站状态有效。服务器 不得 在 Tk 头字段或特定于请求的跟踪状态资源的表示中发送 G 作为跟踪状态值。
如果全站跟踪状态中存在 G
DNT:1 的请求的跟踪数据;并且,Tk 头字段,并在该字段的值中包含一个特定于选中方的 status-id,以便可以通过特定于请求的跟踪状态资源获取有关该选中方的信息(参见 第 7.4.2 节 特定于请求的跟踪状态)。关于网关自身执行的跟踪,G 响应可被视为等同于下文定义的 T(跟踪)响应。全站跟踪状态表示中的其他信息表明了网关打算如何遵守所表达的跟踪偏好,除了网关流程所暗示的潜在数据共享之外。
跟踪状态值 N 意味着源服务器声称通过指定资源收集的数据不用于跟踪,也不会以任何能够实现跟踪的形式与其他数据合并。
跟踪状态值 T 意味着源服务器可能会使用通过指定资源收集的数据执行或启用跟踪。跟踪状态表示中提供的信息可能会表明此类跟踪是否仅限于一组通常被接受的用途,或者是否遵守一个或多个合规性制度。
跟踪状态值 C 意味着源服务器认为它已事先获得跟踪此用户、用户代理或设备的同意(也许是通过本规范未定义的某种机制),并且该先前的同意会覆盖此协议所表达的跟踪偏好。发送 C 跟踪状态值的源服务器对于指定资源 必须 在其相应跟踪状态表示的 config 属性内提供控制同意的参考(第 7.5 节 跟踪状态表示)。
跟踪状态值 P 意味着源服务器在实时情况下不知道它是否已事先获得跟踪此用户、用户代理或设备的同意,但承诺在确定此类同意之前不使用或共享任何 DNT:1 数据,并进一步承诺在四十八小时内删除或永久去标识化任何未获得此类同意的 DNT:1 数据。
由于此状态值本身并不表明特定请求是否被跟踪,发送 P 跟踪状态值的源服务器 必须 在相应的跟踪状态表示中提供一个 config 属性,该属性链接到一个用于获取同意状态的资源。
P 跟踪状态值专门用于解决受众调查系统,对于这些系统,在请求时确定同意要么是不切实际的(由于遗留系统无法跟上网络流量),要么如果第一方站点能够确定哪些用户已同意,则可能会被“操纵”。数据不能用于个性化目的。如果可以在请求时确定同意,则首选 C 跟踪状态。
跟踪状态值 D 意味着源服务器不能或不愿尊重从请求用户代理接收到的跟踪偏好。发送 D 跟踪状态值的源服务器 必须 在服务器相应的隐私政策中详细说明在哪些条件下可能会不理会跟踪偏好。
例如,源服务器可能会不理会从被认为不符合要求的特定用户代理(或通过特定网络中介)接收到的 DNT 字段,或者由于先前的安全事件可能正在从特定源网络位置收集额外数据,或者可能被迫不理会某些 DNT 请求以遵守当地法律、法规或命令。
本规范的撰写基于这样一种假设:D 跟踪状态值仅在可以充分向用户描述为正常行为的例外情况的情况下使用。如果事实证明并非如此,则要么是服务器发送 D 信号的决定需要重新审视,要么是本规范需要重新审视,或者两者都需要。
跟踪状态值 U 意味着该请求导致适用于此用户、用户代理或设备的跟踪状态发生了潜在变化。依赖于缓存跟踪状态的用户代理 应该 通过在适用的跟踪状态资源上发出新请求来使用当前状态更新缓存条目。
源服务器 不得 在除响应状态更改请求的 Tk 头字段以外的任何地方发送 U 作为跟踪状态值。
对 TSV 集合的可扩展性确保了随着区域法律和监管环境随时间演变,以及合规性规范得到相应开发,该协议将继续可用。
如果该扩展已由本规范的未来版本或 compliance 属性中标识的合规性制度定义,则源服务器 可以 发送一个 TSV-extension 字符作为 TSV。除了存储或呈现服务器的响应之外,接收方 必须 将其无法识别的 TSV-extension 值视为 P(仅在同意的情况下跟踪)。
TSV-extension = %x23-25 ; #$%
/ %x2A-3B ; *+,-./0-9:;
/ %x40-42 ; @AB
/ %x45-46 ; EF
/ %x48-4D ; HIJKLM
/ %x4F ; O
/ %x51-53 ; QRS
/ %x56-5A ; VWXYZ
/ %x5F ; _
/ %x61-7A ; a-z
Tk 响应头字段是用于指示适用于相应请求的跟踪状态的一种方式。如果其全站跟踪状态值为 ?(动态)或 G(网关),或者当跟踪状态发生交互式更改并由 U(更新)指示时,源服务器 必须 发送一个 Tk 头字段。
Tk-field-name = "Tk" Tk-field-value = TSV [ ";" status-id ]
Tk 字段值以跟踪状态值(第 7.2 节 跟踪状态值)开头,后跟一个可选的分号和一个引用特定于请求的跟踪状态资源的 status-id(第 7.3.2 节 引用特定于请求的跟踪状态资源)。
例如,对于声称不进行跟踪的资源的 Tk 头字段如下所示
Tk: N
如果源服务器有多个针对请求的特定跟踪政策,使得跟踪状态可能会根据请求的某些方面(例如方法、目标资源、头字段、数据等)而有所不同,则源服务器可以提供一个额外的已知资源子树,对应于每个这些不同的跟踪状态。Tk 字段值的 status-id 部分指示哪个具体的跟踪状态资源适用于当前请求。status-id 区分大小写。
status-id = 1*id-char id-char = ALPHA / DIGIT / "_" / "-" / "+" / "=" / "/"
例如,包含以下内容的响应
Tk: T;fRx42
表示通过目标资源收集的数据可能用于跟踪,并且可以通过对以下地址执行检索请求来获得适用的跟踪状态表示
/.well-known/dnt/fRx42
请注意,status-id 是相对于当前请求的源服务器进行解析的。如果需要,针对该 URI 的检索请求可以重定向到其他服务器。status-id 被有意限制为一小组字符,以鼓励使用短令牌而不是可能很长的、人类可读的字符串。
如果 Tk 字段值的跟踪状态值为 ?(动态),则源服务器 必须 在字段值中发送一个 status-id。
除了本规范范围之外,还可以使用交互式机制,这些机制具有请求和获得事先跟踪同意或修改事先同意指示的效果。例如,跟踪状态资源的 status 对象定义了一个 config 属性,该属性可以引用此类机制。虽然本规范未定义此类带外机制,但它们的存在可能会影响跟踪状态对象的响应值。
当源服务器通过 HTTP 提供建立或修改带外跟踪偏好的机制时,如果状态更改请求导致该服务器的跟踪状态发生变化,源服务器 必须 在机制的响应中加以指示。这种交互式状态更改的指示通过在响应中发送一个 Tk 头字段并带有 U(更新)的跟踪状态值来实现。
Tk: U
一个 全站跟踪状态资源 提供有关位于该源服务器的资源的潜在跟踪行为的信息。全站跟踪状态资源具有众所周知的标识符
/.well-known/dnt/
相对于源服务器的 URI [RFC5785]。
接收到针对其全站跟踪状态资源的有效 GET 请求的源服务器 必须 发送一个包含下文定义的机器可读全站跟踪状态表示的成功响应,或一系列导致此类表示的重定向。无法提供对此类表示的访问权限意味着源服务器未实现此协议。该表示可以被缓存,如 第 7.4.4 节 缓存 中所述。
有关跟踪状态资源如何用于发现对本协议的支持的示例,请参见 第 8. 节 用例。
如果源服务器有多个针对请求的特定跟踪政策,使得跟踪状态可能会根据请求的某些方面(例如方法、目标资源、头字段、数据等)而有所不同,则源服务器可以提供一个额外的已知资源子树,对应于每个这些不同的跟踪状态。Tk 响应头字段(第 7.3 节 HTTP 响应的 Tk 头字段)可以包含一个 status-id 来指示哪个具体的跟踪状态资源适用于当前请求。
一个 跟踪状态资源空间 由以下 URI 模板定义 [RFC6570]
/.well-known/dnt/{+status-id}
其中 status-id 的值是由响应先前请求的 Tk 字段值提供的 URI 安全字符字符串。例如,先前包含以下内容的响应
Tk: ?;ahoy
引用了特定的跟踪状态资源
/.well-known/dnt/ahoy
特定于请求的跟踪状态资源空间内的资源使用与全站跟踪状态资源相同的格式表示。
在发送跟踪状态请求时,用户代理 应该 包含任何会在正常请求中发送到该源服务器的 Cookie 数据 [RFC6265](在请求之前设置),因为服务器可能需要这些数据来确定当前的跟踪状态。例如,Cookie 数据可能表明用户之前曾做出过拒绝或同意该源服务器跟踪的带外决定。
源服务器 不得 保留有关全站跟踪状态资源或跟踪状态资源空间内请求的跟踪数据,无论请求中是否存在、缺失或 DNT 头字段、Cookie 或任何其他信息的值如何。此外,源服务器 不得 在这些请求的响应中发送 Set-Cookie 或 Set-Cookie2 头字段,包括重定向跟踪状态请求的响应,并且 不得 发送具有发起跟踪内容(超出请求中已存在的内容)的响应。用户代理 应该 忽略或将此类响应中接收到的任何 Set-Cookie 或 Set-Cookie2 头字段视为错误。
如果跟踪状态适用于所有用户,无论接收到的 DNT 字段值和通过请求接收到的其他数据如何,则源服务器 应该 将响应标记为可缓存 [RFC7234],并分配一个足以启用共享缓存的生存时间(过期或最大使用次数),但该生存时间不得超过该服务跟踪行为可能增加的最早时间点。
例如,如果跟踪状态响应设置为七天后过期,则服务跟踪行为增加的最早时间点是跟踪状态表示被更新以反映新行为后的七天,因为旧副本可能会在缓存中持续存在,直到过期被触发。服务的跟踪行为可以随时减少,无论是否对应于跟踪状态资源的更改。
如果跟踪状态仅适用于具有相同 DNT 字段值的用户,则源服务器 必须 发送一个 Vary 头字段,其字段值包含“DNT”,或者包含以下指令之一的 Cache-Control 头字段:“private”、“no-cache”、“no-store” 或 “max-age=0”。
如果跟踪状态仅适用于请求它的特定用户,则源服务器 必须 发送一个 Cache-Control 头字段,包含以下指令之一:“private”、“no-cache” 或 “no-store”。
无论缓存控制设置如何,预计用户代理每个会话仅会检查一次(最多)服务的跟踪状态。打算更改其跟踪状态以增加跟踪行为的公共互联网站点 必须 在该服务上激活新行为之前至少 24 小时,按照该计划的行为更新跟踪状态资源。
根据跟踪状态的有效验证调整行为并依赖缓存的跟踪状态响应的用户代理 应该 检查其状态更改请求(例如 POST、PUT、DELETE 等)的响应,查看是否存在带有 U 跟踪状态值的 Tk 头字段,如 第 7.3.3 节 指示交互式状态更改 中所述。
对于每个跟踪状态资源,源服务器 必须 使用 application/tracking-status+json 媒体类型提供有效的表示。此媒体类型包含序列化为 JSON [RFC8259] 的 状态对象。有关 application/tracking-status+json 媒体类型的更多信息,请参见 第 B. 节 注册。
跟踪状态表示由一个包含描述适用于 指定资源 的跟踪状态的属性的单一 状态对象 组成。大多数属性是可选的,并且可以 随时间扩展,如下面的 Orderly 模式所示 [Orderly]
object {
string tracking; // TSV
array { string; } compliance?; // hrefs
string qualifiers?; // compliance flags
array { string; } controller?; // hrefs
array { string; } same-party?; // domains
array { string; } audit?; // hrefs
string policy?; // href
string config?; // href
}*;
以下表示示例演示了一个具有本规范定义的所有属性的状态对象。
{
"tracking": "T",
"compliance": ["https://acme.example.org/tracking101"],
"qualifiers": "afc",
"controller": ["https://www.example.com/privacy"],
"same-party": [
"example.com",
"example_vids.net",
"example_stats.com"
],
"audit": [
"http://auditor.example.org/727073"
],
"policy": "/privacy.html#tracking",
"config": "http://example.com/your/data"
}
状态对象 必须 具有一个名为 tracking 的属性,其字符串值包含适用于 指定资源 的跟踪状态值(第 7.2 节 跟踪状态值)。
例如,以下演示了一个适用于任何不执行跟踪的资源的最小跟踪状态表示。
{"tracking": "N"}
源服务器 可以 发送一个名为 compliance 的属性,其值为包含 URI 引用的数组,这些引用标识源服务器声称针对指定资源遵守的特定制度。传达此类合规声明被认为可以提高透明度,这可能会影响用户关于允许跟踪的决策或配置。
如果源服务器发送了一个 TSV-extension 或本规范的后续版本未定义的 状态对象中的扩展属性,则源服务器 必须 发送一个 compliance 属性,其中包含对该扩展的权威规范的引用。如果 compliance 数组中的多个引用定义了相同的扩展值,则源服务器 应该 按预期的优先顺序在数组中列出引用。
源服务器 可以 发送一个名为 qualifiers 的属性,其字符串值包含与跟踪程度的解释或限制相对应的一系列区分大小写的字符。多个限定符表明指定资源可能适用多个解释或跟踪形式。每个限定符的含义被认为由 compliance 中列出的一个或多个制度定义。
源服务器 可以 发送一个名为 controller 的属性,其值为包含 URI 引用的数组,这些引用间接标识声称为通过指定资源收集的个人数据负责的数据控制者的一方或多方。如果负责数据控制者不拥有指定资源的域名,源服务器 必须 发送一个 controller 属性。
未发送 controller 的源服务器暗示其域名所有者是唯一的数据控制者;有关数据控制者的信息应在指定资源的站点根页面上,或通过从该页面清晰指示的链接找到(即,缺席的 controller 属性等同于:"controller":["/"])。
如果 指定资源 拥有联合数据控制者(即多方对收集的数据拥有独立控制权),源服务器 必须 发送一个 controller 属性,其中包含每个数据控制者的参考。
controller 中提供的每个 URI 引用都应指向一个资源,如果对该 URI 执行检索操作,该资源将向用户提供(至少)相应方的身份及其数据收集做法的信息。
由于用户在给定站点上的体验可能由从多个域组装而成的资源组成,因此站点区分那些受其自身控制的域(即与引用站点共享相同数据控制者)可能很有用。源服务器 可以 发送一个名为 same-party 的属性,其值为包含源服务器声称为同一方的域名列表的数组,只要它们被指定资源引用,并且通过这些引用收集的所有数据都与指定资源共享相同的数据控制者。
用户代理可以使用提供的 same-party 数组,来通知或为声称为同一方的引用与未做此类声明的引用启用不同的行为。例如,用户代理可能会选择排除对未被引用站点声称为同一方的其他域的请求,或者对这些请求执行额外的预检验证。
源服务器 可以 发送一个名为 audit 的属性,其值为包含指向指定资源隐私政策和跟踪行为的外部审计的 URI 引用的数组。最好是审计参考指向描述审计员和审计结果的资源;但是,如果此类资源不可用,则提供审计员的参考就足够了。
源服务器 可以 发送一个名为 policy 的属性,其字符串值包含指向描述指定资源相关隐私政策的人类可读文档的 URI 引用。该文档可以通知用户当访问指定资源时可能收集的数据,以及此类数据的收集、使用或共享如何根据收到的表达跟踪偏好(DNT:1 或 DNT:0)而有所不同。
如果服务器是调用 JavaScript API 以存储 用户授予的异常 的脚本的 有效脚本源,则该服务器 必须 发送一个 policy 属性,如 第 6.3 节 授予异常 中所述。
此类政策文档的内容超出了本协议的范围,仅是对机器可读跟踪状态表示中内容的补充。如果没有提供 policy 属性,此信息可能通过 controller 中提供的链接获得。
如果与指定资源关联的政策碰巧被定义为适用于多个站点的通用标准,或通过引用包含了此类标准,则该标准应通过机器可读 compliance 属性内的 URI 进行引用。
源服务器 可以 发送一个名为 config 的属性,其字符串值包含指向资源 URI 的引用,该资源用于让用户控制通过指定资源(以及可能的其他资源)收集的个人数据。如果跟踪状态值表示事先同意 (C),则源服务器 必须 发送一个引用描述如何建立此类同意以及如何撤销该同意的资源的 config 属性。
配置资源可能包括查看过去收集的数据、删除部分或全部数据、提供额外数据(如果需要),或者“选择加入”、“选择退出”或以其他方式修改有关数据收集的带外同意状态的能力。此类资源的设计、它提供对数据的访问程度以及如何实现带外同意机制超出了本协议的范围。
如果没有提供 config 属性,此信息可能通过 controller 或 policy 中提供的链接获得。
状态对象的可扩展性确保了随着区域法律和监管环境随时间演变,以及合规性规范得到相应开发,该协议将继续可用。
如果这些扩展已由本规范的未来版本或 compliance 属性中标识的合规性制度定义,则源服务器 可以 在 状态对象 中发送其他属性。除了存储或呈现服务器的响应之外,接收方 必须 忽略其无法识别的扩展属性。
如果源服务器收到带有 DNT:1 的请求,并且没有针对跟踪该用户的带外同意,并且希望拒绝访问所请求的资源,直到用户提供某种形式的用户授予的异常或跟踪同意,则源服务器 应该 发送 409 (Conflict) 响应,并附带描述为何拒绝请求以及如何提供所需的同意或异常以避免此冲突的消息负载 [RFC7231]。
如果用户登录是授予访问权限的方式之一,则 409 响应应在头字段和/或消息体中包含用户身份验证机制。
本节是非规范性的。
本节用于收集描述用户代理可能关于跟踪状态提出的问题以及如何使用该协议来回答这些问题的用例。需要更多的案例。
可以通过针对服务 URI 的全站跟踪资源
发出检索请求来发现给定服务的此协议部署。/.well-known/dnt/
如果响应是错误,则该服务未实现此标准。如果响应是重定向,则跟随重定向以获取跟踪状态(达到合理的重定向最大值以避免配置错误的无限请求循环)。如果响应成功,则从消息负载中获取跟踪状态表示(如果可能),否则将其视为错误。
在站点正常服务之外的资源上提供跟踪状态的一个主要优势是,可以在使用这些服务之前访问和查看状态。
用户代理可以通过首先发出上述的全站跟踪状态表示的检索请求,然后解析 JSON 表示以提取 状态对象 来检查 指定资源 的跟踪状态。如果检索不成功或解析导致语法错误,用户代理应认为该站点不符合此协议。
状态对象应该具有一个名为 tracking 的属性,其中包含跟踪状态值。每个跟踪状态值的含义定义在 第 7.2 节 跟踪状态值。
如果跟踪状态值为 N,则源服务器声称在至少接下来的 24 小时内,或者在 Cache-Control 信息指示该响应过期之前,不会对指定资源执行任何跟踪。
如果跟踪状态值不是 N,则源服务器声称在至少接下来的 24 小时内,或者在 Cache-Control 信息指示该响应过期之前,它可能会对正在检查的 URI 的请求跟踪用户代理。
通过 DNT 头字段传达的信息被最小化,以避免滥用该字段进行指纹识别或作为侧信道。然而,未来的 DNT 扩展可能允许在通过 DNT:0 发出跟踪同意信号时发送额外信息,因为此同意机制旨在比 Cookie 更持久,并且可以用作传达伪名标识符,作为允许设置 Cookie 的用户首选替代方案。
使用客户端存储始终是一个安全问题。虽然为每个 用户授予的异常 存储的信息是有限的,且脚本无法直接访问,但存储过多的异常可能会超过可用存储空间,或者表明试图利用其他漏洞。
关于脚本存储超出其 有效脚本源 范围的异常的能力也存在安全顾虑。参见 第 6.6.1 节 存储跟踪异常的 API 中的 API 安全性注释。
本规范定义了一种传达用户跟踪偏好的协议,而不是一种本身能防止跟踪的协议。可能会有人想当然地认为 隐私设计
将证明要求 DNT:1 作为所有用户代理的默认配置是合理的。然而,这将违反字段语义,使请求中的存在毫无意义,并为每个 HTTP 请求增加额外的 8 个字节(且毫无效果)。
DNT 信号本身对增强用户隐私毫无作用。只有当接收者认为该信号是经过深思熟虑和自觉配置的,而不是作为默认值定义时,他们才会将其视为用户的偏好。此外,当未发送信号时,接收者仍然受制于在没有同意的情况下存在的任何关于跟踪的监管、法律或其他区域要求。
用户授予的异常引入了隐私风险。通过存储客户端可配置状态并提供在稍后了解它的功能,用户授予的异常 API 可能会促进用户指纹识别和跟踪。用户代理开发人员在实现时应考虑指纹识别的可能性,并可能考虑通过速率限制请求或使用其他启发式方法来减轻指纹识别风险。
存储的异常数据库实际上是在存储用户随时间浏览的站点的本地历史记录。每个用户配置文件(以及每个隐身会话)都需要单独的数据库,并且应防止被观察。用户可能希望清除存储的异常,或整体清除数据库,但作为清除可见浏览器历史记录之外的单独操作。
本规范由 W3C 跟踪保护工作组内部及周边的多次讨论,以及 Adrian Bateman (Microsoft)、Justin Brookman (CDT)、Nick Doty (W3C/MIT)、Marcos Caceres (Mozilla)、Rob van Eijk (受邀专家)、Roy T. Fielding (Adobe)、Vinay Goel (Adobe)、Tom Lowenthal (Mozilla)、Jonathan Mayer (Stanford)、Aleecia M. McDonald (Stanford)、Mike O'Neill (Baycloud Systems)、Matthias Schunter (Intel)、John Simpson (Consumer Watchdog)、David Singer (Apple)、Rigo Wenning (W3C/ERCIM)、Shane Wiley (Yahoo!) 和 Andy Zeigler (Microsoft) 的书面贡献组成。
DNT 头字段基于 Jonathan Mayer (Stanford)、Arvind Narayanan (Stanford) 和 Sid Stamm (Mozilla) 的原始 Do Not Track 提交。doNotTrack 的 JavaScript DOM 属性基于 Andy Zeigler、Adrian Bateman 和 Eliot Graff (Microsoft) 的 Web 跟踪保护 提交。非常感谢 Robin Berjon 为 ReSpec.js 所做的贡献。
媒体类型 application/tracking-status+json 用于跟踪状态表示(第 7.5 节 跟踪状态表示)。
DNT 头字段(定义在 第 5.2 节 HTTP 请求的 DNT 头字段)将在协议“http”的消息头注册表中注册 [RFC3864]。
DNT 在本规范中的使用仅限于提供 HTTP 请求内的控制数据,该数据由单个值组成,不包含逗号列表分隔符;每条消息不允许有多个 DNT 头字段。DNT 旨在端到端地通过中介且不进行修改地传递;它不打算列在 Connection 中。虽然不太可能在 PUT 请求中使用,但该字段不是表示的一部分,也不打算以此方式存储。
DNT 和 Tk 都经过专门设计,以避免需要基于 DNT 值而变化的响应。但是,选择根据接收到的 DNT 值生成不同内容的服务器可以通过在响应的 Vary 头字段中包含 DNT 字段名称来指示这一点。
Tk 头字段(定义在 第 7.3 节 HTTP 响应的 Tk 头字段)将在协议“http”的消息头注册表中注册 [RFC3864]。
Tk 在本规范中的使用仅限于提供 HTTP 响应内的控制数据,该数据由单个值组成,不包含逗号列表分隔符;每条消息不允许有多个 Tk 头字段。Tk 旨在端到端地通过中介且不进行修改地传递;它不打算列在 Connection 中。
在 第 7.4 节 追踪状态资源 中定义的用于追踪状态资源的知名 URI 空间,需在知名 URI 注册表 [RFC5785] 中进行注册。
追踪异常上的名称和解释参数已被进一步定义为 UTF-8 编码,且与用于告知同意的自然语言保持一致。
增加了用于注册 DNT 和 Tk 首部字段,以及注册知名 dnt URI 空间的附录。
客户端脚本 API 已被重写,减少了函数使用并改用 Promise。API 名称也已更改,以防止与先前 API 的潜在部署产生混淆。
关于浏览上下文、顶级源(top-level origin)和域(domain)的术语已更新,以使用 HTML5 中的术语。
本规范现已定义如何扩展 Tk 首部字段(例如,以符合未来可能的法律要求)。目前尚无此类扩展。
向 DNT 首部字段添加扩展的能力不再被标记为“有风险”,因为工作组认为该功能无法被移除。