通过 CloudFormation 为现有表添加自动缩放到 AWS DynamoDB
Posted
技术标签:
【中文标题】通过 CloudFormation 为现有表添加自动缩放到 AWS DynamoDB【英文标题】:Adding autoscaling to AWS DynamoDB via CloudFormation for already existing table 【发布时间】:2018-02-10 21:52:06 【问题描述】:我们的团队很高兴看到宣布推出 AWS DynamoDB 的自动缩放功能,在尝试通过在 Web 界面中添加配置时,我们发现这很好地满足了我们应用程序的四个需求。
但是,通过 CF 添加相同配置的尝试被证明有点复杂。本文提供的以下示例 - http://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/aws-resource-dynamodb-table.html#cfn-dynamodb-table-examples-application-autoscaling - 下面是结果,它不起作用。堆栈详细信息:
17:02:25 UTC+0300 UPDATE_ROLLBACK_IN_PROGRESS AWS::CloudFormation::Stack my-stack The following resource(s) failed to create: [WriteCapacityScalableTarget].
17:02:24 UTC+0300 CREATE_FAILED AWS::ApplicationAutoScaling::ScalableTarget WriteCapacityScalableTarget table/TableName|dynamodb:table:WriteCapacityUnits|dynamodb already exists
17:02:18 UTC+0300 CREATE_IN_PROGRESS AWS::ApplicationAutoScaling::ScalableTarget WriteCapacityScalableTarget
17:02:15 UTC+0300 CREATE_COMPLETE AWS::IAM::Role ScalingRole
17:01:42 UTC+0300 CREATE_IN_PROGRESS AWS::IAM::Role ScalingRole Resource creation Initiated
17:01:42 UTC+0300 CREATE_IN_PROGRESS AWS::IAM::Role ScalingRole
17:01:37 UTC+0300 UPDATE_IN_PROGRESS AWS::CloudFormation::Stack my-stack User Initiated
我的CF脚本如下:
"Resources":
"MyCustomTableName":
"Type": "AWS::DynamoDB::Table",
"Properties":
"TableName": "TableName",
"AttributeDefinitions": [
"AttributeName": "someAttribute1:someAttribute2",
"AttributeType": "S"
],
"KeySchema": [
"AttributeName": "someAttribute1:someAttribute2",
"KeyType": "HASH"
],
"ProvisionedThroughput":
"ReadCapacityUnits": 1,
"WriteCapacityUnits": 1
,
"StreamSpecification":
"StreamViewType": "NEW_AND_OLD_IMAGES"
,
"WriteCapacityScalableTarget":
"Type": "AWS::ApplicationAutoScaling::ScalableTarget",
"Properties":
"MaxCapacity": 30,
"MinCapacity": 1,
"ResourceId":
"Fn::Join": [
"/",
[
"table",
"Ref": "MyCustomTableName"
]
]
,
"RoleARN":
"Fn::GetAtt": [
"ScalingRole",
"Arn"
]
,
"ScalableDimension": "dynamodb:table:WriteCapacityUnits",
"ServiceNamespace": "dynamodb"
,
"ScalingRole":
"Type": "AWS::IAM::Role",
"Properties":
"AssumeRolePolicyDocument":
"Version": "2012-10-17",
"Statement": [
"Effect": "Allow",
"Principal":
"Service": [
"application-autoscaling.amazonaws.com"
]
,
"Action": [
"sts:AssumeRole"
]
]
,
"Path": "/",
"Policies": [
"PolicyName": "root",
"PolicyDocument":
"Version": "2012-10-17",
"Statement": [
"Effect": "Allow",
"Action": [
"dynamodb:DescribeTable",
"dynamodb:UpdateTable",
"cloudwatch:PutMetricAlarm",
"cloudwatch:DescribeAlarms",
"cloudwatch:GetMetricStatistics",
"cloudwatch:SetAlarmState",
"cloudwatch:DeleteAlarms"
],
"Resource": "*"
]
]
,
"WriteScalingPolicy":
"Type": "AWS::ApplicationAutoScaling::ScalingPolicy",
"Properties":
"PolicyName": "WriteAutoScalingPolicy",
"PolicyType": "TargetTrackingScaling",
"ScalingTargetId":
"Ref": "WriteCapacityScalableTarget"
,
"TargetTrackingScalingPolicyConfiguration":
"TargetValue": 70.0,
"ScaleInCooldown": 60,
"ScaleOutCooldown": 60,
"PredefinedMetricSpecification":
"PredefinedMetricType": "DynamoDBWriteCapacityUtilization"
如果有人能解释为什么会发生这种情况,我将非常感激:)
【问题讨论】:
奇怪的是,似乎只有一个特定的表存在问题 - 通过控制台添加或删除自动缩放没有帮助 - 脚本仍然因上述错误而失败。解决此问题的唯一方法是通过 CF 更新预置容量(不可扩展),然后才通过相同的 CF 脚本添加自动扩展。 【参考方案1】:按照错误信息进行
CREATE_FAILED AWS::ApplicationAutoScaling::ScalableTarget WriteCapacityScalableTarget table/TableName|dynamodb:table:WriteCapacityUnits|dynamodb already exists
您正在创建一个名为 "TableName": "TableName"
的 DynamoDB 资源。一个区域内不能有两个同名的 dynamoDB 表。
转到 DynamoDB 控制台并检查您是否有任何此类表并将其删除。发布该模板应该可以正常工作。
选项 2:如果您想继续使用现有表,则可以从 CF 模板中删除 AWS::DynamoDB::Table 资源。
【讨论】:
谢谢。我从错误消息中得到的印象是,该表的 WriteCapacityUnits 已经创建——因为它们已经创建了,因为该表已经存在。但是删除表资源本身是否意味着该表被删除?它有数据,我不想丢失(或迁移,就此而言)。所以要明确一点,表资源是很久以前创建的,我只想为其添加自动缩放 - 通过将 WriteCapacityScalableTarget、ScalingRole 和 WriteScalingPolicy 引入 CF 模板。 我也尝试过模拟。首先使用 CF 模板创建 DynamoDB 表,然后将 WritingCapacityScalableTarget、ScalingRole 和 WriteScalingPolicy 添加到 CF 模板并执行更新堆栈。进展顺利。那么,您是否有可能通过控制台测试了一些东西而忘记清除它?【参考方案2】:对我来说,在为已经存在的发电机表设置自动缩放时出现此错误。确保您已删除为该发电机表设置的任何手动(通过控制台)自动缩放。然后重新执行,堆栈将到达UPDATE_COMPLETE
阶段。
【讨论】:
已确认。我通过 AWS 控制台创建并随后删除了一个 DynamoDB 表。尝试通过 CloudFormation 创建具有自动缩放规则的同名表时,它抱怨该表的自动缩放策略已经存在。我需要通过 AWS 控制台重新创建表,禁用表的扩展,然后删除表。只有在这样做之后,CloudFormation 才成功。以上是关于通过 CloudFormation 为现有表添加自动缩放到 AWS DynamoDB的主要内容,如果未能解决你的问题,请参考以下文章
将现有 AWS 资源整合到 CloudFormation 堆栈中
无法通过自定义 cloudformation 资源调用 lambda 函数
无法使用 CloudFormation 将 GSI 添加到 DynamoDB 表
如何使用 CloudFormation 模板更新现有 AWS API Gateway