The Airbnb Tech Blog | Medium 中文 关注 Airbnb 工程博客是一个由 Airbnb 工程团队撰写的文章集合,讨论了各种技术、创新和行业案例。该网站为读者提供了对软件工程、产品开发、可扩展性、性能等领域的深入分析和见解,还涵盖了技术、领导力和团队协作方面的新趋势,为改进科技公司提供了智慧。 The Airbnb Tech Blog - Medium medium.com RSS medium.com The Airbnb Tech Blog | Medium 中文 RSS thenote.app
灵活认证:为 Airbnb 的数百万用户重新构想认证体系 Airbnb 重构了其认证系统,推出了灵活认证(Flexible Authentication),以应对用户需求与技术复杂性。团队认识到用户登录间隔不规则,将其视为核心挑战而非边缘情况。新方法“先识别,后挑战”将用户识别与验证方式分离,使服务器能够根据用户上下文和区域因素智能选择最合适的挑战。关键的产品洞察是:每个认证屏幕都必须提供逃生路径,由此衍生出“尝试其他方式”选项与挑战选择器。将认证体验完全由服务器驱动,实现了更快的迭代与实验,绕过了冗长的客户端发布周期。这种服务器驱动模式显著减少了客户端代码和包体积,从而提升了性能。最终,新系统带来了更高的认证成功率和更低的重复账户数量,同时降低了运营成本。灵活认证代表了一种持续改进的框架,强调产品洞察与工程架构密不可分。核心教训在于:将决策边界从客户端移至服务器端,才能解锁全球规模系统所需的迭代速度。 Flexible Authentication: Reimagining authentication for millions of users at Airbnb medium.com +1
评估驱动开发:从大规模评估生成式人工智能中汲取的教训 Airbnb 强调将评估视为构建可信生成式 AI 产品的关键工程学科。传统软件测试的假设受到大语言模型(LLM)输出非确定性和主观性的挑战,往往需要 AI 来评估 AI。Airbnb 的产品团队构建基于 LLM 的功能,并由基础设施团队提供工具集和最佳实践。一个基础原则是:必须从项目 outset 开始规划评估,以避免虚假信心和未检测到的回归。"一条规则"是手动审查数据,并通过检查原型输出来建立对成功的直觉。这一习惯演变为评估驱动的开发,其中失败模式被识别、编码并持续测试。评估驱动开发的关键原则包括:明确目标、让真实错误指导指标、使用小而精的评估者集合、指定决策者以及持续协作。三种评估方法形成分层结构:程序化检查用于明显失败,LLM-as-a-Judge 用于细微的质量判断,人工评估用于边缘案例和验证。程序化检查基于确定性代码测试,而 LLM-as-a-Judge 则利用更强的 LLM 对照评分标准进行评估,需要校准以确保可信度。人工评估作为真值和高 stakes 决策的黄金标准。对于代理系统,评估跨越多个层级,不仅检查最终输出,还审查推理路径和工具调用。一个实际 walkthrough 展示了探索初始失败、构建包含程序化检查和校准虚拟法官的分层评估,并通过生产监控进行扩展。关键要点强调:查看数据、避免通用指标、从小处着手、校准评估者、采用分层防御,并在生产中镜像评估。最终,成功的 AI 产品开发取决于评估成为一项协作的团队运动,它塑造了产品成功的定义。 Eval-driven development: Lessons from evaluating GenAI at scale medium.com +1
通过从客人旅程中学习来个性化 Airbnb 搜索 Airbnb 开发了一种基于 Transformer 的序列模型,通过理解用户随时间的行为来个性化房源推荐。传统方法依赖手工特征,难以扩展且表达能力受限。新模型解决了房源浏览量巨大以及预订相对于其他事件极为稀疏等挑战。它将用户历史划分为长期序列(包含低频但信息丰富的事件)和短期序列(最近的房源浏览)。为提升训练效率,他们实施了诸如批量搜索、利用分桶和稀疏计算来减少填充等策略。服务架构将计算密集的序列编码器与实时排序模型解耦,以实现低延迟。仅使用长期序列的初步测试已显示出改进效果,加入短期浏览序列后进一步提升。引入与序列编码器协同训练的集合级排序器后,排序质量得到更大提升。在线 A/B 测试证实了这些增益,显示出预订量和浏览量的显著增长。该系统的有效性也在推广邮件排序中得到验证,凸显了用户嵌入的泛化能力。这一新方法使 Airbnb 能够比以往更深入地理解用户偏好。未来工作包括实时更新、更丰富的事件类型以及生成式推荐器。 Personalizing Airbnb search by learning from the guest journey medium.com +1
从数周缩短至一天:我们如何让大语言模型评估快得足以支持快速迭代 将生产级语言模型系统上线需要快速迭代改进,但由于模型和评估过程的非确定性,这一挑战尤为突出。Airbnb 通过构建覆盖四个层面的可靠 LLM 基础设施,聚焦工程优化与集成,以应对这些挑战。其核心原则是:组件间的接口处最容易出现问题,因此全面的端到端测试至关重要。第一层专注于评估噪声的诊断性框定,区分数据噪声与判断不确定性,以理解性能波动。LLM 评估中的噪声可能源于评分者对输入的不同打分,或 LLM 生成的参考答案发生变化,从而难以辨别模型真正的改进。准确诊断的关键在于区分认识性不确定性(模型/评分者的局限性)与偶然性不确定性(任务本身的歧义)。第二层通过稳定输入给评分者,建立确定性的评估基础。这通过为每个样本缓存参考答案和评分实现,确保相同输入始终返回缓存结果,从而使评估可复现且高效。这种确定性测量是第一层诊断能力得以实现的前提。第三层通过微适配器实现有界、范围受限的模型突变。这些是仅在特定缺陷上训练的小型 LoRA 补丁,支持快速(约一小时)训练及类似热修复的部署。为防止适配器堆栈性能退化,需遵循三条生命周期规则:融合并发触发的补丁、在累积数据上重新训练、以及卸载未使用的补丁。第四层在系统接口处提供端到端验证。尽管各组件单独表现正常,但其交互仍可能导致意外行为。该层面涉及将代表性输入运行于整个生产路径,以衡量综合质量与延迟,确保在部署前暴露接口处的缺陷。这四个层面构成一个依赖栈,每一层的有效性均依赖于其他层面。 From weeks to a day: how we made LLM evaluation fast enough to iterate on medium.com +1
超越单一规模:Airbnb 如何为多产品世界演进其数据架构 Airbnb 向 Homes、Experiences 和 Services 的扩展,要求其离线数据仓库的数据建模框架进行重构。核心挑战在于如何在保持一致性与灵活性的同时,避免数据孤岛和技术债务。他们采取了一种平衡策略,将集中化原则与去中心化建模指南相结合。三项基础原则确保了数据的一致性:禁止混合模型、统一的标识符命名规范以及清晰的命名空间组织。建模指南使各团队能够根据属性的共享性与独特性、未来演进方向以及下游消费场景,自主选择独立模型或单体模型。针对 Listing(房源)、Availability(可用性)、Location(位置)及 Guest Interactions(用户互动)等特定产品领域,因其属性差异显著,采用独立模型;而 Messaging(消息)、Payments(支付)和 Customer Support(客户支持)等跨领域概念,则通过单体模型实现统一视图。离线数据仓库作为关键的转换层,负责将原始生产数据标准化以供分析使用。管理数据债务(包括迁移遗留表)是一项重大任务,需要谨慎的沟通与验证。该框架为 Airbnb 不断变化的数据需求提供了可扩展且一致的基础。 Scaling beyond one: How Airbnb evolved its data architecture for a multi-product world medium.com +1
Sitar-agent:构建可扩展的可靠动态配置边车” Airbnb 开发了 Sitar Agent,一个轻量级的 Kubernetes Sidecar,用于可靠地向数千个服务实例交付动态配置变更。配置交付始于开发人员通过 Git 或 UI 创建或更新配置值,这些值随后存储于 Sitar Service 中。Sitar Service 会定期将配置的全量状态打包为压缩快照并上传至 AWS S3。当服务 Pod 启动时,Sitar Agent 首先将这些 S3 快照下载到挂载的磁盘上,从而实现快速引导。随后,Agent 与 Sitar Service 同步自快照创建以来所做的任何变更,并向主应用容器发出就绪信号。启动后,Agent 每隔数秒持续轮询 Sitar Service 以获取更新。主应用容器通过 Sitar 客户端库从挂载的磁盘读取配置,该库缓存配置值并检测文件变更。一项关键的设计决策是将 Sitar Agent 作为独立的 Sidecar 容器,而非集成到主容器中,此举优先考虑了可靠性、操作安全性和多语言支持,而非微小的成本节约。该系统采用拉取(pull)模型,Agent 轮询 Sitar Service,并通过服务端缓存和基于令牌的数据库访问进行优化,以降低负载。对于本地磁盘键值存储,Airbnb 选择了 SQLite 而非基于 Sparkey 的旧版实现,原因在于 SQLite 在并发能力、性能及多语言支持方面表现更优。SQLite 内置的预写日志(Write-Ahead Logging)允许在写入期间进行并发读取,其更简单的运维模型也优于 RocksDB 虽性能更高但复杂度更大的方案。这种健壮的 Sidecar 设计确保了关键配置能够快速、可靠地交付至 Airbnb 庞大的服务舰队。 Sitar-agent: Building a reliable dynamic configuration sidecar at scale medium.com +1
当历史辜负你时,向地理借取力量。 新冠疫情带来了预测挑战,因为它扰乱了历史模式,使得传统模型不可靠。需求复苏不同步且地理分布不均,疫苗接种和边境重新开放的进度各不相同。若等待每个复苏市场的本地数据,将导致在相当长一段时间内处于“盲目预测”状态。Airbnb 的解决方案是横向跨地理区域观察,而非仅向后回溯时间。他们观察到复苏是顺序展开的,某些走廊在其他地区之前便已出现变化。一个关键信号是平均预订提前期:在干扰期间缩短,在复苏期间延长。通过比较欧洲和北美等地区这些提前期变化的时序,他们可以推断一个市场如何基于另一个市场的经验对重新开放做出反应。这使得他们能够将早期受影响走廊的后验分布作为信息丰富的先验,用于后期受影响的市场。这种先验传播机制实现了实时学习与预测,即使在本地数据稀缺的市场也是如此。该方法需要全球覆盖范围、细粒度数据以及分层贝叶斯建模框架。该方法不仅适用于危机情境,还可用于预测新产品功能上线或监管变更的影响。它允许从早期采用市场立即学习,从而为尚未经历变化的市场提供预测依据。 When history fails you, borrow from geography medium.com +1
利用统一的知识图谱基础设施扩展 Airbnb 的身份图谱 Airbnb 从使用 PaaS 图数据库转向构建内部知识图谱基础设施,以提升性能。身份图谱对于信任与安全至关重要,最初依赖关系型数据库,随后采用 SaaS 图数据库,但面临可扩展性和延迟挑战。新的内部托管基础设施基于 JanusGraph 和 DynamoDB 构建,提供统一平台。为实现 Airbnb 的性能需求,实施了关键优化,包括自定义事务和并行查询执行。该平台支持多租户操作并强制执行模式约束。客户端查询优化(包括重写 Gremlin 查询)进一步提升了性能。内部图谱基础设施显著提高了可扩展性并增强了系统稳定性。各类查询模式均实现了性能提升,从而加快了读 API 的响应时间。自管理系统能够更快地解决故障事件。新系统的写入 QPS 达到原有方案的 10 倍。迁移大幅降低了复杂查询的 P99 延迟。Airbnb 的知识图谱现已支持关键用例。 Scaling Airbnb’s identity graph with a unified knowledge graph infrastructure medium.com +1
Viaduct 1.0 与 Airbnb 数据网格的未来 Viaduct 是 Airbnb 面向数据的服务网格,现已作为社区驱动的项目发布,并提供了稳定的 API。它作为基于 GraphQL 的接口,用于访问和交互各种数据源。Viaduct 的目标是为组织的数据提供统一模式,同时支持去中心化开发。与 GraphQL Federation 不同,Viaduct 通过部署在共享多租户运行时上的模块来分布开发工作。团队通过创建包含 SDL 和解析器的模块来贡献代码,专注于领域逻辑。Viaduct 也可作为联邦架构中的子图运行。1.0 版本新增了功能、通过注解实现的稳定性以及自动化发布机制。Airbnb 致力于社区参与,利用 GitHub 进行架构讨论。文章还突出了 Airbnb 工程师将在 GraphQLConf 2026 上举行的 upcoming 讨论,展示 Viaduct 的能力,包括概率测试、监控、分片解决方案以及使用大语言模型生成模拟数据。该公告鼓励希望统一数据层或为项目做出贡献的人员参与。 Viaduct 1.0 and the future of Airbnb’s data mesh medium.com +1
大规模可靠监控 核心问题在于,可观测性系统在它所监控的基础设施发生故障时也可能失效,从而形成循环依赖。Airbnb 与许多组织一样,曾面临此类问题:其指标管道依赖于它所观测的同一套系统。必须打破这一依赖链,以确保监控的可靠性,尤其是在发生中断时。为解决这一问题,Airbnb 通过由云团队管理的专用 Kubernetes 集群实现了计算隔离。他们重新设计了网络架构,构建了一个基于 Envoy 的自定义第 7 层入口层,以绕过服务网格来传输遥测数据,从而确保优先级和隔离性。由于指标具有极高的数据量,专用网络路径可避免拥塞和潜在的中断。Airbnb 还实施了元监控(meta-monitoring),即对可观测性栈本身进行监控,以检测潜在问题。元监控的关键组成部分是采用“死信开关”(Dead Man's Switch)机制来检测监控系统自身的故障。这一整体方法构建了一个稳健的信号链,可防止可观测性设置中出现静默故障。关键启示在于将监控视为生产系统,确保其可靠性超越其所观测的系统。这对于实现及时的故障响应以及维持用户和业务信心至关重要。这些原则具有普适性,涉及为构建稳健的系统设计而隔离故障域。 Monitoring reliably at scale medium.com +1
船长:构建 Airbnb 的嵌入式工作流引擎 Airbnb 面临复杂工作流(如保险理赔)的持久化执行挑战。现有的外部编排引擎解决方案存在运维复杂和供应商锁定等缺点。为解决这些问题,Airbnb 构建了 Skipper,一种嵌入到每个服务内部的流程引擎。Skipper 强调简洁性、无单点故障以及复用现有数据库。其核心设计包括定义逻辑与动作的工作流,这些工作流封装了单个操作。持久性通过回放机制实现:将动作结果检查点化地写入数据库。回放机制使得工作流在中断后能够从断点处恢复。为提高效率,状态字段被持久化,并通过信号来更新工作流的状态。使用 Skipper 测试工作流更加简便,因为它无需配置队列或模拟任何基础设施。这种方法在确保持久化执行的同时,不引入额外依赖,也不牺牲性能。 Skipper: Building Airbnb’s embedded workflow engine medium.com +1
在 Airbnb 构建容错指标存储系统 Airbnb 开发了一套内部存储系统,用于处理每秒 5000 万个样本以及 2.5 PB 的时间序列数据。这一转变的必要性源于其不断演进的产品和基础设施中广泛部署的代码监控所产生的海量数据。主要工程挑战在于如何高效地持久化并服务这一庞大的数据集。为应对如此巨大的规模,Airbnb 采用了多租户架构,按服务或进程对租户进行隔离,以实现稳定的分组与归因。他们实施了 Shuffle Sharding 机制,将租户工作负载隔离开来,通过将租户仅写入并查询部分节点,从而提升了系统的容错能力。针对租户接入和配置管理等运营复杂性,系统引入了统一的控制平面,自动化租户接入流程并简化配置更新。该系统的关键需求包括:每秒处理超过 5000 万个样本、支持大量仪表板和告警,并保持低查询执行延迟。初期通过影子集群进行的验证揭示了可靠性问题、压缩延迟以及在大数据量负载下查询性能缓慢等问题。解决这些挑战的第一步是确保单个集群的可靠性,重点通过基准测试、防护机制和查询路径隔离,来稳定写入、读取和压缩操作。系统通过在三可用区部署具备状态感知能力的组件实现了容错。同时,实施了副本级限制和租户级控制,以有效管理集群规模并保护系统。随后,系统演进为多集群架构,以降低故障影响范围并增强灵活性。然而,多集群方案也带来了指标发现、查询以及运营开销等方面的复杂性。这些问题通过租户与集群映射工具以及基于 Kubernetes Operator 的自动化部署策略得到了缓解。引入带有自定义增强的 Promxy 后,实现了跨集群查询与告警功能。此次实践的关键经验包括:跨集群查询成本高昂,以及部署一致性的重要性——这可通过自动化和标准化部署来实现。其理念逐渐演变为将集群视为可替换的资源(类似“牲畜”),而非关键且独特的“宠物”,从而更易于扩展和维护。最终,构建该平台需要架构创新、严谨的运营实践,以及在管理预期方面的文化转变。 Building a fault-tolerant metrics storage system at Airbnb medium.com +1
以隐私为先的连接:赋能 Airbnb 的社交体验 Airbnb 正演变为一个更具社交属性的平台,通过“体验”(Experiences)功能强调社区连接。平台将用户隐私置于首位,通过区分内部用户数据与面向公众的个人资料来实现这一目标。用户可自主控制个人资料的可见性,决定在“体验”中分享哪些信息。为此,Airbnb 采用独特的用户 ID 和资料 ID,以支持不同场景下的灵活隐私设置。这使得用户能够在适当情况下拥有多个独立资料,例如房东资料和租客资料。Airbnb 还采用名为 Himeji 的权限管理系统,确保最小权限原则并强化数据安全。该实施过程包括自动化审计、团队协作以及借助 AI 进行重构,以确保标识符的正确使用。在迁移过程中,类型安全与严格测试对于维护数据完整性至关重要。最终,Airbnb 的隐私原则旨在平衡社交功能与用户对个人信息的控制权。这一方法致力于在 Airbnb 社区中同时促进连接与隐私。该系统的建立,旨在让用户能够自信地与他人建立联系并分享信息。 Privacy-first connections: Empowering social experiences at Airbnb medium.com +1
将 Airbnb 的 JVM Monorepo 迁移到 Bazel Airbnb 将其巨大的 JVM 单体仓库从 Gradle 迁移到 Bazel,这个过程花了 4.5 年。切换的主要原因是 Bazel 的速度、可靠性和统一的构建基础设施更为出色。Bazel 的缓存和远程执行大大加快了构建和测试时间,提高了开发人员的生产力。迁移解决了 Gradle 的不可靠性问题,这些问题源于非 hermetic 构建和资源竞争。Airbnb 的 Viaduct 服务的概念验证证明了 Bazel 的有效性,从而导致了更广泛的采用。一个关键组件是自动构建文件生成器,以最小化开发人员的工作量并维护共存的构建系统。这个生成器高效地解析源文件、管理依赖循环并支持细粒度的构建图。迁移还涉及解决诸如多版本第三方库支持和确保部署兼容性等挑战。最后,严格的测试,特别是服务的启动和集成测试,验证了 Bazel 构建部署的正确性。总的来说,结果是一个大大改进的构建系统,开发人员的满意度也大大提高。 Migrating Airbnb’s JVM Monorepo to Bazel medium.com +1