本文介绍了 Auth0 如何为服务设计架构,以确保可扩展性和高可用性,从而每月处理逾 15 亿次登录。 如今,身份验证对绝大多数应用程序而言至关重要。Auth0 可以为任何堆栈上的各类(移动、Web 和原生)应用程序提供身份验证、授权和单点登录服务。 我们设计的 Auth0 一开始就可以在任何地方运行:我们的云、你的云,甚至在你自己的私有基础设施上。 在本文中我们将详细探讨我们的公共 SaaS 部署,并简要介绍 auth0.com 背后的基础设施,以及用来确保它顺畅运行的高可用性策略。 我们曾在 2014 年撰文介绍了 Auth0 的架构,自那以来 Auth0 已发生了很大的变化,下面是几大要点:
核心服务架构 图 1:Auth0.com 的核心服务架构 我们的核心服务包括如下不同的层:
高可用性 2014 年,我们使用了多云架构(使用 Azure 和 AWS,还有谷歌云上的一些额外资源),多年来该架构为我们提供了良好的服务。随着使用量(和负载)迅速增加,我们发现自己越来越依赖 AWS 资源。 最初,我们将环境中的主区域切换到 AWS,Azure 留作故障切换区域。我们开始使用更多的 AWS 资源(比如 Kinesis 和 SQS)时,将同样的功能特性放在这两家提供商处开始遇到了麻烦。 随着移动(和扩展)的速度越来越快,我们选择继续支持 Azure,但功能同等性(feature parity)有限。 如果 AWS 上的一切出现故障,我们仍可以使用 Azure 集群来支持身份验证等核心功能,但是不支持我们一直在开发的许多新功能。 2016 年出现几次严重宕机后,我们决定最终集中到 AWS 上。我们停止了与确保服务和自动化平台无关的全部工作,而是专注于:
比如说,不妨看看我们的美国环境架构。我们有这个总体结构,如下图: 图 2:Auth0 美国环境架构 下图是单一可用区内部的结构: 图 3:Auth0 单一可用区 在这种情况下,我们使用两个 AWS 区域:
正常情况下,所有请求都流向 us-west-2,由三个独立的可用区处理请求。 这就是我们实现高可用性的方式:所有服务(包括数据库)在每个可用区(AZ)上都有运行中的实例。 如果一个可用区因数据中心故障而宕机,我们仍有两个可用区来处理请求;如果整个区域宕机或出现错误,我们可以通知 Route53 故障切换到 us-west-1、恢复操作。 我们在服务故障切换方面有不同的成熟度级别:一些服务(比如在 Elasticsearch 上构建缓存的用户搜索 v2)可正常运行,但数据稍显陈旧,不过核心功能按预期运行。 在数据层中,我们使用:
我们每年至少进行一次故障切换演练,我们有剧本和自动化,帮助新的基础设施工程师尽快了解如何演练以及由此带来的影响。 我们的部署通常由 Jenkins 节点触发;视服务而定,我们使用 Puppet、SaltStack 及/或 Ansible 来更新单个节点或一组节点,或者我们更新 AMI,为不可变的部署创建新的自动扩展组。 我们为新旧服务部署了不同类型的环境;由于我们需要为应该统一的系统维护自动化、文档和监控,结果证明这基本上很低效。 我们目前在为一些核心服务推出蓝/绿部署(blue/green deployment),我们打算为每个核心的支持服务实施同样的一套。 自动化测试 除了每个项目的单元测试覆盖外,我们还有在每个环境中运行的多个功能测试套件。 我们在部署到生产环境之前先在试运行环境上运行,完成部署后再在生产环境中运行,以确保一切正常。 我们的自动化测试要点:
CDN 2017 年之前我们运行自己专门定制的 CDN,在多个区域运行 Nginx、Varnish 和 EC2 节点。 2017 年以后,我们改用 CloudFront,它为我们带来了几个好处,包括:
但同时也有几个缺点,比如我们需要运行 Lambdas 来执行一些配置(比如将自定义标头添加到 PDF 文件等等)。不过,好处绝对压倒缺点。 Extend 我们提供的功能之一是能够通过身份验证规则或自定义数据库连接,运行自定义代码,作为登录事务的一部分。 这些功能由 Extend(https:///)提供支持,Extend 是一个可扩展性平台,由 Auth0 发展而来,现在还被其他公司所使用。 有了 Extend,我们的客户就可以用那些脚本和规则编写所需的任何服务,扩展配置文件、规范属性和发送通知等。 我们有专门针对 Auth0 的 Extend 集群,它们结合使用 EC2 自动扩展组、Docker 容器和自定义代理,以处理来自我们用户的请求,每秒处理数千个请求,并快速响应负载变化。 想了解这如何构建和运行的更多信息,请参阅这篇介绍如何构建自己的无服务器平台的文章(https://tomasz./2018/03/how-to-build-your-own-serverless-platform.html)。 监控 我们结合使用不同的工具来监控和调试问题:
我们的绝大多数警报来自 CloudWatch 和 DataDog。 我们往往通过 TerraForm 来配置 CloudWatch 警报,用 CloudWatch 来监控的主要问题有:
CloudWatch 是基于 AWS 生成的指标(比如来自负载均衡系统或自动扩展组的指标)来监控警报的最佳工具。 CloudWatch 警报通常发送给 PagerDuty,再从 PagerDuty 发送给 Slack/手机。 DataDog 是我们用来存储时间序列指标并采取相应操作的服务。我们发送来自 Linux 系统、AWS 资源和现成服务(比如 Nginx 或 MongoDB)的指标,还发送来自我们构建的自定义服务(比如 Management API)的指标。 我们有许多 DataDog 监控指标,举几个例子:
从上面例子中可以看出,我们监控低级指标(如磁盘空间)和高级指标(如 MongoDB 副本集变更,这提醒我们主节点定义是否发生了变化)。我们做了大量的工作,设计了一些相当复杂的指标来监控一些服务。 DataDog 警报的输出非常灵活,我们通常将它们全部发送给 Slack,只把那些“引人注意”的警报发送给 PagerDuty,比如错误高峰,或者我们确信对客户产生影响的大多数事件。 至于日志记录方面,我们使用 SumoLogic 和 Kibana;我们使用 SumoLogic 来记录审计跟踪记录和 AWS 生成的许多日志,我们使用 Kibana 存储来自我们自己的服务和其他“现成”服务(如 Nginx 和 MongoDB)的应用程序日志。 未来设想 我们的平台经历了很大的变化,以处理额外负载和对客户来说很重要的众多使用场景,但我们仍有优化的空间。 不仅我们的平台在扩大,我们的工程部门规模也在扩大:我们有许多新团队构建自己的服务,而且需要自动化、工具和可扩展性方面的指导。 有鉴于此,我们落实了这些计划,不仅扩展平台,还夯实工程实践:
作者:Dirceu Tiegs(沈建苗编译) |
|