在 ATProto 之上运行 ActivityPub

Hacker News Top 新闻

摘要

本文建议在 AT Protocol 的 PDS 之上运行 ActivityPub,认为结合两种架构可以在保持与现有联邦式社交媒体兼容性的同时,提供更好的用户自主权和可信退出机制。

暂无内容
查看原文
查看缓存全文

缓存时间: 2026/07/10 15:21

# ActivityPub 叠加 ATProto 来源:https://berjon.com/ap-at/ ¿Por qué no los dos? 一幅古斯塔夫·多雷风格的嵌合体生物,类似龙形,背上驮着一位女子,通体绿色。在政治运动圈里有这样一个笑话:如果你有一个托洛茨基主义者(你可以把“托洛茨基主义者”替换成任何其他派别),你就有了一党;如果你有两个托洛茨基主义者,你就有两个派系;而如果你有三个托洛茨基主义者,那就得党内分裂了。 如今开放社交媒体领域的氛围似乎也是如此。人们觉得必须选边站队并捍卫己方,宁可互相撕咬,也不愿确保那些“豹子”不会伤人。我想这在某种程度上非常社交媒体化,也非常愚蠢。 我想通过提出一个大家都可以一起讨厌的建议,来缓解这种装腔作势的乏味感。或者更严肃地说,我想通过一个简短的练习来证明,稍微多关注一些有趣的架构细节可能并非最愚蠢的事。这可以为更广泛地讨论Web上的社交媒体奠定基础。 这只是一个草图,并且存在问题。我最初想制作一个原型,但由于工作原因,我几乎没有带宽来做原型(所以我主要把笔记扔到博客上)。把它看作一个设计挑衅(https://en.wikipedia.org/wiki/Speculative_design),挑衅的点在于: > 只需相对较少的工作,我们就可以在 ATProto 的个人数据服务器(PDS)之上运行 ActivityPub。 我不会试图说服你,我们*可以*在不修改两者当前状态的情况下做到这一点,但我想让你关注*为什么*这件事值得思考,并且如果运气好的话,说服你我们*应该*朝这个方向前进(即使不一定非得是这个确切的组合)。请注意,我很难相信我是第一个想到这一点的人,但我确实没找到任何相关的东西。也许你认为我应该是唯一想到这个主意的人。 首先要理解的是,AT 协议 (https://atproto.com/) 并不是 Bluesky。ATProto 旨在成为构建社交媒体应用的通用工具箱,并且可以说它扩展了(或者可以轻松扩展)到支持个人数据服务器(PDS)的通用基础设施。事实上,ATProto 架构明确被描述为 PDS,并且该 PDS 是一个用户代理 (https://berjon.com/user-agency/)。虽然 Bluesky 已经明确表示他们打算控制实现 Bluesky(运行在 ATProto 之上)的 `app.bsky` API 路由,但他们也明确表示 `com.atproto` 路由旨在成为开放标准。(这尚未获得治理机制来保证,但我本来也不打算请求许可。) 我之所以提请你注意这种区别,是因为 ATProto 具有有趣的特性,特别是它如何支持可插拔的身份(不依赖于你使用的服务器)以及签名的数据仓库。这赋予了用户权力,而不是像传统联邦那样将权力赋予服务器管理员。这意味着你总是可以保证可信退出 (https://subconscious.substack.com/p/credible-exit),你不会被锁定。默认情况下,电子邮件式的联邦(这是 AP 的底层模型)容易被掌控,而电子邮件确实已经被掌控了(约 85% 是 Gmail,迁移要么在域名层面,要么靠管理员的好意——他们可能接受转发)。 然而,ATProto 本身并不做任何社交媒体。它“只是”一个层,在其之上可以实现协议。这并不意味着它可以用来实现任意的协议,但 ActivityPub/Activity Streams 有一个非常好的间接层,使这变得容易得多:`Actor` 文档 (https://www.w3.org/TR/activitystreams-core/#actors)。一个演员是任何可以拥有活动、从而可以在社交上做事的实体。你可以从几乎任何地方获取演员文档,例如,你可以通过在我的 Mastodon 身份 URL 后添加 `.json` (https://mastodon.social/@robin.json) 来查看我的。你也可以通过将句柄解析为 DID,并在 DID 文档中找到嵌入的信息来获取它。 演员文档有一个巧妙的特性:它为你提供了各种操作的 API 端点的 URL。也就是说,它不是期望整个 API 的端点位于预定义的位置,而是为每个端点指定了任意的 URL。从我的 Mastodon 演员文档中删除一些冗余后,我们可以看到列出了几个这样的端点: ```json { "@context": "https://www.w3.org/ns/activitystreams", "id": "https://mastodon.social/users/robin", "type": "Person", "following": "https://mastodon.social/users/robin/following", "followers": "https://mastodon.social/users/robin/followers", "inbox": "https://mastodon.social/users/robin/inbox", "outbox": "https://mastodon.social/users/robin/outbox", "preferredUsername": "robin", "name": "Robin Berjon" } ``` 这意味着我们可以将其用作间接层,指向带有 ActivityPub 路由的个人 ATProto PDS: ```json { "@context": "https://www.w3.org/ns/activitystreams", "id": "https://mastodon.social/users/robin", "type": "Person", "following": "https://pds.berjon.com/xrpc/org.w3.activitypub.following", "followers": "https://pds.berjon.com/xrpc/org.w3.activitypub.followers", "inbox": "https://pds.berjon.com/xrpc/org.w3.activitypub.inbox", "outbox": "https://pds.berjon.com/xrpc/org.w3.activitypub.outbox", "preferredUsername": "robin.berjon.com", "name": "Robin Berjon" } ``` 成功了吗?还没。 ## 我们遇到了麻烦 我知道你们正坐在座位边缘,咬指甲,有些人紧抓珍珠,等着看我们是否真的可以只通过一点 JSON 调整和一个 ATProto 应用,在不修改任何一个规范的情况下,在 ATProto 上运行 ActivityPub。答案是:还不完全行,但并非遥不可及或不切实际。 第一个问题是,一个 XRPC nsid(例如 `org.w3.activitypub.inbox`)可以是查询(GET)或过程(POST),但据我所知,不能两者都是。但 ActivityPub 的 `inbox` 属性必须支持多个方法。先不谈关于 REST 与 RPC 的长期争论(*哈欠连篇*),这并非无法弥合的重大问题。要么可以为不同的方法更新演员文档,添加独立的属性(对于非 ATProto 实现,这些属性可以指向相同的 URL),要么可以修改 XRPC Lexicon 以支持重载方法。阻碍这里沟通的唯一障碍是人们对这个决定过于虔诚。在现实世界中,这是一个相对容易的修复。 第二个问题是身份和句柄系统并不完全一致。我相信没有什么能阻止 `com.atproto.identity.resolveHandle` 解析 `@[email protected]`,就像它解析 `@robin.berjon.com` 一样,它可能只是去掉开头的 `@`,将另一个 `@` 替换为 `.`,然后使用 DNS 解析 DID。这甚至与 IndieWeb ActivityPub 兼容,在该协议中演员拥有自己的域名(这在 ATProto 用户中相对常见)。应该可以让演员文档也指向 DID,并且 DID 文档反向链接到它作为补充。 (我在这里不打算讨论 DID 的局限性,特别是 `did:plc` 的问题,因为它们不影响集成。我一直在想 DSNP 是否可以为 DID 方法提供合适的基础,但那是另一个话题了。) 然后……就这样了?我的猜测是,由于我还没有机会实际端到端地实现这一点,我可能遗漏了一些棘手问题。但乍一看,这比你在激烈的网络辩论中所想象的要可行得多。 ## 为什么要这么做,老兄? 绝大多数情况下,我们对社交媒体的体验是孤岛式的。它们是封闭的环境,旨在让你留在内部,并且与外部世界的整合非常差。 Activity* 标准和 ATProto 都以不同的方式打破了这种孤岛化。Activity* 构建在 URL 之上,可以大致“社交化”Web 上的几乎任何内容,这很好,但它们不触及底层基础。通常的期望是,要么你运行自己的服务器(这并不适合所有人),要么你必须加入一个联邦服务器,这往往会让你受制于管理员(而且,正如有些人不幸发现的那样,并非所有管理员都很好)。ATProto 方面则为一个可扩展的、围绕用户代理 (https://berjon.com/user-agency/) 和可信退出 (https://subconscious.substack.com/p/credible-exit) 设计的 PDS 提供了良好的基础。这意味着你的在线存在可以由监护人托管(这样你就不必担心运行服务器),但如果你不喜欢你的托管方,你可以保证能够(可验证地)把你的内容带到别处,而且一切都不会改变,你甚至不需要更新你的句柄或设置重定向。 也就是说,它们解决不同的问题,并且解决方案是互补的。通过采取一些小步骤使这两个世界兼容,我们可以从两者中获得更多的价值。 似乎值得一试! --- *本文是重新构想Web部分内容系列的一部分。你可以阅读该系列的其他文章:* 1. 构建下一代 Web (https://berjon.com/next-web/) 2. Web 为了用户代理 (https://berjon.com/user-agency/) 3. 你需要一个更大的浏览器 (https://berjon.com/bigger-browser/) 4. Web 磁贴 (https://berjon.com/web-tiles/) 5. ActivityPub 叠加 ATProto (https://berjon.com/ap-at/) ## 致谢 非常感谢以下出色的人们(按字母顺序排列)提供的宝贵反馈:Amy Guy, Benjamin Goering, Ben Harnett, Blaine Cook, Boris Mann, Brian Kardell, Brooklyn Zelenka, Dave Justice, Dietrich Ayala, Dominique Hazaël-Massieux, Fabrice Desré, Ian Preston, Juan Caballero, Kjetil Kjernsmo, Marcin Rataj, Margaux Vitre, Maria Farrell, and Tess O'Connor。不用说,本文中任何愚蠢和荒谬之处都完全是我自己的责任。

相似文章

ATProto中没有实例

Hacker News Top

解释为何来自Mastodon/ActivityPub的“实例”概念不适用于ATProto(Bluesky的协议),并阐明在ATProto架构中托管和聚合是分离的。

实现ActivityPub为何困难,又为何不必如此

Lobsters Hottest

本文解释了实现ActivityPub协议的复杂性,例如处理多种HTTP签名标准和JSON-LD上下文,并介绍了Fedify,这是一个旨在简化构建ActivityPub应用的TypeScript框架。

ATProto 许可数据提案草案

Hacker News Top

Bluesky 已发布 AT 协议上许可数据的提案草案,同时还有用户列表、审核、OAuth 等其他提案,作为其持续开发工作的一部分。

ActivityPub实现E2EE前的长尾工作

Lobsters Hottest

本文详细介绍了为ActivityPub实现端到端加密(E2EE)所需进行的剩余技术工作,将其分解为基本的消息传递、安全和真实性目标,并解释了密钥透明度和MLS协议如何融入这项工作。

Mandy:Goblins上的ActivityPub

Lobsters Hottest

Spritely Institute发布了Mandy,一个原型,它在Goblins演员模型框架之上实现了ActivityPub,使得ActivityPub参与者可以通过HTTP访问。