Skip to content

Instantly share code, notes, and snippets.

@sebdah
Last active August 29, 2015 14:18

Revisions

  1. sebdah revised this gist Apr 10, 2015. 1 changed file with 1 addition and 1 deletion.
    2 changes: 1 addition & 1 deletion dynamodb-hack.json
    Original file line number Diff line number Diff line change
    @@ -146,7 +146,7 @@
    "easy_install pip || error_exit 'Failed to install pip'",
    "log \"Installed pip\"",
    "echo \"dynamic-dynamodb>=1.7.0,<2.0.0\">/etc/dynamic-dynamodb/requirements.txt",
    "pip install -U -r /etc/dynamic-dynamodb/requirements.txt || error_exit 'Failed to install dynamic-dynamodb package from pip repository'",
    "sudo pip install -U -r /etc/dynamic-dynamodb/requirements.txt || error_exit 'Failed to install dynamic-dynamodb package from pip repository'",
    "log \"Installed dynamic-dynamodb\"",
    "",
    "",
  2. sebdah revised this gist Apr 10, 2015. 1 changed file with 531 additions and 531 deletions.
    1,062 changes: 531 additions & 531 deletions dynamodb-hack.json
    Original file line number Diff line number Diff line change
    @@ -1,533 +1,533 @@
    {
    "AWSTemplateFormatVersion": "2010-09-09",
    "Description": "This is a sample CloudFormation template for deploying Dynamic DynamoDB. This package will be installed from the Python Package Index repository. For more information, see http://dynamic-dynamodb.readthedocs.org.",
    "Parameters": {
    "S3Bucket": {
    "Type": "String",
    "Default": "s3://bucket-name/folder-path-if-applicable/",
    "Description": "Remove this default value and enter your pre-created S3 Bucket url upto folder name. (Please include the trailing /. Example: https://s3.amazonaws.com/my-bucket/ should be input as s3://my-bucket/). It will be used for storing a copy of Dynamic DynamoDB configuration file."
    },
    "S3BucketRegion": {
    "Type": "String",
    "Default": "us-east-1",
    "Description": "Region the S3 bucket is located in. This is needed due to a limitation in the AWS CLI (https://github.com/aws/aws-cli/issues/564)"
    },
    "KeyPair": {
    "Default": "key-pair-name",
    "Description": "Remove this default value and enter the name of your EC2 keypair to use for SSH access",
    "Type": "String",
    "MinLength": "1",
    "MaxLength": "64",
    "AllowedPattern": "[-_ a-zA-Z0-9]*",
    "ConstraintDescription": "can contain only alphanumeric characters, spaces, dashes and underscores."
    },
    "InstanceType": {
    "Default": "t1.micro",
    "Description": "AWS EC2 instance type",
    "Type": "String"
    }
    },
    "Mappings": {
    "Region2AMI": {
    "us-east-1": {
    "64": "ami-fb8e9292"
    },
    "us-west-1": {
    "64": "ami-7aba833f"
    },
    "us-west-2": {
    "64": "ami-043a5034"
    },
    "eu-west-1": {
    "64": "ami-2918e35e"
    },
    "sa-east-1": {
    "64": "ami-215dff3c"
    },
    "ap-southeast-1": {
    "64": "ami-b40d5ee6"
    },
    "ap-southeast-2": {
    "64": "ami-3b4bd301"
    },
    "ap-northeast-1": {
    "64": "ami-c9562fc8"
    }
    }
    },
    "Resources": {
    "LaunchConfig": {
    "Type": "AWS::AutoScaling::LaunchConfiguration",
    "Properties": {
    "ImageId": {
    "Fn::FindInMap": [
    "Region2AMI",
    {
    "Ref": "AWS::Region"
    },
    "64"
    ]
    },
    "InstanceType": {
    "Ref": "InstanceType"
    },
    "KeyName": {
    "Ref": "KeyPair"
    },
    "SecurityGroups": [
    {
    "Ref": "SecurityGroup"
    }
    ],
    "IamInstanceProfile": {
    "Ref": "IamInstanceProfile"
    },
    "UserData": {
    "Fn::Base64": {
    "Fn::Join": [
    "\n",
    [
    "#!/usr/bin/env bash",
    "# Helper function",
    "log(){",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`",
    " echo \"$timenow: $1\" >> $INSTALLER_LOG_FILE_LOCATION",
    "}",
    "",
    "backup_file_locally(){",
    " FILE=$1",
    " BACKUP_FILE_NAME=$FILE.`date +\"%Y.%m.%d.%H.%M.%S.%N\".backup`",
    " mv $FILE \"$FILE.`date +\"%Y.%m.%d.%H.%M.%S.%N\".backup`\"",
    " log \"Backed up $FILE to $BACKUP_FILE_NAME\"",
    "}",
    "error_exit(){",
    " log \"$1\"",
    {
    "Fn::Join": [
    "",
    [
    "/opt/aws/bin/cfn-signal ",
    " -e 1 ",
    " -r \"$1\"",
    " '",
    {
    "Ref": "WaitHandle"
    },
    "'\n"
    ]
    ]
    },
    " exit 1",
    "}",
    "INSTALLER_LOG_FILE_LOCATION=/etc/dynamic-dynamodb/logs/installer.log",
    "mkdir -p /etc/dynamic-dynamodb/{scripts,logs} || error_exit 'Failed to create /etc/dynamic-dynamodb'",
    {
    "Fn::Join": [
    " ",
    [
    "/opt/aws/bin/cfn-init ",
    " --stack ",
    {
    "Ref": "AWS::StackId"
    },
    " --resource LaunchConfig ",
    " --region ",
    {
    "Ref": "AWS::Region"
    },
    " || error_exit 'Failed in AWS::CloudFormation::Init. Check logs at /var/log/cfn-init.log'"
    ]
    ]
    },
    "",
    "if [[ -f $INSTALLER_LOG_FILE_LOCATION ]]; then",
    " backup_file_locally $INSTALLER_LOG_FILE_LOCATION",
    "fi",
    "easy_install pip || error_exit 'Failed to install pip'",
    "log \"Installed pip\"",
    "echo \"dynamic-dynamodb>=1.7.0,<2.0.0\">/etc/dynamic-dynamodb/requirements.txt",
    "pip install -U -r /etc/dynamic-dynamodb/requirements.txt || error_exit 'Failed to install dynamic-dynamodb package from pip repository'",
    "log \"Installed dynamic-dynamodb\"",
    "",
    "",
    "mkdir -p ~/.aws || error_exit 'Failed to create /home/root/.aws'",
    "cp /home/ec2-user/.aws/config ~/.aws/config",
    {
    "Fn::Join": [
    "",
    [
    "echo \"aws s3 cp /etc/dynamic-dynamodb/dynamic-dynamodb.conf ",
    {
    "Ref": "S3Bucket"
    },
    "dynamic-dynamodb.conf --region ",
    {
    "Ref": "S3BucketRegion"
    },
    " || (echo 'Failed to upload /etc/dynamic-dynamodb/dynamic-dynamodb.conf to ",
    {
    "Ref": "S3Bucket"
    },
    "' ; exit 1)\">/etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh",
    " || error_exit 'Failed to create /etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh'"
    ]
    ]
    },
    {
    "Fn::Join": [
    " ",
    [
    "sh /etc/dynamic-dynamodb/scripts/init_config_file.sh /etc/dynamic-dynamodb/dynamic-dynamodb.conf",
    {
    "Ref": "S3Bucket"
    },
    " $INSTALLER_LOG_FILE_LOCATION",
    " || error_exit 'Failed to initialize config file'"
    ]
    ]
    },
    "service dynamic-dynamodb start || error_exit 'Failed to start dynamic-dynamodb service. Check /etc/dynamic-dynamodb/logs/service.log'",
    "log \"Dynamic dynamodb service started\"",
    {
    "Fn::Join": [
    "",
    [
    "# All is well so signal success\n",
    "/opt/aws/bin/cfn-signal -e 0 -r \"Dynamic DynamoDB instance setup complete\" '",
    {
    "Ref": "WaitHandle"
    },
    "'\n"
    ]
    ]
    }
    ]
    ]
    }
    }
    },
    "Metadata": {
    "AWS::CloudFormation::Init": {
    "config": {
    "files": {
    "/home/ec2-user/.aws/config": {
    "content": {
    "Fn::Join": [
    "",
    [
    "[default]\n",
    "region=",
    {
    "Ref": "AWS::Region"
    },
    "\n"
    ]
    ]
    },
    "mode": "000755",
    "owner": "root",
    "group": "root"
    },
    "/etc/init.d/dynamic-dynamodb": {
    "content": {
    "Fn::Join": [
    "\n",
    [
    "#!/usr/bin/env bash",
    "### BEGIN INIT INFO",
    "# Provides: dynamic-dynamodb",
    "# Required-Start: $remote_fs $syslog",
    "# Required-Stop: $remote_fs $syslog",
    "# Default-Start: 2 3 4 5",
    "# Default-Stop: 0 1 6",
    "# Short-Description: Automatic scaling for AWS DynamoDB",
    "# Description: Dynamic DynamoDB provides automatic scaling for AWS DynamoDB",
    "### END INIT INFO",
    "",
    "NAME=dynamicdynamodb",
    "DAEMON=/usr/bin/dynamic-dynamodb",
    "DRY_RUN=$2",
    "DAEMON_START_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --daemon start\"",
    "DAEMON_STOP_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --daemon stop\"",
    "SCRIPTNAME=/etc/init.d/$NAME",
    "SERVICE_LOG_FILE=/etc/dynamic-dynamodb/logs/service.log",
    "",
    "if [ \"$DRY_RUN\" == \"--dry-run\" ]; then",
    " DAEMON_START_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --dry-run --daemon start\"",
    " DAEMON_STOP_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --dry-run --daemon stop\"",
    "elif [ \"$2\" != \"\" ]; then",
    " echo \"$2\"",
    " echo \"Second parameter has to be --dry-run and is used only when running start/restart/force-reload commands\"",
    " exit 1",
    "fi",
    "",
    "# Exit if the package is not installed",
    "[ -x \"$DAEMON\" ] || exit 1",
    "",
    ". /etc/rc.d/init.d/functions",
    "",
    "log(){",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`",
    " echo \"$timenow: $1\"",
    " echo \"$timenow: $1\" >> $SERVICE_LOG_FILE",
    "}",
    "",
    "error_exit(){",
    " log \"$1\"",
    " exit 1",
    "}",
    "",
    "",
    "do_start()",
    "{",
    " if [ \"$DRY_RUN\" == \"--dry-run\" ]; then",
    " log \"do_start:Dry run mode, not uploading latest config file to S3\"",
    " else",
    " log \"do_start:Firstly, uploading latest config file to S3\"",
    " sh /etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh || error_exit \"Failed in uploading config file to s3 bucket\"",
    " fi",
    " log \"do_start:Starting $NAME\"",
    " daemon $DAEMON $DAEMON_START_ARGS || error_exit \"Failed in starting $NAME service\"",
    "}",
    "",
    "do_stop()",
    "{",
    " log \"do_stop:Stopping $NAME\"",
    " daemon $DAEMON $DAEMON_STOP_ARGS || error_exit \"Failed in stopping $NAME service\"",
    "}",
    "",
    "",
    "case \"$1\" in",
    " start)",
    " do_start",
    " ;;",
    " stop)",
    " do_stop",
    " ;;",
    " status)",
    " status \"$DAEMON\" \"$NAME\" && exit 0 || exit $?",
    " ;;",
    " restart|force-reload)",
    " do_stop",
    " do_start",
    " #*)",
    " ;;",
    " *)",
    " echo \"Usage: $SCRIPTNAME {start|stop|status|restart|force-reload}\" >&2",
    " exit 3",
    " ;;",
    "esac",
    "",
    ":"
    ]
    ]
    },
    "mode": "000755",
    "owner": "root",
    "group": "root"
    },
    "/etc/dynamic-dynamodb/scripts/init_config_file.sh": {
    "content": {
    "Fn::Join": [
    "",
    [
    "#!/usr/bin/env bash\n",
    "CONFIG_FILE_LOCAL_LOCATION=$1\n",
    "S3_BUCKET=$2\n",
    "INSTALLER_LOG_FILE_LOCATION=$3\n",
    "CONFIG_FILE_S3_LOCATION=\"$S3_BUCKET\"dynamic-dynamodb.conf\n",
    "DOES_CONFIG_FILE_EXIST_ON_S3=0\n",
    "DOES_CONFIG_FILE_EXIST_ON_LOCALLY=0\n\n",
    "log(){\n",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`\n",
    " echo \"$timenow: $1\" >> $INSTALLER_LOG_FILE_LOCATION\n",
    "}\n\n",
    "error_exit(){\n",
    " log \"$1\"\n",
    " exit 1\n",
    "}\n\n",
    "backup_file_locally(){\n",
    " FILE=$1\n",
    " BACKUP_FILE_NAME=$FILE.`date +\\\"%Y.%m.%d.%H.%M.%S.%N\\\".backup`\n",
    " mv $FILE \"$FILE.`date +\\\"%Y.%m.%d.%H.%M.%S.%N\\\".backup`\" || error_exit \"Failed in creating backup file $BACKUP_FILE_NAME\"\n",
    " log \"Backed up $FILE to $BACKUP_FILE_NAME\"\n",
    "}\n\n",
    "generate_new_config_file(){\n",
    " log \"Loading an example config file to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    " cp /etc/dynamic-dynamodb/example-dynamic-dynamodb.conf $CONFIG_FILE_LOCAL_LOCATION\n",
    " sed -i 's/region:\\ us-east-1/region:\\ ",
    {
    "Ref": "AWS::Region"
    },
    "/g' /etc/dynamic-dynamodb/example-dynamic-dynamodb.conf\n",
    " log \"Loaded example configuration to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    "}\n\n",
    "download_from_s3(){\n",
    " aws s3 cp $CONFIG_FILE_S3_LOCATION $CONFIG_FILE_LOCAL_LOCATION --region ",
    {
    "Ref": "S3BucketRegion"
    },
    " || error_exit \"Failed to download config file from $CONFIG_FILE_S3_LOCATION to $CONFIG_FILE_S3_LOCATION even though it existed on S3\"\n",
    " log \"Downloaded config file from $CONFIG_FILE_S3_LOCATION to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    "}\n\n",
    "aws s3 cp $CONFIG_FILE_S3_LOCATION . --region ",
    {
    "Ref": "S3BucketRegion"
    },
    " >/dev/null 2>&1\n",
    "if [[ \"$?\" -eq 0 ]]; then\n",
    " DOES_CONFIG_FILE_EXIST_ON_S3=1\n",
    "fi\n\n",
    "if [[ -f $CONFIG_FILE_LOCAL_LOCATION ]]; then\n",
    " DOES_CONFIG_FILE_EXIST_ON_LOCALLY=1\n",
    "fi\n\n",
    "if [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 0 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 0 ]; then\n",
    " generate_new_config_file\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 0 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 1 ]; then\n",
    " log \"Config file exists locally and not on $CONFIG_FILE_S3_LOCATION, continuing to use the file\";\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 1 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 0 ]; then\n",
    " download_from_s3\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 1 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 1 ]; then\n",
    " backup_file_locally $CONFIG_FILE_LOCAL_LOCATION\n",
    " download_from_s3\n",
    "fi\n"
    ]
    ]
    },
    "mode": "000755",
    "owner": "root",
    "group": "root"
    },
    "/etc/dynamic-dynamodb/example-dynamic-dynamodb.conf": {
    "source": "https://raw.github.com/sebdah/dynamic-dynamodb/master/example-dynamic-dynamodb.conf",
    "mode": "000644",
    "owner": "root",
    "group": "root"
    }
    }
    }
    }
    }
    },
    "AutoScalingGroup": {
    "Type": "AWS::AutoScaling::AutoScalingGroup",
    "Properties": {
    "AvailabilityZones": {
    "Fn::GetAZs": ""
    },
    "Cooldown": 300,
    "LaunchConfigurationName": {
    "Ref": "LaunchConfig"
    },
    "MaxSize": 1,
    "MinSize": 1,
    "Tags": [
    {
    "Key": "Name",
    "Value": "dynamic-dynamodb",
    "PropagateAtLaunch": "true"
    }
    ]
    }
    },
    "IamRole": {
    "Type": "AWS::IAM::Role",
    "Properties": {
    "AssumeRolePolicyDocument": {
    "Version": "2012-10-17",
    "Statement": [
    {
    "Effect": "Allow",
    "Principal": {
    "Service": [
    "ec2.amazonaws.com"
    ]
    },
    "Action": [
    "sts:AssumeRole"
    ]
    }
    ]
    },
    "Path": "/",
    "Policies": [
    {
    "PolicyName": "root",
    "PolicyDocument": {
    "Version": "2012-10-17",
    "Statement": [
    {
    "Effect": "Allow",
    "Action": [
    "dynamodb:DescribeTable",
    "dynamodb:ListTables",
    "dynamodb:UpdateTable",
    "cloudwatch:GetMetricStatistics",
    "s3:PutObject",
    "s3:GetObject"
    ],
    "Resource": [
    "*"
    ]
    },
    {
    "Effect": "Allow",
    "Action": [
    "sns:Publish"
    ],
    "Resource": [
    "arn:aws:sns:*::dynamic-dynamodb"
    ]
    }
    ]
    }
    }
    ]
    }
    },
    "IamInstanceProfile": {
    "Type": "AWS::IAM::InstanceProfile",
    "Properties": {
    "Path": "/",
    "Roles": [
    {
    "Ref": "IamRole"
    }
    ]
    }
    },
    "SecurityGroup": {
    "Type": "AWS::EC2::SecurityGroup",
    "Properties": {
    "GroupDescription": "Allow access to MyInstance",
    "SecurityGroupIngress": [
    {
    "IpProtocol": "tcp",
    "FromPort": 22,
    "ToPort": 22,
    "CidrIp": "0.0.0.0/0"
    }
    ]
    }
    },
    "WaitHandle": {
    "Type": "AWS::CloudFormation::WaitConditionHandle"
    },
    "WaitCondition": {
    "Type": "AWS::CloudFormation::WaitCondition",
    "DependsOn": "AutoScalingGroup",
    "Properties": {
    "Handle": {
    "Ref": "WaitHandle"
    },
    "Timeout": "600"
    }
    }
    },
    "Outputs": {
    "URL": {
    "Description": "EC2 instance",
    "Value": "You can find your EC2 instance at https://console.aws.amazon.com/ec2/v2/home?#Instances:search=dynamic-dynamodb"
    }
    }
    "AWSTemplateFormatVersion":"2010-09-09",
    "Description":"This is a sample CloudFormation template for deploying Dynamic DynamoDB. This package will be installed from the Python Package Index repository. For more information, see http://dynamic-dynamodb.readthedocs.org.",
    "Parameters":{
    "S3Bucket":{
    "Type":"String",
    "Default":"s3://bucket-name/folder-path-if-applicable/",
    "Description":"Remove this default value and enter your pre-created S3 Bucket url upto folder name. (Please include the trailing /. Example: https://s3.amazonaws.com/my-bucket/ should be input as s3://my-bucket/). It will be used for storing a copy of Dynamic DynamoDB configuration file."
    },
    "S3BucketRegion":{
    "Type":"String",
    "Default":"us-east-1",
    "Description":"Region the S3 bucket is located in. This is needed due to a limitation in the AWS CLI (https://github.com/aws/aws-cli/issues/564)"
    },
    "KeyPair":{
    "Default":"key-pair-name",
    "Description":"Remove this default value and enter the name of your EC2 keypair to use for SSH access",
    "Type":"String",
    "MinLength":"1",
    "MaxLength":"64",
    "AllowedPattern":"[-_ a-zA-Z0-9]*",
    "ConstraintDescription":"can contain only alphanumeric characters, spaces, dashes and underscores."
    },
    "InstanceType":{
    "Default":"t1.micro",
    "Description":"AWS EC2 instance type",
    "Type":"String"
    }
    },
    "Mappings":{
    "Region2AMI":{
    "us-east-1":{
    "64":"ami-fb8e9292"
    },
    "us-west-1":{
    "64":"ami-7aba833f"
    },
    "us-west-2":{
    "64":"ami-043a5034"
    },
    "eu-west-1":{
    "64":"ami-2918e35e"
    },
    "sa-east-1":{
    "64":"ami-215dff3c"
    },
    "ap-southeast-1":{
    "64":"ami-b40d5ee6"
    },
    "ap-southeast-2":{
    "64":"ami-3b4bd301"
    },
    "ap-northeast-1":{
    "64":"ami-c9562fc8"
    }
    }
    },
    "Resources":{
    "LaunchConfig":{
    "Type":"AWS::AutoScaling::LaunchConfiguration",
    "Properties":{
    "ImageId":{
    "Fn::FindInMap":[
    "Region2AMI",
    {
    "Ref":"AWS::Region"
    },
    "64"
    ]
    },
    "InstanceType":{
    "Ref":"InstanceType"
    },
    "KeyName":{
    "Ref":"KeyPair"
    },
    "SecurityGroups":[
    {
    "Ref":"SecurityGroup"
    }
    ],
    "IamInstanceProfile":{
    "Ref":"IamInstanceProfile"
    },
    "UserData":{
    "Fn::Base64":{
    "Fn::Join":[
    "\n",
    [
    "#!/usr/bin/env bash",
    "# Helper function",
    "log(){",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`",
    " echo \"$timenow: $1\" >> $INSTALLER_LOG_FILE_LOCATION",
    "}",
    "",
    "backup_file_locally(){",
    " FILE=$1",
    " BACKUP_FILE_NAME=$FILE.`date +\"%Y.%m.%d.%H.%M.%S.%N\".backup`",
    " mv $FILE \"$FILE.`date +\"%Y.%m.%d.%H.%M.%S.%N\".backup`\"",
    " log \"Backed up $FILE to $BACKUP_FILE_NAME\"",
    "}",
    "error_exit(){",
    " log \"$1\"",
    {
    "Fn::Join":[
    "",
    [
    "/opt/aws/bin/cfn-signal ",
    " -e 1 ",
    " -r \"$1\"",
    " '",
    {
    "Ref":"WaitHandle"
    },
    "'\n"
    ]
    ]
    },
    " exit 1",
    "}",
    "INSTALLER_LOG_FILE_LOCATION=/etc/dynamic-dynamodb/logs/installer.log",
    "mkdir -p /etc/dynamic-dynamodb/{scripts,logs} || error_exit 'Failed to create /etc/dynamic-dynamodb'",
    {
    "Fn::Join":[
    " ",
    [
    "/opt/aws/bin/cfn-init ",
    " --stack ",
    {
    "Ref":"AWS::StackId"
    },
    " --resource LaunchConfig ",
    " --region ",
    {
    "Ref":"AWS::Region"
    },
    " || error_exit 'Failed in AWS::CloudFormation::Init. Check logs at /var/log/cfn-init.log'"
    ]
    ]
    },
    "",
    "if [[ -f $INSTALLER_LOG_FILE_LOCATION ]]; then",
    " backup_file_locally $INSTALLER_LOG_FILE_LOCATION",
    "fi",
    "easy_install pip || error_exit 'Failed to install pip'",
    "log \"Installed pip\"",
    "echo \"dynamic-dynamodb>=1.7.0,<2.0.0\">/etc/dynamic-dynamodb/requirements.txt",
    "pip install -U -r /etc/dynamic-dynamodb/requirements.txt || error_exit 'Failed to install dynamic-dynamodb package from pip repository'",
    "log \"Installed dynamic-dynamodb\"",
    "",
    "",
    "mkdir -p ~/.aws || error_exit 'Failed to create /home/root/.aws'",
    "cp /home/ec2-user/.aws/config ~/.aws/config",
    {
    "Fn::Join":[
    "",
    [
    "echo \"aws s3 cp /etc/dynamic-dynamodb/dynamic-dynamodb.conf ",
    {
    "Ref":"S3Bucket"
    },
    "dynamic-dynamodb.conf --region ",
    {
    "Ref":"S3BucketRegion"
    },
    " || (echo 'Failed to upload /etc/dynamic-dynamodb/dynamic-dynamodb.conf to ",
    {
    "Ref":"S3Bucket"
    },
    "' ; exit 1)\">/etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh",
    " || error_exit 'Failed to create /etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh'"
    ]
    ]
    },
    {
    "Fn::Join":[
    " ",
    [
    "sh /etc/dynamic-dynamodb/scripts/init_config_file.sh /etc/dynamic-dynamodb/dynamic-dynamodb.conf",
    {
    "Ref":"S3Bucket"
    },
    " $INSTALLER_LOG_FILE_LOCATION",
    " || error_exit 'Failed to initialize config file'"
    ]
    ]
    },
    "service dynamic-dynamodb start || error_exit 'Failed to start dynamic-dynamodb service. Check /etc/dynamic-dynamodb/logs/service.log'",
    "log \"Dynamic dynamodb service started\"",
    {
    "Fn::Join":[
    "",
    [
    "# All is well so signal success\n",
    "/opt/aws/bin/cfn-signal -e 0 -r \"Dynamic DynamoDB instance setup complete\" '",
    {
    "Ref":"WaitHandle"
    },
    "'\n"
    ]
    ]
    }
    ]
    ]
    }
    }
    },
    "Metadata":{
    "AWS::CloudFormation::Init":{
    "config":{
    "files":{
    "/home/ec2-user/.aws/config":{
    "content":{
    "Fn::Join":[
    "",
    [
    "[default]\n",
    "region=",
    {
    "Ref":"AWS::Region"
    },
    "\n"
    ]
    ]
    },
    "mode":"000755",
    "owner":"root",
    "group":"root"
    },
    "/etc/init.d/dynamic-dynamodb":{
    "content":{
    "Fn::Join":[
    "\n",
    [
    "#!/usr/bin/env bash",
    "### BEGIN INIT INFO",
    "# Provides: dynamic-dynamodb",
    "# Required-Start: $remote_fs $syslog",
    "# Required-Stop: $remote_fs $syslog",
    "# Default-Start: 2 3 4 5",
    "# Default-Stop: 0 1 6",
    "# Short-Description: Automatic scaling for AWS DynamoDB",
    "# Description: Dynamic DynamoDB provides automatic scaling for AWS DynamoDB",
    "### END INIT INFO",
    "",
    "NAME=dynamicdynamodb",
    "DAEMON=/usr/bin/dynamic-dynamodb",
    "DRY_RUN=$2",
    "DAEMON_START_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --daemon start\"",
    "DAEMON_STOP_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --daemon stop\"",
    "SCRIPTNAME=/etc/init.d/$NAME",
    "SERVICE_LOG_FILE=/etc/dynamic-dynamodb/logs/service.log",
    "",
    "if [ \"$DRY_RUN\" == \"--dry-run\" ]; then",
    " DAEMON_START_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --dry-run --daemon start\"",
    " DAEMON_STOP_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --dry-run --daemon stop\"",
    "elif [ \"$2\" != \"\" ]; then",
    " echo \"$2\"",
    " echo \"Second parameter has to be --dry-run and is used only when running start/restart/force-reload commands\"",
    " exit 1",
    "fi",
    "",
    "# Exit if the package is not installed",
    "[ -x \"$DAEMON\" ] || exit 1",
    "",
    ". /etc/rc.d/init.d/functions",
    "",
    "log(){",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`",
    " echo \"$timenow: $1\"",
    " echo \"$timenow: $1\" >> $SERVICE_LOG_FILE",
    "}",
    "",
    "error_exit(){",
    " log \"$1\"",
    " exit 1",
    "}",
    "",
    "",
    "do_start()",
    "{",
    " if [ \"$DRY_RUN\" == \"--dry-run\" ]; then",
    " log \"do_start:Dry run mode, not uploading latest config file to S3\"",
    " else",
    " log \"do_start:Firstly, uploading latest config file to S3\"",
    " sh /etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh || error_exit \"Failed in uploading config file to s3 bucket\"",
    " fi",
    " log \"do_start:Starting $NAME\"",
    " daemon $DAEMON $DAEMON_START_ARGS || error_exit \"Failed in starting $NAME service\"",
    "}",
    "",
    "do_stop()",
    "{",
    " log \"do_stop:Stopping $NAME\"",
    " daemon $DAEMON $DAEMON_STOP_ARGS || error_exit \"Failed in stopping $NAME service\"",
    "}",
    "",
    "",
    "case \"$1\" in",
    " start)",
    " do_start",
    " ;;",
    " stop)",
    " do_stop",
    " ;;",
    " status)",
    " status \"$DAEMON\" \"$NAME\" && exit 0 || exit $?",
    " ;;",
    " restart|force-reload)",
    " do_stop",
    " do_start",
    " #*)",
    " ;;",
    " *)",
    " echo \"Usage: $SCRIPTNAME {start|stop|status|restart|force-reload}\" >&2",
    " exit 3",
    " ;;",
    "esac",
    "",
    ":"
    ]
    ]
    },
    "mode":"000755",
    "owner":"root",
    "group":"root"
    },
    "/etc/dynamic-dynamodb/scripts/init_config_file.sh":{
    "content":{
    "Fn::Join":[
    "",
    [
    "#!/usr/bin/env bash\n",
    "CONFIG_FILE_LOCAL_LOCATION=$1\n",
    "S3_BUCKET=$2\n",
    "INSTALLER_LOG_FILE_LOCATION=$3\n",
    "CONFIG_FILE_S3_LOCATION=\"$S3_BUCKET\"dynamic-dynamodb.conf\n",
    "DOES_CONFIG_FILE_EXIST_ON_S3=0\n",
    "DOES_CONFIG_FILE_EXIST_ON_LOCALLY=0\n\n",
    "log(){\n",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`\n",
    " echo \"$timenow: $1\" >> $INSTALLER_LOG_FILE_LOCATION\n",
    "}\n\n",
    "error_exit(){\n",
    " log \"$1\"\n",
    " exit 1\n",
    "}\n\n",
    "backup_file_locally(){\n",
    " FILE=$1\n",
    " BACKUP_FILE_NAME=$FILE.`date +\\\"%Y.%m.%d.%H.%M.%S.%N\\\".backup`\n",
    " mv $FILE \"$FILE.`date +\\\"%Y.%m.%d.%H.%M.%S.%N\\\".backup`\" || error_exit \"Failed in creating backup file $BACKUP_FILE_NAME\"\n",
    " log \"Backed up $FILE to $BACKUP_FILE_NAME\"\n",
    "}\n\n",
    "generate_new_config_file(){\n",
    " log \"Loading an example config file to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    " cp /etc/dynamic-dynamodb/example-dynamic-dynamodb.conf $CONFIG_FILE_LOCAL_LOCATION\n",
    " sed -i 's/region:\\ us-east-1/region:\\ ",
    {
    "Ref":"AWS::Region"
    },
    "/g' /etc/dynamic-dynamodb/example-dynamic-dynamodb.conf\n",
    " log \"Loaded example configuration to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    "}\n\n",
    "download_from_s3(){\n",
    " aws s3 cp $CONFIG_FILE_S3_LOCATION $CONFIG_FILE_LOCAL_LOCATION --region ",
    {
    "Ref":"S3BucketRegion"
    },
    " || error_exit \"Failed to download config file from $CONFIG_FILE_S3_LOCATION to $CONFIG_FILE_S3_LOCATION even though it existed on S3\"\n",
    " log \"Downloaded config file from $CONFIG_FILE_S3_LOCATION to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    "}\n\n",
    "aws s3 cp $CONFIG_FILE_S3_LOCATION . --region ",
    {
    "Ref":"S3BucketRegion"
    },
    " >/dev/null 2>&1\n",
    "if [[ \"$?\" -eq 0 ]]; then\n",
    " DOES_CONFIG_FILE_EXIST_ON_S3=1\n",
    "fi\n\n",
    "if [[ -f $CONFIG_FILE_LOCAL_LOCATION ]]; then\n",
    " DOES_CONFIG_FILE_EXIST_ON_LOCALLY=1\n",
    "fi\n\n",
    "if [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 0 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 0 ]; then\n",
    " generate_new_config_file\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 0 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 1 ]; then\n",
    " log \"Config file exists locally and not on $CONFIG_FILE_S3_LOCATION, continuing to use the file\";\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 1 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 0 ]; then\n",
    " download_from_s3\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 1 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 1 ]; then\n",
    " backup_file_locally $CONFIG_FILE_LOCAL_LOCATION\n",
    " download_from_s3\n",
    "fi\n"
    ]
    ]
    },
    "mode":"000755",
    "owner":"root",
    "group":"root"
    },
    "/etc/dynamic-dynamodb/example-dynamic-dynamodb.conf":{
    "source":"https://raw.github.com/sebdah/dynamic-dynamodb/master/example-dynamic-dynamodb.conf",
    "mode":"000644",
    "owner":"root",
    "group":"root"
    }
    }
    }
    }
    }
    },
    "AutoScalingGroup":{
    "Type":"AWS::AutoScaling::AutoScalingGroup",
    "Properties":{
    "AvailabilityZones":{
    "Fn::GetAZs":""
    },
    "Cooldown":300,
    "LaunchConfigurationName":{
    "Ref":"LaunchConfig"
    },
    "MaxSize":1,
    "MinSize":1,
    "Tags":[
    {
    "Key":"Name",
    "Value":"dynamic-dynamodb",
    "PropagateAtLaunch":"true"
    }
    ]
    }
    },
    "IamRole":{
    "Type":"AWS::IAM::Role",
    "Properties":{
    "AssumeRolePolicyDocument":{
    "Version":"2012-10-17",
    "Statement":[
    {
    "Effect":"Allow",
    "Principal":{
    "Service":[
    "ec2.amazonaws.com"
    ]
    },
    "Action":[
    "sts:AssumeRole"
    ]
    }
    ]
    },
    "Path":"/",
    "Policies":[
    {
    "PolicyName":"root",
    "PolicyDocument":{
    "Version":"2012-10-17",
    "Statement":[
    {
    "Effect":"Allow",
    "Action":[
    "dynamodb:DescribeTable",
    "dynamodb:ListTables",
    "dynamodb:UpdateTable",
    "cloudwatch:GetMetricStatistics",
    "s3:PutObject",
    "s3:GetObject"
    ],
    "Resource":[
    "*"
    ]
    },
    {
    "Effect":"Allow",
    "Action":[
    "sns:Publish"
    ],
    "Resource":[
    "arn:aws:sns:*::dynamic-dynamodb"
    ]
    }
    ]
    }
    }
    ]
    }
    },
    "IamInstanceProfile":{
    "Type":"AWS::IAM::InstanceProfile",
    "Properties":{
    "Path":"/",
    "Roles":[
    {
    "Ref":"IamRole"
    }
    ]
    }
    },
    "SecurityGroup":{
    "Type":"AWS::EC2::SecurityGroup",
    "Properties":{
    "GroupDescription":"Allow access to MyInstance",
    "SecurityGroupIngress":[
    {
    "IpProtocol":"tcp",
    "FromPort":22,
    "ToPort":22,
    "CidrIp":"0.0.0.0/0"
    }
    ]
    }
    },
    "WaitHandle":{
    "Type":"AWS::CloudFormation::WaitConditionHandle"
    },
    "WaitCondition":{
    "Type":"AWS::CloudFormation::WaitCondition",
    "DependsOn":"AutoScalingGroup",
    "Properties":{
    "Handle":{
    "Ref":"WaitHandle"
    },
    "Timeout":"600"
    }
    }
    },
    "Outputs":{
    "URL":{
    "Description":"EC2 instance",
    "Value":"You can find your EC2 instance at https://console.aws.amazon.com/ec2/v2/home?#Instances:search=dynamic-dynamodb"
    }
    }
    }
  3. sebdah created this gist Apr 10, 2015.
    533 changes: 533 additions & 0 deletions dynamodb-hack.json
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,533 @@
    {
    "AWSTemplateFormatVersion": "2010-09-09",
    "Description": "This is a sample CloudFormation template for deploying Dynamic DynamoDB. This package will be installed from the Python Package Index repository. For more information, see http://dynamic-dynamodb.readthedocs.org.",
    "Parameters": {
    "S3Bucket": {
    "Type": "String",
    "Default": "s3://bucket-name/folder-path-if-applicable/",
    "Description": "Remove this default value and enter your pre-created S3 Bucket url upto folder name. (Please include the trailing /. Example: https://s3.amazonaws.com/my-bucket/ should be input as s3://my-bucket/). It will be used for storing a copy of Dynamic DynamoDB configuration file."
    },
    "S3BucketRegion": {
    "Type": "String",
    "Default": "us-east-1",
    "Description": "Region the S3 bucket is located in. This is needed due to a limitation in the AWS CLI (https://github.com/aws/aws-cli/issues/564)"
    },
    "KeyPair": {
    "Default": "key-pair-name",
    "Description": "Remove this default value and enter the name of your EC2 keypair to use for SSH access",
    "Type": "String",
    "MinLength": "1",
    "MaxLength": "64",
    "AllowedPattern": "[-_ a-zA-Z0-9]*",
    "ConstraintDescription": "can contain only alphanumeric characters, spaces, dashes and underscores."
    },
    "InstanceType": {
    "Default": "t1.micro",
    "Description": "AWS EC2 instance type",
    "Type": "String"
    }
    },
    "Mappings": {
    "Region2AMI": {
    "us-east-1": {
    "64": "ami-fb8e9292"
    },
    "us-west-1": {
    "64": "ami-7aba833f"
    },
    "us-west-2": {
    "64": "ami-043a5034"
    },
    "eu-west-1": {
    "64": "ami-2918e35e"
    },
    "sa-east-1": {
    "64": "ami-215dff3c"
    },
    "ap-southeast-1": {
    "64": "ami-b40d5ee6"
    },
    "ap-southeast-2": {
    "64": "ami-3b4bd301"
    },
    "ap-northeast-1": {
    "64": "ami-c9562fc8"
    }
    }
    },
    "Resources": {
    "LaunchConfig": {
    "Type": "AWS::AutoScaling::LaunchConfiguration",
    "Properties": {
    "ImageId": {
    "Fn::FindInMap": [
    "Region2AMI",
    {
    "Ref": "AWS::Region"
    },
    "64"
    ]
    },
    "InstanceType": {
    "Ref": "InstanceType"
    },
    "KeyName": {
    "Ref": "KeyPair"
    },
    "SecurityGroups": [
    {
    "Ref": "SecurityGroup"
    }
    ],
    "IamInstanceProfile": {
    "Ref": "IamInstanceProfile"
    },
    "UserData": {
    "Fn::Base64": {
    "Fn::Join": [
    "\n",
    [
    "#!/usr/bin/env bash",
    "# Helper function",
    "log(){",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`",
    " echo \"$timenow: $1\" >> $INSTALLER_LOG_FILE_LOCATION",
    "}",
    "",
    "backup_file_locally(){",
    " FILE=$1",
    " BACKUP_FILE_NAME=$FILE.`date +\"%Y.%m.%d.%H.%M.%S.%N\".backup`",
    " mv $FILE \"$FILE.`date +\"%Y.%m.%d.%H.%M.%S.%N\".backup`\"",
    " log \"Backed up $FILE to $BACKUP_FILE_NAME\"",
    "}",
    "error_exit(){",
    " log \"$1\"",
    {
    "Fn::Join": [
    "",
    [
    "/opt/aws/bin/cfn-signal ",
    " -e 1 ",
    " -r \"$1\"",
    " '",
    {
    "Ref": "WaitHandle"
    },
    "'\n"
    ]
    ]
    },
    " exit 1",
    "}",
    "INSTALLER_LOG_FILE_LOCATION=/etc/dynamic-dynamodb/logs/installer.log",
    "mkdir -p /etc/dynamic-dynamodb/{scripts,logs} || error_exit 'Failed to create /etc/dynamic-dynamodb'",
    {
    "Fn::Join": [
    " ",
    [
    "/opt/aws/bin/cfn-init ",
    " --stack ",
    {
    "Ref": "AWS::StackId"
    },
    " --resource LaunchConfig ",
    " --region ",
    {
    "Ref": "AWS::Region"
    },
    " || error_exit 'Failed in AWS::CloudFormation::Init. Check logs at /var/log/cfn-init.log'"
    ]
    ]
    },
    "",
    "if [[ -f $INSTALLER_LOG_FILE_LOCATION ]]; then",
    " backup_file_locally $INSTALLER_LOG_FILE_LOCATION",
    "fi",
    "easy_install pip || error_exit 'Failed to install pip'",
    "log \"Installed pip\"",
    "echo \"dynamic-dynamodb>=1.7.0,<2.0.0\">/etc/dynamic-dynamodb/requirements.txt",
    "pip install -U -r /etc/dynamic-dynamodb/requirements.txt || error_exit 'Failed to install dynamic-dynamodb package from pip repository'",
    "log \"Installed dynamic-dynamodb\"",
    "",
    "",
    "mkdir -p ~/.aws || error_exit 'Failed to create /home/root/.aws'",
    "cp /home/ec2-user/.aws/config ~/.aws/config",
    {
    "Fn::Join": [
    "",
    [
    "echo \"aws s3 cp /etc/dynamic-dynamodb/dynamic-dynamodb.conf ",
    {
    "Ref": "S3Bucket"
    },
    "dynamic-dynamodb.conf --region ",
    {
    "Ref": "S3BucketRegion"
    },
    " || (echo 'Failed to upload /etc/dynamic-dynamodb/dynamic-dynamodb.conf to ",
    {
    "Ref": "S3Bucket"
    },
    "' ; exit 1)\">/etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh",
    " || error_exit 'Failed to create /etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh'"
    ]
    ]
    },
    {
    "Fn::Join": [
    " ",
    [
    "sh /etc/dynamic-dynamodb/scripts/init_config_file.sh /etc/dynamic-dynamodb/dynamic-dynamodb.conf",
    {
    "Ref": "S3Bucket"
    },
    " $INSTALLER_LOG_FILE_LOCATION",
    " || error_exit 'Failed to initialize config file'"
    ]
    ]
    },
    "service dynamic-dynamodb start || error_exit 'Failed to start dynamic-dynamodb service. Check /etc/dynamic-dynamodb/logs/service.log'",
    "log \"Dynamic dynamodb service started\"",
    {
    "Fn::Join": [
    "",
    [
    "# All is well so signal success\n",
    "/opt/aws/bin/cfn-signal -e 0 -r \"Dynamic DynamoDB instance setup complete\" '",
    {
    "Ref": "WaitHandle"
    },
    "'\n"
    ]
    ]
    }
    ]
    ]
    }
    }
    },
    "Metadata": {
    "AWS::CloudFormation::Init": {
    "config": {
    "files": {
    "/home/ec2-user/.aws/config": {
    "content": {
    "Fn::Join": [
    "",
    [
    "[default]\n",
    "region=",
    {
    "Ref": "AWS::Region"
    },
    "\n"
    ]
    ]
    },
    "mode": "000755",
    "owner": "root",
    "group": "root"
    },
    "/etc/init.d/dynamic-dynamodb": {
    "content": {
    "Fn::Join": [
    "\n",
    [
    "#!/usr/bin/env bash",
    "### BEGIN INIT INFO",
    "# Provides: dynamic-dynamodb",
    "# Required-Start: $remote_fs $syslog",
    "# Required-Stop: $remote_fs $syslog",
    "# Default-Start: 2 3 4 5",
    "# Default-Stop: 0 1 6",
    "# Short-Description: Automatic scaling for AWS DynamoDB",
    "# Description: Dynamic DynamoDB provides automatic scaling for AWS DynamoDB",
    "### END INIT INFO",
    "",
    "NAME=dynamicdynamodb",
    "DAEMON=/usr/bin/dynamic-dynamodb",
    "DRY_RUN=$2",
    "DAEMON_START_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --daemon start\"",
    "DAEMON_STOP_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --daemon stop\"",
    "SCRIPTNAME=/etc/init.d/$NAME",
    "SERVICE_LOG_FILE=/etc/dynamic-dynamodb/logs/service.log",
    "",
    "if [ \"$DRY_RUN\" == \"--dry-run\" ]; then",
    " DAEMON_START_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --dry-run --daemon start\"",
    " DAEMON_STOP_ARGS=\"--config /etc/dynamic-dynamodb/dynamic-dynamodb.conf --dry-run --daemon stop\"",
    "elif [ \"$2\" != \"\" ]; then",
    " echo \"$2\"",
    " echo \"Second parameter has to be --dry-run and is used only when running start/restart/force-reload commands\"",
    " exit 1",
    "fi",
    "",
    "# Exit if the package is not installed",
    "[ -x \"$DAEMON\" ] || exit 1",
    "",
    ". /etc/rc.d/init.d/functions",
    "",
    "log(){",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`",
    " echo \"$timenow: $1\"",
    " echo \"$timenow: $1\" >> $SERVICE_LOG_FILE",
    "}",
    "",
    "error_exit(){",
    " log \"$1\"",
    " exit 1",
    "}",
    "",
    "",
    "do_start()",
    "{",
    " if [ \"$DRY_RUN\" == \"--dry-run\" ]; then",
    " log \"do_start:Dry run mode, not uploading latest config file to S3\"",
    " else",
    " log \"do_start:Firstly, uploading latest config file to S3\"",
    " sh /etc/dynamic-dynamodb/scripts/upload-config-to-s3.sh || error_exit \"Failed in uploading config file to s3 bucket\"",
    " fi",
    " log \"do_start:Starting $NAME\"",
    " daemon $DAEMON $DAEMON_START_ARGS || error_exit \"Failed in starting $NAME service\"",
    "}",
    "",
    "do_stop()",
    "{",
    " log \"do_stop:Stopping $NAME\"",
    " daemon $DAEMON $DAEMON_STOP_ARGS || error_exit \"Failed in stopping $NAME service\"",
    "}",
    "",
    "",
    "case \"$1\" in",
    " start)",
    " do_start",
    " ;;",
    " stop)",
    " do_stop",
    " ;;",
    " status)",
    " status \"$DAEMON\" \"$NAME\" && exit 0 || exit $?",
    " ;;",
    " restart|force-reload)",
    " do_stop",
    " do_start",
    " #*)",
    " ;;",
    " *)",
    " echo \"Usage: $SCRIPTNAME {start|stop|status|restart|force-reload}\" >&2",
    " exit 3",
    " ;;",
    "esac",
    "",
    ":"
    ]
    ]
    },
    "mode": "000755",
    "owner": "root",
    "group": "root"
    },
    "/etc/dynamic-dynamodb/scripts/init_config_file.sh": {
    "content": {
    "Fn::Join": [
    "",
    [
    "#!/usr/bin/env bash\n",
    "CONFIG_FILE_LOCAL_LOCATION=$1\n",
    "S3_BUCKET=$2\n",
    "INSTALLER_LOG_FILE_LOCATION=$3\n",
    "CONFIG_FILE_S3_LOCATION=\"$S3_BUCKET\"dynamic-dynamodb.conf\n",
    "DOES_CONFIG_FILE_EXIST_ON_S3=0\n",
    "DOES_CONFIG_FILE_EXIST_ON_LOCALLY=0\n\n",
    "log(){\n",
    " timenow=`date +%Y-%m-%dT%H:%M:%S.%N`\n",
    " echo \"$timenow: $1\" >> $INSTALLER_LOG_FILE_LOCATION\n",
    "}\n\n",
    "error_exit(){\n",
    " log \"$1\"\n",
    " exit 1\n",
    "}\n\n",
    "backup_file_locally(){\n",
    " FILE=$1\n",
    " BACKUP_FILE_NAME=$FILE.`date +\\\"%Y.%m.%d.%H.%M.%S.%N\\\".backup`\n",
    " mv $FILE \"$FILE.`date +\\\"%Y.%m.%d.%H.%M.%S.%N\\\".backup`\" || error_exit \"Failed in creating backup file $BACKUP_FILE_NAME\"\n",
    " log \"Backed up $FILE to $BACKUP_FILE_NAME\"\n",
    "}\n\n",
    "generate_new_config_file(){\n",
    " log \"Loading an example config file to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    " cp /etc/dynamic-dynamodb/example-dynamic-dynamodb.conf $CONFIG_FILE_LOCAL_LOCATION\n",
    " sed -i 's/region:\\ us-east-1/region:\\ ",
    {
    "Ref": "AWS::Region"
    },
    "/g' /etc/dynamic-dynamodb/example-dynamic-dynamodb.conf\n",
    " log \"Loaded example configuration to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    "}\n\n",
    "download_from_s3(){\n",
    " aws s3 cp $CONFIG_FILE_S3_LOCATION $CONFIG_FILE_LOCAL_LOCATION --region ",
    {
    "Ref": "S3BucketRegion"
    },
    " || error_exit \"Failed to download config file from $CONFIG_FILE_S3_LOCATION to $CONFIG_FILE_S3_LOCATION even though it existed on S3\"\n",
    " log \"Downloaded config file from $CONFIG_FILE_S3_LOCATION to $CONFIG_FILE_LOCAL_LOCATION\"\n",
    "}\n\n",
    "aws s3 cp $CONFIG_FILE_S3_LOCATION . --region ",
    {
    "Ref": "S3BucketRegion"
    },
    " >/dev/null 2>&1\n",
    "if [[ \"$?\" -eq 0 ]]; then\n",
    " DOES_CONFIG_FILE_EXIST_ON_S3=1\n",
    "fi\n\n",
    "if [[ -f $CONFIG_FILE_LOCAL_LOCATION ]]; then\n",
    " DOES_CONFIG_FILE_EXIST_ON_LOCALLY=1\n",
    "fi\n\n",
    "if [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 0 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 0 ]; then\n",
    " generate_new_config_file\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 0 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 1 ]; then\n",
    " log \"Config file exists locally and not on $CONFIG_FILE_S3_LOCATION, continuing to use the file\";\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 1 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 0 ]; then\n",
    " download_from_s3\n",
    "elif [ $DOES_CONFIG_FILE_EXIST_ON_S3 -eq 1 ] && [ $DOES_CONFIG_FILE_EXIST_ON_LOCALLY -eq 1 ]; then\n",
    " backup_file_locally $CONFIG_FILE_LOCAL_LOCATION\n",
    " download_from_s3\n",
    "fi\n"
    ]
    ]
    },
    "mode": "000755",
    "owner": "root",
    "group": "root"
    },
    "/etc/dynamic-dynamodb/example-dynamic-dynamodb.conf": {
    "source": "https://raw.github.com/sebdah/dynamic-dynamodb/master/example-dynamic-dynamodb.conf",
    "mode": "000644",
    "owner": "root",
    "group": "root"
    }
    }
    }
    }
    }
    },
    "AutoScalingGroup": {
    "Type": "AWS::AutoScaling::AutoScalingGroup",
    "Properties": {
    "AvailabilityZones": {
    "Fn::GetAZs": ""
    },
    "Cooldown": 300,
    "LaunchConfigurationName": {
    "Ref": "LaunchConfig"
    },
    "MaxSize": 1,
    "MinSize": 1,
    "Tags": [
    {
    "Key": "Name",
    "Value": "dynamic-dynamodb",
    "PropagateAtLaunch": "true"
    }
    ]
    }
    },
    "IamRole": {
    "Type": "AWS::IAM::Role",
    "Properties": {
    "AssumeRolePolicyDocument": {
    "Version": "2012-10-17",
    "Statement": [
    {
    "Effect": "Allow",
    "Principal": {
    "Service": [
    "ec2.amazonaws.com"
    ]
    },
    "Action": [
    "sts:AssumeRole"
    ]
    }
    ]
    },
    "Path": "/",
    "Policies": [
    {
    "PolicyName": "root",
    "PolicyDocument": {
    "Version": "2012-10-17",
    "Statement": [
    {
    "Effect": "Allow",
    "Action": [
    "dynamodb:DescribeTable",
    "dynamodb:ListTables",
    "dynamodb:UpdateTable",
    "cloudwatch:GetMetricStatistics",
    "s3:PutObject",
    "s3:GetObject"
    ],
    "Resource": [
    "*"
    ]
    },
    {
    "Effect": "Allow",
    "Action": [
    "sns:Publish"
    ],
    "Resource": [
    "arn:aws:sns:*::dynamic-dynamodb"
    ]
    }
    ]
    }
    }
    ]
    }
    },
    "IamInstanceProfile": {
    "Type": "AWS::IAM::InstanceProfile",
    "Properties": {
    "Path": "/",
    "Roles": [
    {
    "Ref": "IamRole"
    }
    ]
    }
    },
    "SecurityGroup": {
    "Type": "AWS::EC2::SecurityGroup",
    "Properties": {
    "GroupDescription": "Allow access to MyInstance",
    "SecurityGroupIngress": [
    {
    "IpProtocol": "tcp",
    "FromPort": 22,
    "ToPort": 22,
    "CidrIp": "0.0.0.0/0"
    }
    ]
    }
    },
    "WaitHandle": {
    "Type": "AWS::CloudFormation::WaitConditionHandle"
    },
    "WaitCondition": {
    "Type": "AWS::CloudFormation::WaitCondition",
    "DependsOn": "AutoScalingGroup",
    "Properties": {
    "Handle": {
    "Ref": "WaitHandle"
    },
    "Timeout": "600"
    }
    }
    },
    "Outputs": {
    "URL": {
    "Description": "EC2 instance",
    "Value": "You can find your EC2 instance at https://console.aws.amazon.com/ec2/v2/home?#Instances:search=dynamic-dynamodb"
    }
    }
    }