4. AWS Batch 环境搭建:计算环境与作业队列
好,咱们直接进入正题。这一章要搞定的,是 AWS Batch 里最核心的两个组件——计算环境和作业队列。说白了,计算环境就是你的算力池,作业队列就是任务调度器。两个搭对了,你的 Batch 工作流才能跑得稳。
4.1 计算环境:你的算力池
计算环境(Compute Environment)是 AWS Batch 的核心资源池。它决定了用什么样的机器、多大算力、按需还是竞价。我最初踩过坑——随便选几个参数就创建,结果跑的作业要么资源不够,要么浪费钱。
4.1.1 类型选择:托管型 vs 非托管型
| 类型 | 说明 | 适用场景 |
|---|---|---|
| 托管型(Managed) | AWS 自动管理 EC2 实例的扩缩容 | 绝大多数场景,推荐 |
| 非托管型(Unmanaged) | 你自行管理底层实例 | 特殊定制需求,极少用 |
我一般直接用托管型。省心,AWS 会根据作业压力自动扩缩,半夜不跑作业时自动缩减到最小,帮你省钱。非托管型……说实话,除非你有非常特殊的网络或安全要求,否则别碰。
4.1.2 实例类型与分配策略
嗯,这里要注意。AWS Batch 允许你指定一组实例类型,而不是单一类型。比如可以混用 c5、m5、r5 系列。我个人习惯把计算密集型(c系)和通用型(m系)放在一起,让 Batch 根据作业需求自动选。
分配策略也很关键。主要有两种:
- BEST_FIT:从当前可用实例里选最合适的。如果你的实例池里已经有空余的 c5.large,它会优先重用,而不是新开一台。适合稳定负载。
- BEST_FIT_PROGRESSIVE:逐步尝试更优实例。它会先尝试最小的,如果不够再升。适合混合负载,但扩缩慢一点。
4.1.3 vCPU 上下限设置
这是最容易踩坑的地方。Min vCPU 和 Max vCPU 必须合理。曾经我有个项目,Min 设了 0,Max 设了 256,结果小规模测试时 Batch 只启动一个实例,作业排队等了好久。后来我调高 Min 到 4,确保至少有几台机器待命。
| 参数 | 建议值 | 踩坑经验 |
|---|---|---|
| Min vCPU | 0(节省)或 4(常驻) | 设为 0 时第一次作业启动慢,但省钱 |
| Max vCPU | 根据作业峰值估算 | 设太小作业排队,设太大浪费钱 |
| Desired vCPU | 可选,一般留空 | 手动设置后 Batch 会强制保持该数量 |
4.1.4 使用 Spot 实例节省成本
如果你能接受作业被中断(比如支持 checkpoint 的深度学习训练),强烈建议用 Spot 实例。AWS Batch 原生支持「使用 Spot 实例的托管计算环境」。我算过一笔账:同样跑 1000 个作业,用 Spot 可以省 60%-80%。
创建 Spot 计算环境时,需要指定一个 Spot 占比。比如 100% 表示全部用 Spot。我个人习惯设 100%,但如果任务必须保证完成,可以混用一些 On-Demand。
# 创建托管计算环境(使用 AWS CLI)
aws batch create-compute-environment \
--compute-environment-name my-spot-env \
--type MANAGED \
--state ENABLED \
--compute-resources type=SPOT,minvCpus=0,maxvCpus=256,desiredvCpus=0,instanceTypes=c5.large,c5.xlarge,c5.2xlarge,subnets=subnet-xxx,securityGroupIds=sg-xxx,spotIamFleetRole=arn:aws:iam::xxx:role/spot-fleet-role,ec2KeyPair=my-key
4.2 作业队列:任务调度中枢
作业队列(Job Queue)把作业分发给计算环境。你可以建立多个队列,每个队列绑定不同的计算环境,实现优先级或资源隔离。
4.2.1 队列与计算环境的关联
一个作业队列可以关联 1 到多个计算环境。我通常会配两个:一个用 Spot 省钱(优先级低),一个用 On-Demand 保底(优先级高)。作业提交时如果 Spot 环境有空闲,就走 Spot;否则自动 fallback 到 On-Demand。
# 创建作业队列,关联两个计算环境
aws batch create-job-queue \
--job-queue-name my-mixed-queue \
--state ENABLED \
--priority 1 \
--compute-environment-order order=1,computeEnvironment=my-spot-env \
--compute-environment-order order=2,computeEnvironment=my-ondemand-env
注意顺序:order 序号小的优先级高。我把 Spot 放在 order=1,表示优先用 Spot 省钱。On-Demand 作为备份只当 Spot 满了才用。
4.2.2 优先级设置
每个作业队列有一个优先级(1-1000,数字越大优先级越高)。不同队列之间按优先级调度。比如你可以建一个 high-priority 队列(priority=100)专门跑线上业务,一个 batch-queue(priority=50)跑离线数据分析。
我见过有人把两个队列的优先级设得一样,结果两个队列的作业混在一起,谁也抢不到资源。所以优先级最好有明显梯度,比如 100、50、10。
4.2.3 状态管理
队列可以随时启用/禁用。禁用后,已在队列中的作业会继续等待,但不再接收新作业。如果你要维护底层计算环境,可以先禁用队列,等维护完再启用。
4.3 避坑指南:创建过程的典型陷阱
- IAM 角色权限不足:创建计算环境时,Batch 服务角色需要 ec2:DescribeInstances、ecs:CreateCluster 等权限。少一个就报错。建议直接用 AWS 托管的
AWSBatchServiceRole,省事。 - 子网和安全组不匹配:选 VPC、子网时,确保子网能访问 ECR(如果拉取镜像)和 S3(如果读写数据)。没有 NAT Gateway 的私有子网会导致作业卡死。
- Spot 实例的 IAM Fleet Role:使用 Spot 实例必须指定
spotIamFleetRole,否则创建计算环境直接失败。这个角色需要用AmazonEC2SpotFleetTaggingRole策略。 - 实例类型不兼容:某些实例类型(比如 p3.2xlarge)需要 EFA 或特殊驱动,Batch 不一定自动配置。建议先在 EC2 测试跑通,再用到 Batch 里。
4.4 快速上手指南:三步搞定
- 创建计算环境:选托管型 + Spot 实例 + 合理 vCPU 范围 + 合适的实例家族。
- 创建作业队列:关联上述计算环境,设置 priority=1。
- 提交测试作业:用一个简单的 echo 或 sleep 作业验证队列通不通。
你可以在 AWS 控制台或 CLI 里执行。我习惯先把配置写成 JSON 文件,方便版本管理:
{
"computeEnvironmentName": "my-test-env",
"type": "MANAGED",
"state": "ENABLED",
"computeResources": {
"type": "SPOT",
"minvCpus": 0,
"maxvCpus": 64,
"instanceTypes": ["c5.large", "c5.xlarge"],
"subnets": ["subnet-12345678"],
"securityGroupIds": ["sg-12345678"],
"spotIamFleetRole": "arn:aws:iam::123456789012:role/spot-fleet-role",
"ec2KeyPair": "my-key"
},
"serviceRole": "arn:aws:iam::123456789012:role/AWSBatchServiceRole"
}
用命令行创建:
aws batch create-compute-environment --cli-input-json file://my-env.json
然后创建队列:
aws batch create-job-queue --job-queue-name my-test-queue --state ENABLED --priority 10 --compute-environment-order order=1,computeEnvironment=my-test-env
aws batch describe-compute-environments 查看状态,VALID 表示正常。如果显示 INVALID,看 describe 输出的 reason 字段,通常能定位问题。
好了,这一章的核心就是计算环境和作业队列的搭配。记得多测试几次,特别是 Spot 中断场景。下一环节我们实际提交一个作业跑起来看看。