-
-
Save mdjnewman/b9d722188f4f9c6bb277a37619665e77 to your computer and use it in GitHub Desktop.
#!/usr/bin/env bash | |
usage="Usage: $(basename "$0") region stack-name [aws-cli-opts] | |
where: | |
region - the AWS region | |
stack-name - the stack name | |
aws-cli-opts - extra options passed directly to create-stack/update-stack | |
" | |
if [ "$1" == "-h" ] || [ "$1" == "--help" ] || [ "$1" == "help" ] || [ "$1" == "usage" ] ; then | |
echo "$usage" | |
exit -1 | |
fi | |
if [ -z "$1" ] || [ -z "$2" ] || [ -z "$3" ] ; then | |
echo "$usage" | |
exit -1 | |
fi | |
shopt -s failglob | |
set -eu -o pipefail | |
echo "Checking if stack exists ..." | |
if ! aws cloudformation describe-stacks --region $1 --stack-name $2 ; then | |
echo -e "\nStack does not exist, creating ..." | |
aws cloudformation create-stack \ | |
--region $1 \ | |
--stack-name $2 \ | |
${@:3} | |
echo "Waiting for stack to be created ..." | |
aws cloudformation wait stack-create-complete \ | |
--region $1 \ | |
--stack-name $2 \ | |
else | |
echo -e "\nStack exists, attempting update ..." | |
set +e | |
update_output=$( aws cloudformation update-stack \ | |
--region $1 \ | |
--stack-name $2 \ | |
${@:3} 2>&1) | |
status=$? | |
set -e | |
echo "$update_output" | |
if [ $status -ne 0 ] ; then | |
# Don't fail for no-op update | |
if [[ $update_output == *"ValidationError"* && $update_output == *"No updates"* ]] ; then | |
echo -e "\nFinished create/update - no updates to be performed" | |
exit 0 | |
else | |
exit $status | |
fi | |
fi | |
echo "Waiting for stack update to complete ..." | |
aws cloudformation wait stack-update-complete \ | |
--region $1 \ | |
--stack-name $2 \ | |
fi | |
echo "Finished create/update successfully!" |
also deploy does not support rollback configuration
Also useful as a workaround to serverless/serverless#2233 and serverless/serverless#2831.
The logic between lines 53 and 63 can be removed by simply adding --no-fail-on-empty-changeset
to the aws cloudformation update-stack ...
command.
Changed my mind - you actually do need separate logic for handling the case of "deploy to an existing stack, but there are no updates to apply". Consider a stack in CREATE_COMPLETE
status, and we go to perform another deploy as an update. If we have no changes to apply, the stack will remain in CREATE_COMPLETE
status, and we must not attempt to use aws cloudformation wait stack-update-complete
because this command would hang forever. So I think the existing snippet is correct, and you should not use --no-fail-on-empty-changeset
Am getting the below error while trying to update the existing stack. What do I need to change in the script?
An error occurred (AlreadyExistsException) when calling the CreateStack operation: Stack [Test-stack] already exists
@viveksamaga I've not tested this since 2016 sorry, it's possible the AWS CLI has introduced some breaking changes
you would choose
aws cloudformation deploy
vs this method IF you are not planning on having your cloudformation parameters in a separate file.create-stack
andupdate-stack
have the --parameters variable that can be set to a file whilstaws cloudformation deploy
does not.