原来用过AWS cloudFormation 服务感觉用于帮客户搭建环境很好用。近期需要客户创建一个阿里云OSS 桶资源,并给一个对应用户mobile APP访问的RAM角色和一个用于server访问的子账号。 文档写了5小节,整个过程比较繁琐,如果需要客户手动操作可能会造成一些困扰。所以这里就看了下和AWS cloudFormation对应的阿里云 资源编排服务(ROS)。此文档记录一些Sample方便以后接着填这种坑。
阿里云的文档写的还是不错的:
模板的基本语法: https://help.aliyun.com/document_detail/28858.html?spm=a2c4g.11186623.6.580.161a3f76e6WOvq
资源索引:https://help.aliyun.com/document_detail/127039.html?spm=a2c4g.11186623.6.554.d1496897MYamIT
场景是需要创建OSS桶,并创建一个访问OSS桶的子账号,并创建一个签发STS服务访问OSS桶的角色。且子账号和角色权限不同。实质上这里就解决2个问题。
1 传入参数
2 如何让第一个资源作为第二个资源的输入,依赖执行
1 传入参数可以使用Parameters参数,如下:
"Parameters": {
"UserInputName": {
"Type": "String",
"Description": {
"en": "user name",
"zh-cn": "待创建阿里云子账号名称"
},
"AllowedPattern": "^[a-z0-9]{1}[a-z0-9\\-.]{1,62}[a-z0-9]{1}$",
"Label": "User Name",
"ConstraintDescription": "Must begin and be end with a lowercase letter or number. The length is within [3, 63]",
"Default": "test"
}
}
即传入了一个参数UserInputName
而如何使用? 需要使用到函数参数
{
"Ref": "UserInputName"
}
就可以在模板的中得到对应输入,并填到对应资源中进行创建。
2 如何让第一个资源作为第二个资源的输入,依赖执行。
如何读取到资源创建的输出呢,也是使用函数,执行后即为资源创建后的输出。
{"Fn::GetAtt": ["RamUser","UserId"]}
如何让第二个资源在第一个资源创建后才执行?
Resources字段中有dependsOn 字段。既可以实现一个资源依赖另一个资源。
下面提供一个创建子账号,并获取子账号AccessKeyID ,并创建一个可以用子账号扮演角色的模板代码。下次好直接抄。
{
"Description": "test",
"Parameters": {
"UserInputName": {
"Type": "String",
"Description": {
"en": "user name",
"zh-cn": "待创建阿里云子账号名称"
},
"AllowedPattern": "^[a-z0-9]{1}[a-z0-9\\-.]{1,62}[a-z0-9]{1}$",
"Label": "User Name",
"ConstraintDescription": "Must begin and be end with a lowercase letter or number. The length is within [3, 63]",
"Default": "test"
}
},
"ROSTemplateFormatVersion": "2015-09-01",
"Outputs": {
"用户名": {
"Value": {"Fn::GetAtt": ["RamUser","UserName"]}
},
"用户ID": {
"Value": {"Fn::GetAtt": ["RamUser","UserId"]}
},
"用户ARN": {
"Value":{
"Fn::Sub": [
"acs:ram::${Var1}:user/${Var2}",
{
"Var1": { "Ref":"ALIYUN::TenantId" },
"Var2": {"Fn::GetAtt": ["RamUser","UserName"]}
}
]
}
},
"用户AccessKeyID": {
"Value": {"Fn::GetAtt": ["RamAK", "AccessKeyId"]}
},
"用户AccessKeySecret": {
"Value": {"Fn::GetAtt": ["RamAK","AccessKeySecret"]}
}
},
"Resources": {
"RamUser":{
"Type": "ALIYUN::RAM::User",
"Properties": {
"UserName": {
"Ref": "UserInputName"
},
"DisplayName": "User"
}
},
"RamAK": {
"Type": "ALIYUN::RAM::AccessKey",
"Properties": {
"UserName": {"Fn::GetAtt": ["RamUser","UserName"]}
},
"DependsOn":"RamUser"
},
"RamRole": {
"Type": "ALIYUN::RAM::Role",
"Properties": {
"RoleName": "AppRole",
"Description": "OSS RAM角色",
"AssumeRolePolicyDocument" : {
"Statement": [
{
"Action": "sts:AssumeRole",
"Effect": "Allow",
"Principal": {
"RAM": [{
"Fn::Sub": [
"acs:ram::${Var1}:user/${Var2}",
{
"Var1": { "Ref":"ALIYUN::TenantId" },
"Var2": {"Fn::GetAtt": ["RamUser","UserName"]}
}
]
}]
}
}
],
"Version":"1"
}
},
"DependsOn":"RamUser"
}
}
}