Hashnode 在 AWS 上使用 Step Functions、EventBridge 和 Redis 创建可扩展的 Feed 架构

Hashnode 构建可扩展的事件驱动架构 (EDA) 用于生成用户动态数据

Hashnode 为数千名用户构建了一个基于事件驱动架构 (EDA) 的可扩展系统,用于生成用户动态数据。该公司采用了 AWS 的无服务器服务,包括 Lambda、Step Functions、EventBridge 和 Redis Cache。该解决方案利用了 Step Functions 的分布式映射功能,支持高并发处理。

背景与问题

Hashnode 之前曾实现了一个个性化用户动态数据的解决方案,但很快发现该方案存在页面加载速度较慢的问题,并且由于动态生成用户动态数据时执行昂贵的查询,存在数据库不稳定性的潜在风险。Hashnode 的软件工程师 Florian Fuchs 提出了优化动态数据计算的总体思路:通过预计算用户动态数据来优化页面加载速度,而不是每次用户访问时都进行计算,从而直接从缓存中返回动态数据,减少页面加载时间。

解决方案架构

工程师们使用 AWS Step Functions 实现了动态数据计算逻辑,并设计了两个工作流:

  1. 数据准备工作流:使用三个 Lambda 函数从数据库中提取相关数据,并将其存储在 AWS ElastiCache (Redis) 缓存中。
  2. 动态数据计算工作流:根据缓存中是否存在用户元数据,动态数据计算逻辑可以完全基于 Redis 缓存中的元数据,或者需要从数据库中提取用户元数据。

在新架构中,动态数据的重新计算由以下事件触发:

  • 帖子创建或更新时,通过 AWS EventBridge 发布事件。
  • 定期通过 EventBridge Scheduler 触发。

Step Functions 的分布式映射功能

Hashnode 团队利用了 Step Functions 中的 Map 状态来编排并行工作负载。Map 状态支持两种模式:

  • 默认内联模式:支持有限的并发,仅接受 JSON 数组作为输入。
  • 分布式模式:适用于大规模并行工作负载,支持处理存储在 S3 中的数据源。在分布式模式下,Step Functions 可以运行超过 10,000 个并行子工作负载。

具体实现

解决方案中使用了两个 Step Functions,均采用分布式模式的 Map 状态:

  • 一个用于处理有缓存元数据的用户。
  • 另一个用于处理没有缓存元数据的用户。

开发人员报告称,目前对数千名用户的动态数据完全重新计算仅需 26 秒。团队还实现了定期缓存清除逻辑,以确保旧的缓存数据被定期清除。

总结

Hashnode 通过使用 AWS 的无服务器服务和 Step Functions 的分布式映射功能,成功构建了一个高效且可扩展的动态数据生成系统。该方案显著提高了页面加载速度,并避免了数据库的潜在不稳定性问题。

阅读 18
0 条评论