我在 AWS Fargate 上构建了按需 Minecraft 主机,以停止支付月费

发布: (2025年12月28日 GMT+8 02:35)
8 分钟阅读
原文: Dev.to

Source: Dev.to

请提供您希望翻译的正文内容,我将为您翻译成简体中文并保持原有的格式、Markdown 语法以及技术术语不变。

Introduction

大多数 Minecraft 服务器托管商都有一个根本缺陷:他们对一台空置 90 % 时间的服务器收取月度订阅费用。

我意识到我每月支付 €20 / month,而我的孩子和我只在大多数周末玩几个小时。这就是 ERGamesPRO 的灵感——一个基于 AWS 的按需 Minecraft 托管平台,目标很简单:

如果没有人在玩,我就不应该付费。
(所谓“无服务器”,指的是没有一直开启的计算资源:没有需要打补丁的 EC2 集群,CPU/RAM 的计费在服务器关闭时停止。存储/任务控制的费用仍然存在,但相较于 24/7 计算来说很小。)

架构:为何选择 Fargate?

我选择 AWS Fargate (ECS) 来实现 scale‑to‑zero(零规模)行为,而无需管理实例。

  • Start – 在仪表板上点击 “Start” 即会为该特定服务器创建一个全新的 Fargate 任务。
  • Stop – 点击 “Stop” 会终止任务,计算费用降至零。

高层架构

层级AWS 服务
计算AWS Fargate (ECS) – 基于 ARM64(Graviton)的 Docker 容器
存储Amazon EFS – 持久化世界数据
编排/计费AWS Lambda + EventBridge
数据库DynamoDB – 用户配置文件和服务器元数据
身份验证Amazon Cognito
DNSAmazon Route 53 – 每个服务器的主机名

Stable Join Address (No Load Balancer)

我没有使用 NLB/ALB 或 Cloud Map。ECS 任务运行在 public subnets 并获取公共 IP。

当服务器启动时,控制平面会自动更新位于域 ergamespro.click 下的 Route 53 记录,将自定义主机名(例如 myserver.ergamespro.click)映射到该任务的公共 IP。

  • TTL: 60 秒
  • Connection method: 玩家始终通过主机名进行连接,即使底层 IP 在重启后可能会变化。

“Scale to Zero”问题

按需主机最难的部分是何时安全地关闭灯光。

我使用 AWS Lambda + EventBridge 构建了一个调和循环:

  1. Watchdog Lambda 每隔几分钟运行一次。
    • 它使用基于 TCP 的 Minecraft Server List Ping 对每个运行中的服务器进行 ping,以读取实时玩家数量。
  2. 如果玩家数量 > 0 → 保持服务器运行。
  3. 如果玩家数量 = 0 且持续 10 分钟 → 触发关机事件。

如果 ping 失败或超时,watchdog 失效打开 并重试,以避免误关机。当关机事件触发时,Fargate 任务停止,计算费用立即结束。对于空闲时间较多的使用场景(例如周末会话),相比 24/7 托管,可将成本降低 约 70–80 %

途中遇到的挑战

1️⃣ 500 资源限制(CDK)

  • 问题:使用 AWS CDK(Python)时,我触及了 CloudFormation 的硬性限制——每个堆栈最多 500 个资源
  • 解决方案:将单体拆分为 七个独立堆栈(Foundation、Data、Compute 等)。部署变得更快、更安全,也更易于理解。

2️⃣ 启动时间与金色镜像

  • 问题:Fargate 并非瞬时启动。运行时拉取约 1 GB 的镜像会导致令人痛苦的冷启动延迟。
  • 解决方案:构建一个流水线,为每个 Minecraft 版本(Vanilla、Paper、Forge)预先构建“金色镜像”,目标平台为 ARM64(Graviton)
    • Graviton 更便宜。
    • 对于典型的基于 Java 的 Minecraft 工作负载,它的表现非常出色。

注意:拥有 100 + 插件的高度模组化服务器可能更适合时钟频率更高的 x86,但对于 Vanilla 和轻量模组包,ARM 是极佳选择。

3️⃣ 使用 EFS 的持久存储

  • 问题:Fargate 任务是短暂的;容器文件系统在任务停止时会消失。
  • 解决方案:使用 Amazon EFS 并配合专用 访问点。每个服务器获得一个独立目录,挂载到 /data,这样世界、配置和备份在重启之间得以持久化。
    • EFS 默认采用 突发吞吐量(可配置为弹性或预置)。
    • 在小规模时突发模式表现极佳;预置吞吐量成本可能过高,因此默认使用突发模式。

4️⃣ 在短暂环境中的文件访问(SFTP)

  • 问题:在 VPS 上你可以 SSH 并上传模组。而在 Fargate 中,当服务器停止时根本没有“可 SSH 的机器”。
  • 解决方案Sidecar 模式——当用户启动服务器时,同时启动 Minecraft 容器和一个 SFTP sidecar
功能细节
两个容器挂载同一 EFS 卷
服务锁定、chroot 的 SFTP 服务器
凭证动态生成,短期有效
端点同一 DNS 名称,固定端口 2222
生命周期任务停止时即消失

由于客户端 IP 不可预测,SFTP 并未基于源 IP 白名单。访问通过短期凭证和锁定的 SFTP 配置进行控制,既保持了文件管理的便利,又不破坏按需模型。

5️⃣ 实时控制台流式传输

  • 问题:我想在网页仪表盘中实时查看日志。Kinesis Data Streams 对于刚起步的项目来说成本太高。
  • 解决方案CloudWatch Logs + WebSockets
    1. Fargate 将日志流入 CloudWatch Logs。
    2. Lambda 轮询新日志条目。
    3. 通过 API Gateway WebSocket 连接将更新推送到前端。

延迟约为 1–2 秒——在大幅降低成本的前提下,这一延迟是可以接受的。

今日平台

结果感觉像是高级托管,但行为却像云原生应用:

  • 启动时间:~50–90 s 从点击到轻量服务器可加入;~3–4 min 对于重度模组包。
  • 隔离性:每个服务器在其自己的 Fargate 任务中运行(无噪声邻居)。
  • 费用模型:仅为服务器运行的时间付费。

接下来是什么?

  • 多区域支持 – 部署更靠近玩家。
  • 每个服务器多个世界 – 在 EFS 上存储多个世界目录,让用户选择要启动的世界。

文档结束。

ETA 已上线 ergames.pro.

ERGamesPRO landing page with the headline “Instant Minecraft Servers” and the subheading “Start in minutes, pause anytime,” promoting pay‑as‑you‑go Minecraft hosting.

我还有一些邀请代码,供想要对架构进行压力测试的开发者和玩家使用——欢迎提供直接反馈。

如果想了解 AWS CDK 结构、Lambda 逻辑或 Fargate 调优的细节,请在评论中提问。

Back to Blog

相关文章

阅读更多 »