【老司机精选】基于隐私保护的广告归因

10033.png

作者:Hummer,目前就职于字节跳动,曾经是从事过 iOS 基础和业务架构研发,也做过 Flutter 基础组件研发,目前从事隐私安全方向的研发工作。

审核:Leo,iOS开发,老司机技术周报编辑,抖音iOS基础体验负责人

文章的开头会从 cookies、广告和追踪的关系讲起,然后开始介绍广告归因的历史,引申出 Apple 的匿名化点击衡量工具 PCM(Private Click Measurement:一款在保护用户隐私的情况下,同时帮助广告商衡量跨站广告转化效果的工具),并进一步介绍 PCM 的最新功能(app-to-web 的广告转化归因),最后介绍 SKAdNetwork 过去一年更新的功能。

Cookie 与广告

Cookie 在互联网广告行业中一直扮演着重要的角色,因为它是广告主进行归因的重要基础。广告归因简单来说就是把广告相关活动和广告效果进行关联的过程,比如用户在搜索网站点击了一个推广链接,进入了广告主的网站,然后购买了一款商品,将购买行为和点击行为进行关联的过程即为一次广告归因。当然你肯定也听过一个较为抽象的名词——转化,即上述举例中的一次成功的购买行为可以视为一个转化。为了更好的理解 cookie 和 归因,我们再看一个根据具体的例子。

image_0

假设你是一位滑板爱好者,想网购一款合适的专业长滑板,于是你打开搜索引擎(比如:searchlongboard.biz),然后输入了关键字“滑板”,这时它为你展示很多条滑板商店的搜索结果,于是你点击了第一条,这时搜索引擎会在浏览器里面存储一个 cookie ,记录了你的搜索历史或者点击的链接,然后浏览器跳转到了一个出售各类专业滑板的商店(比如:longboardshop.biz),你把自己非常喜欢的一款滑板加入了购物车并完成了付款,此时搜索引擎之前存储的 cookie 发生更新,把你的点击和购买行为关联到一起,这样可以非常高效地进行广告转化效果的衡量。像 searchforlongboard.biz 这样的网站还可以通过记录你的点击、浏览的网站、浏览时长等信息构建你的用户画像,并在你不知情的情况下,把你的用户画像出售给了广告主。

以上行为称为跨网域追踪。大部分用户不希望在网上冲浪时泄漏自己的隐私信息,包括兴趣点、点击行为、个人信息等,追踪会失去用户对网站的信任感并造成商业和用户间的错位。现在越来越多的用户开始寻找反制措施,比如使用广告屏蔽插件限制网站的追踪行为,从用户角度来讲,广告屏蔽插件确实是一个不错的选择,但是也会导致一些网站兼容问题,可能导致浏览体验不佳。此外,因为插件会屏蔽所有的广告,自然导致广告归因活动不再有任何可能性。

image_1

用户和商业网站在广告追踪共识上的分歧严重影响了网页的浏览体验,所以 Apple 开始研发一款既能保护用户隐私又不让广告行业过度受损的技术。2017年 Apple 推出了智能防追踪技术( Intelligent Tracking Prevention 简称 ITP),它可以识别出追踪者并防止用户被追踪者画像,同时不影响完整的网页浏览体验。还是以上面买滑板为例,你点击了搜索引擎推荐的结果,它在浏览器里记录了相关的 cookie ,然后你在滑板电商网站上完成了一笔交易,此时 ITP 会阻止该电商网站将 cookie 或者其他数据发送给第三方,比如搜索引擎公司,因此搜索引擎便无法在你点击链接和购买滑板之间建立联系。

当然对用户的追踪不仅仅发生在网页端,同时也发生在移动端。IDFA(Identifier For Advertisers)也称为广告标识符,长久以来一直被用于对 iOS 用户地跨 app 对追踪和画像。Apple 在 2020 年推出了 SKAdNetwork 框架,用于广告网络在对 app 安装进行归因时保护用户的隐私,之后会对它进行详细介绍。

在用户不知情、不同意的情况下擅自分享用户的个人数据的行为严重侵犯了用户的个人隐私。不仅 像 Apple 这样的商业公司开始意识到保护用户隐私的重要性,越来越多国家或地区的监管机构也开始重视用户隐私,比如 CCPA 和 GDPR 就规定网站必须告知用户,其数据是如何被使用的,此外,越来越多的浏览器也开始内置防追踪的功能。因此,基于追踪用户的商业模式注定是不可持续的。

PCM

如何在保护用户隐私和保持广告商业繁荣之间取得平衡成为了非常重要的课题。Apple 在这个问题上给出的答案就是匿名化点击衡量(PCM),PCM 是 W3C 隐私保护小组的一个提案,为了成为行业通用标准,还需要更多浏览器厂商进行适配。PCM 是一种纯本地化的广告归因机制,意味着有限的信息能够阻止网站识别特定用户,使用 PCM 时用户不会被追踪,所以 app 不需要用 App Tracking Transparency 弹窗提醒用户,目前 Safari 已经完全支持 web-to-web 和 app-to-web 的广告归因。

web-to-web 归因

还是以滑板为例来介绍 PCM 的工作原理:当你点击了搜素引擎的推广链接,该链接会产生两个信息,Source ID 和 目标网站(Destination Site),其中 Source ID 是标识本次广告活动的一个 8 比特大小的值,目标网站是指商品链接或广告主的网站,这两个值将会被存储在浏览器中;当你进入滑板的电商网站,并将喜爱的滑板加入了购物车,此时电商网站可以使用一个值记录此次的转化行为,这个值称为触发数据(Trigger Data),触发数据是 4 比特大小的值,可以用于表示转化事件,比如可以是点击了喜欢按钮或者将商品加入了购物车,又或者是完成了一次商品交易,这个值也会储存在浏览器中。

我们注意到所有的数据都存储在本地设备的浏览器上,那么如何将这些信息报送给搜索引擎和电商网站呢?当浏览器检测到一次成功的转化时,会将这些信息整理成一份报告,浏览器会在转化发生后的 24 到 48 小时内随机地向搜索引擎和电商网站发送这份报告,这样可以允许网站对广告转化结果进行归因,同时又保证用户不会被跨域追踪。这种随机延迟的机制能有效防止网站通过时间节点将点击和转化关联起来进而识别出特定用户。在最新的 iOS 15 和 macOS 12 系统中,还加入了 IP 地址保护机制,在发送报告的时候防止 IP 地址被用于生成设备指纹。

开发实战

image_2

如图所示,在搜索引擎的推广链接上增加了两个属性:

// Mark an ad with PCM data on the source site
<a href="https://longboardshop.biz/lemonYellowLongboard.html"
   attributionsourceid="55"
   attributiondestination="https://longboardshop.biz"/>
复制代码

它们表示的意思是,柠檬色的滑板的营销 ID 是 55,该广告将会在 longboardshop.biz 的网站上发生转化。

image_3

而在电商网站侧,可以通过 HTTP GET 请求向搜索网站发送触发事件:

// Specify the trigger data for a conversion
<img src="https://searchforlongboardbiz/convert/?action=addToCart />
复制代码

然后搜索网站会返回一个固定格式的地址:

https://searchlongboard.biz/.well-known/private-click-measurement/trigger-attribution/15/
复制代码

那么加入购物车的转化值就是 15(Trigger Data),如果加入购物车之后又发生了更重要的转化,比如购买行为,那么可以使用优先级更高的 6 比特数据覆盖之前的转化值。这一步的目的是兼容现有的归因方案,方便过渡到 PCM 。

image_4

最后一步为发送报告,报告将以 JSON 格式发送到搜索和电商网站的固定地址:

https://xxx.biz/.well-known/private-click-measurement/report-attribution/
复制代码

这份报告将转化和点击关联到了一起,但是并不涉及任何可以识别个人用户的信息,网站只知道某位用户在某个地点将一款柠檬色的滑板加入了购物车。

Safari 在发送报告时会将用户的 IP 地址隐藏起来,以防止被搜索引擎和广告主这样的公司所滥用。 image_5

app-to-web 归因

​ 除了 web-to-web 的归因场景,现在 PCM 支持进行 app-to-web 的归因场景了,接下来我们看一下 app-to-web 的归因场景是如何运作的。首先,你打开一款社交软件,然后你看到了一款滑板的广告,于是想买滑板的你点击了这个广告,此时 Source ID 和目标网站两个属性信息会被存储在本地设备上,之后跳转到了 Safari 并打开了滑板电商的网站,你点击了加入购物车按钮出发了转化事件,浏览器把转化值存储起来,在接下来的 24 到 48 小时内向社交 app 和电商网站报告归因结果。 ​

开发实战

社交 app 的报告接收地址需要在 info.plist 中使用 NSAdvertisingAttributionReportEndpoint 进行注册: image_6

系统会自动在这个地址后面拼接上一个固定路径:

https://example.com/.well-known/private-click-measurement/report-attribution
复制代码

为了保证转化是由用户的点击触发的,Apple 提供了一个新的组件——UIEventAttributionView,将它放置在广告之上,可以用于验证点击事件发生在归因报告发送之前。

let eventAttributionView = UIEventAttributionView()

eventAttributionView.translatesAutoresizingMaskIntoConstraints = false
adView.addSubview(eventAttributionView)
NSLayoutConstraint.activate([
    adView.topAnchor.constraint(equalTo: eventAttributionView.topAnchor),
    adView.leadingAnchor.constraint(equalTo: eventAttributionView.leadingAnchor),
    adView.trailingAnchor.constraint(equalTo: eventAttributionView.trailingAnchor),
    adView.bottomAnchor.constraint(equalTo: eventAttributionView.bottomAnchor)
])
复制代码

当用户点击广告之后需要创建一个 UIEventAttribution 实例,在 app 打开浏览器时,这个UIEventAttribution 中的信息会被传递给电商网站。

let adURL = URL(string: "https://longboardshop.biz/lemonYellowLongboard.html")!
let eventAttribution =
    UIEventAttribution(sourceIdentifier: 55,
                       destinationURL: adURL,
                       sourceDescription: "Lemon Yellow Longboard ad.",
                       purchaser: "Longboard Shop, Inc.")
复制代码

UIEventAttribution 实例会包括以下信息:

  • Source ID:广告活动标识符,比如柠檬色的滑板
  • 目标网站URL:转化发生的地方,比如滑板电商网站地址
  • 对Source的描述:对点击广告的描述
  • 广告主:对广告购买者的描述

如果 app 生命周期是基于 UIScene 的,只需要创建一个 OpenExternalURLOptions 对象,并作为参数传递给 open 方法即可:

let sceneOpenURLOptions = UIScene.OpenExternalURLOptions()
sceneOpenURLOptions.eventAttribution = eventAttribution

self.view.window?.windowScene?.open(adURL,
                                    options: sceneOpenURLOptions,
                                    completionHandler: nil)
复制代码

如果 app 生命周期是基于 UIApplication 的,需要将 OpenExternalURLOptions 对象包裹在字典中再传递给 open 方法:

let appOpenURLOptions: [UIApplication.OpenExternalURLOptionsKey : Any] = [
    .eventAttribution: eventAttribution
]
UIApplication.shared.open(adURL,
                          options: appOpenURLOptions,
                          completionHandler: nil)
复制代码

PCM 防欺诈

因为 PCM 的归因报告不包含任何可识别身份的信息,所以接收者不能完全信任收到的归因报告。为了解决信任问题,PCM 使用加密签名的方式防止欺诈,其核心思想是在报告接收者看不到消息的情况下对报告进行签名,其中蕴含的数学原理是 RSA 盲签名。接下来介绍如何使用 RSA 盲签名机制防止欺诈: ​image_7

当你点击搜索引擎上的推广链接时,浏览器会向搜索网站请求它的公钥(e,n),当归因事件产生时会浏览器会生成一个归因报告,此时浏览器希望搜索网站能够对该报告签名同时又不能读取报告的内容。

image_8

可以使用该公式生成一个隐藏消息,其中 m 可以是报告原文也可以是报告的哈希值,而 r 是与公钥中的 n 互质的较大随机数,将隐藏消息发送给搜索网站。

image_9

image_10

搜索网站接收到该隐藏消息后,使用它的私钥(d,n)按照上面公式对该消息进行签名,再将结果返回给浏览器。 image_11

image_12 浏览器根据上面的公式去除签名结果中的 r 因子,便得到了搜索网站对原始报告的签名。

image_13

在归因事件发生的 24 小时后,浏览器会将签名的报告发送给搜索网站和电商网站,二者便可以利用搜索网站的公钥对报告的可靠性进行验证。

image_14

PCM 的测试模式

对于开发者而言如何对 PCM 进行测试是非常关键的一环,而 Apple 也在最新 iOS / macOS 系统的 Safari 中内置了 PCM debug 模式,打开方式如下图所示,开启 debug 模式后,归因报告将会每 10 秒发送一次,而不是正常模式的 24 到 48 小时随机发送。

macOS系统上打开方式: Safari -> 偏好设置 -> 高级,勾选“在菜单栏中显示开发菜单”,在“开发”菜单中打开 PCM Debug 模式。 image_15​ ​ iOS系统上打开方式: image_16

SKAdNetwork 新功能

首先让我们一起回顾一下 SKAdNetwork 的工作原理。SKAdNetwork 的参与者有 3 个:广告网络,发布广告的应用和被推广的应用。

假如你在一款社交 app 的信息流中看到了一个和滑板有关的 app 的广告,那么这款滑板 app 的广告是由某个广告网络所提供的,社交 app 扮演了发布广告的角色,而这款滑板 app 就是被推广的 app 。

image_17​当你点击了这款滑板 app 的广告后,会跳转到 App Store,同时广告网络的 ID、社交 app 的 ID、该广告的营销 ID、时间戳以及其他防欺诈的信息立即以报告的形式存储在 App Store 中。

然后你安装了滑板 app 这款软件,当第一次打开滑板 app 时,滑板 app 需要调用 StoreKit 提供的接口:

class func registerAppForAdNetworkAttribution()

class func updateConversionValue(_ conversionValue: Int)
复制代码

二者选一即可,因为两个接口都可以用于触发归因定时器(24小时),区别在于后者可以使用一个更大的归因值重置定时器,只要这个 24 小时定时器的倒计时没有结束,可以调用任意次该更新接口。

倒计时结束之后,接下来的 0-24 小时内,App Store 会把归因报告发送给广告网络。 image_18

关于 SKAdNetwork 更多更详细的内容可以回顾去年 WWDC 两篇 session:Build trust through better privacy《WWDC20 10676 - 通过更好的隐私保护与用户建立信任》) 和 What's new with in-app purchase

接下来我们看一下在 WWDC20 之后,SKAdNetwork 更新了哪些功能。

支持更安全的签名算法

SKAdNetwork 2.1 开始支持更安全的 256 位密钥,该密钥用于生成每个广告的签名,更详细的内容可以参考以下几篇文章: ​

支持浏览型转化归因

SKAdNetwork 2.2 增加了对浏览型转化归因的支持。 以下是 Google Analytics 对点击型转化和浏览型转化的解释:

点击型转化:不管投放了多少个不同的广告系列,转化功劳都会归于广告系列中最后点击的那个广告。 浏览型转化:如果在看到广告和发生转化之间没有发生任何点击,则不管投放了多少个不同的广告系列,转化功劳都会归于广告系列中用户最后看到的那个广告。

image_19​ 要想使用 SKAdNetwork 的浏览型转化归因功能,需要以下步骤:

  1. 需要创建一个 SKAdImpression 对象的实例;
  2. 生成广告的签名;
  3. 在开始展示广告时调用 startImpression(_:completionHandler:)
  4. 结束展示广告时调用 endImpression(_:completionHandler:)

更详细的步骤可以查看 Signing and Providing Ads 对于浏览型广告的介绍。

与浏览型转化一起引入的功能还有保真度参数,可以理解为一种优先级,点击型转化的保真度是 1 ,而浏览型转化的保真度是 0,意味着点击型转化的归因报告相比于浏览型转化的归因报告有更高的优先级。这其实呼应了广告归因的通用标准,即一次转化会优先归因到最后一次点击上,其次再归因到最后一次展示上。

支持多方反馈

image_20​从 iOS 14.6 开始,SKAdNetwork 3.0 可以向 6 个广告网络发送归因报告。

对于一次转化,系统会对广告网络进行排名,其依据是广告网络提供的广告的类型以及该广告最后展示的时间,即距离转化时间点最近的广告排名更高,以及点击型转化比浏览型转化的排名更高,排名第一的广告网络可以接收到包含 conversion-valuesource-app-id 的归因报告,而其他广告网络接收到的报告中不包含这两个值,并且 did-win 参数为 false

从 iOS 15 开始,广告主也可以接收到归因报告,只需要在 app 的 info.plist 中配置NSAdvertisingAttributionReportEndpoint 作为报告接收地址即可。

更详细的内容请参考Receiving Ad Attributions and Postbacks

IP地址保护

在 iOS 15 系统上 SKAdNetwork 也享有 IP 地址保护的能力,该功能和 PCM 中的作用是一致,防止 IP 地址被广告网络或者广告主用对用户的追踪。

SKAdNetwork 的测试模式

使用 SKAdNetwork 的测试模式可以缩小发送归因报告的时间窗口,由普通模式下的 24-48 小时降低到 5-10 分钟,有利于加快开发速度。 进入 SKAdNetwork 的测试模式需要满足以下几个条件:

  1. 保证广告每次展示时的随机数(nonce)必须唯一;
  2. 用于生成广告签名的参数的顺序必须正确;
  3. app 的 source-app-id 为 0 ,并且 app 的签名必须时 development 类型;
  4. 测试机上需要安装 SKAdNetwork 的描述文件,下载方式参考Downloading a Testing Profile

总结

以上内容就是 WWDC21 上所有与广告归因相关内容的介绍,可以看出 Apple 在过去一年不断地完善 PCM 和 SKAdNetwork ,目前已经具备了 web-to-web、app-to-web 和 app-to-app 的归因能力,相信不久后 web-to-app 的归因功能也会到来。

关注我们

我们是「老司机技术周报」,一个持续追求精品 iOS 内容的技术公众号。欢迎关注。

关注有礼,关注【老司机技术周报】,回复「2021」,领取 2017/2018/2019/2020 内参

支持作者

在这里给大家推荐一下 《WWDC21 内参》 这个专栏,一共有 102 篇关于 WWDC21 的内容,本文的内容也来源于此。如果对其余内容感兴趣,欢迎戳链接阅读更多 ~

WWDC 内参 系列是由老司机牵头组织的精品原创内容系列。 已经做了几年了,口碑一直不错。 主要是针对每年的 WWDC 的内容,做一次精选,并号召一群一线互联网的 iOS 开发者,结合自己的实际开发经验、苹果文档和视频内容做二次创作。

猜你喜欢

转载自juejin.im/post/7103719736982110244