我正在尝试编写一个执行以下操作的bash函数:
我遇到的问题是--capabilities CAPABILITY_IAM
语句中命令else
的最后一位,如果我有多个参数,我不想一直传递。
An error occurred (InsufficientCapabilitiesException) when calling the CreateStack operation: Requires capabilities : [CAPABILITY_NAMED_IAM]
// that means I need to pass in --capabilities CAPABILITY_IAM
有没有办法告诉bash:嘿,从第3个参数中获取所有arg,然后在其后添加--capabilities CAPABILITY_IAM
?像在JavaScript中一样,我可以这样做:
function allTogetherNow(a, b, ...c) {
console.log(`${a}, ${b}, ${c}. Can I have a little more?`);
}
allTogetherNow('one', 'two', 'three', 'four')
这是我的职能:
cloudformation_create() {
if [ -z "$3" ]; then
aws cloudformation create-stack --stack-name "$1" --template-body file://"$2" --capabilities CAPABILITY_IAM
else
aws cloudformation create-stack --stack-name "$1" --template-body file://"$2" --parameters "${@:3}" --capabilities CAPABILITY_IAM
fi
}
如果我不使用bash函数,则第3个参数等等看起来像这样:
aws cloudformation create-stack --stack-name MY_STACK_NAME --template-body file://MY_FILE_NAME --parameters ParameterKey=KeyPairName,ParameterValue=TestKey ParameterKey=SubnetIDs,ParameterValue=SubnetID1 --capabilities CAPABILITY_IAM
2019年5月22日更新:
按照丹尼斯·威廉姆森的回答。我尝试过:
cloudformation_create STACK_NAME FILE_NAME ParameterKey=KeyPairName,ParameterValue=TestKey ParameterKey=SubnetIDs,ParameterValue=SubnetID1
错误:
An error occurred (ValidationError) when calling the CreateStack operation: Parameters: [...] must have values
cloudformation_create STACK_NAME FILE_NAME "ParameterKey=KeyPairName,ParameterValue=TestKey ParameterKey=SubnetIDs,ParameterValue=SubnetID1"
错误:
An error occurred (ValidationError) when calling the CreateStack operation: ParameterValue for ... is required
ParameterKey
和ParameterValue
的情况下通过:cloudformation_create STACK_NAME FILE_NAME KeyPairName=TestKey SubnetIDs=SubnetID1
错误:
Parameter validation failed:
Unknown parameter in Parameters[0]: "PARAM_NAME", must be one of: ParameterKey, ParameterValue, UsePreviousValue, ResolvedValue
// list of all the params with the above error
ParameterKey
和ParameterValue
并以字符串形式传入。出现错误:arameter validation failed:
Unknown parameter in Parameters[0]: "PARAM_NAME", must be one of: ParameterKey, ParameterValue, UsePreviousValue, ResolvedValue
我尝试了Alex Harvey的答案并得到了:
An error occurred (ValidationError) when calling the CreateStack operation: Template format error: unsupported structure.
答案 0 :(得分:3)
基于LeBlue的答案和对docs的快速阅读,看来您需要根据函数的参数来构建--parameters
的参数:
cloudformation_create () {
local IFS=,
local parameters="${*:3}"
#if block not shown
aws cloud_formation ... --parameters "$parameters" ...
这假定您的函数被这样调用:
cloudformation_create foo bar baz=123 qux=456
也就是说,使用键,已经形成了值对。
上面的代码段通过将IFS
设置为逗号来工作。在引号内使用$*
会使其中包含的元素使用IFS
的第一个字符进行连接。如果您需要在函数的另一部分中使用分词功能,则可能需要保存IFS
的当前值,然后再进行更改,然后在加入分配后将其恢复。
结果,$parameters
的扩展名为baz=123,qux=456
答案 1 :(得分:1)
我不确定是否能回答您的问题,但也许会对您有所帮助。
$#是参数的数量。
$ @将包含所有参数,您可以传递它。
#!/bin/bash
foo()
{
echo "params in foo: " $#
echo "p1: " $1
echo "p2: " $2
echo "p3: " $3
}
echo "number of paramters: " $#
foo $@ 3 # pass params and add one to the end
致电:
./test.sh 1 2
输出:
number of paramters: 2
params in foo: 3
p1: 1
p2: 2
p3: 3
答案 2 :(得分:1)
我怀疑参数扩展错误,因为--parameters
可能需要一个 参数。
引用cloudformation_create
的所有需要结束的参数作为--parameters
标志的值:
cloudformation_create "the-stack" "the-filename" "all the parameters"
或将函数重写为 not 用"$*"
扩展为多个参数(将每个arg合并为一个)
cloudformation_create () {
...
else
aws cloudformation ... --parameters "${*:3}" --capabilities CAPABILITY_IAM
fi
}
这会将所有值保留为一个字符串/参数,两者都将转换为:
aws cloudformation ... --parameters "all other parameters" --capabilities CAPABILITY_IAM
与您的版本相反:
aws cloudformation ... --parameters "all" "other" "parameters" --capabilities CAPABILITY_IAM
答案 3 :(得分:0)
我会这样写:
cloudformation_create() {
local stack_name=$1
local template_body=$2
shift 2 ; local parameters="$@"
local command=(aws cloudformation create-stack
--stack-name "$stack_name"
--template-body "file://$template_body")
[ ! -z "$parameters" ] && \
command+=(--parameters "$parameters")
command+=(--capabilities CAPABILITY_IAM)
${command[@]}
}
注意:
shift 2
会将$3
旋转到$1
,这样您就可以照常使用$@
。答案 4 :(得分:0)
首先,感谢大家的帮助。
我已经意识到了这个问题(并且我的错误):
AWS用Requires capabilities : [CAPABILITY_NAMED_IAM]
返回了错误,我的函数有[CAPABILITY_IAM]
。
取决于模板以及与创建IAM相关的参数,需要[CAPABILITY_NAMED_IAM]
或[CAPABILITY_IAM]
。我发现答案here很有帮助。
因此,对于我而言,bash函数很好,对于我尝试创建的模板,我需要传递--capabilities CAPABILITY_NAMED_IAM
。我已经尝试过了,而且效果很好。