【发布时间】:2017-06-22 04:07:50
【问题描述】:
有没有办法在自动扩展组+启动配置中将 IPv6 地址自动分配给 EC2 实例?
VPC 和子网均针对 IPv6 设置。手动创建的实例是可以的。 我也可以手动分配它们,但我似乎无法在 CloudFormation 中找到方法。
【问题讨论】:
标签: amazon-ec2 ipv6 amazon-cloudformation
有没有办法在自动扩展组+启动配置中将 IPv6 地址自动分配给 EC2 实例?
VPC 和子网均针对 IPv6 设置。手动创建的实例是可以的。 我也可以手动分配它们,但我似乎无法在 CloudFormation 中找到方法。
【问题讨论】:
标签: amazon-ec2 ipv6 amazon-cloudformation
目前的状态是 CloudFormation 对 IPv6 的支持是可行的。不好玩也不完整,但你可以用它构建一个堆栈——我不得不使用 2 个自定义资源:
这是我的设置:
VPCipv6:
Type: "AWS::EC2::VPCCidrBlock"
Properties:
VpcId: !Ref VPC
AmazonProvidedIpv6CidrBlock: true
VPCipv6Prefix:
Type: Custom::Variable
Properties:
ServiceToken: !GetAtt [ IdentityFunc, Arn ]
Value: !Select [ 0, !Split [ "00::/", !Select [ 0, !GetAtt VPC.Ipv6CidrBlocks ] ] ]
IdentityFunc 是在 Lambda 中为“自定义变量”实现的“身份函数”,as described in this answer。与此链接的答案不同,我直接在同一个堆栈中实现该函数,因此更易于维护。 See here for the gist.
RouteInternet6:
Type: "AWS::EC2::Route"
Properties:
RouteTableId: !Ref RouteTableMain
DestinationIpv6CidrBlock: "::/0"
GatewayId: !Ref IGWPublicNet
DependsOn:
- IGWNetAttachment
IGWNetAttachment 是对堆栈中定义的AWS::EC2::VPCGatewayAttachment 的引用。如果不等待,可能无法正确设置路由
SubnetA:
Type: AWS::EC2::Subnet
Properties:
AvailabilityZone: !Select [ 0, !GetAZs { Ref: "AWS::Region" } ]
CidrBlock: 172.20.0.0/24
MapPublicIpOnLaunch: true
# The following does not work if MapPublicIpOnLaunch because of EC2 bug
## AssignIpv6AddressOnCreation: true
Ipv6CidrBlock: !Sub "${VPCipv6Prefix.Value}00::/64"
VpcId:
Ref: VPC
关于 AssignIpv6AddressOnCreation 被注释掉 - 这通常是您想要做的,但显然,EC2 API 中有一个错误阻止它工作 - 这不是 CloudFormation 的错误。这在this AWS forums thread 中进行了记录,以及我接下来将在此处介绍的解决方案。
AssignIpv6AddressOnCreation 问题:这是 lambda 设置:
IPv6WorkaroundRole:
Type: AWS::IAM::Role
Properties:
AssumeRolePolicyDocument:
Version: '2012-10-17'
Statement:
- Effect: Allow
Principal:
Service:
- lambda.amazonaws.com
Action:
- sts:AssumeRole
Path: "/"
Policies:
- PolicyName: !Sub "ipv6-fix-logs-${AWS::StackName}"
PolicyDocument:
Version: '2012-10-17'
Statement:
- Effect: Allow
Action:
- logs:CreateLogGroup
- logs:CreateLogStream
- logs:PutLogEvents
Resource: arn:aws:logs:*:*:*
- PolicyName: !Sub "ipv6-fix-modify-${AWS::StackName}"
PolicyDocument:
Version: '2012-10-17'
Statement:
- Effect: Allow
Action:
- ec2:ModifySubnetAttribute
Resource: "*"
IPv6WorkaroundLambda:
Type: AWS::Lambda::Function
Properties:
Handler: "index.lambda_handler"
Code: #import cfnresponse below required to send respose back to CFN
ZipFile:
Fn::Sub: |
import cfnresponse
import boto3
def lambda_handler(event, context):
if event['RequestType'] is 'Delete':
cfnresponse.send(event, context, cfnresponse.SUCCESS)
return
responseValue = event['ResourceProperties']['SubnetId']
ec2 = boto3.client('ec2', region_name='${AWS::Region}')
ec2.modify_subnet_attribute(AssignIpv6AddressOnCreation={
'Value': True
},
SubnetId=responseValue)
responseData = {}
responseData['SubnetId'] = responseValue
cfnresponse.send(event, context, cfnresponse.SUCCESS, responseData, "CustomResourcePhysicalID")
Runtime: python2.7
Role: !GetAtt IPv6WorkaroundRole.Arn
Timeout: 30
这就是你使用它的方式:
IPv6WorkaroundSubnetA:
Type: Custom::SubnetModify
Properties:
ServiceToken: !GetAtt IPv6WorkaroundLambda.Arn
SubnetId: !Ref SubnetA
此调用与自动缩放组竞争以完成设置,但它不太可能失败 - 我运行了几十次,在第一个实例启动之前正确设置字段从来没有问题。
【讨论】:
我遇到了一个非常相似的问题,并就此与 AWS Support 进行了交谈。当前状态是 CloudFormation 对 IPv6 的支持非常有限。
我们最终为许多特定于 IPv6 的事物创建了自定义资源。我们有一个自定义资源:
自定义资源只是执行“原始”API 调用的 Lambda 函数,以及授予 Lambda 执行该 API 调用足够权限的 IAM 角色。
【讨论】: