stack_master 0.3.1 → 0.4.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/README.md +55 -23
- data/lib/stack_master.rb +2 -0
- data/lib/stack_master/command.rb +8 -2
- data/lib/stack_master/config.rb +18 -1
- data/lib/stack_master/parameter_resolvers/secret.rb +1 -0
- data/lib/stack_master/template_compiler.rb +3 -0
- data/lib/stack_master/template_compilers/cfndsl.rb +11 -0
- data/lib/stack_master/template_compilers/yaml.rb +11 -0
- data/lib/stack_master/version.rb +1 -1
- data/spec/fixtures/stack_master.yml +2 -0
- data/spec/fixtures/templates/json/valid_myapp_vpc.json +53 -0
- data/spec/fixtures/templates/rb/cfndsl/sample.json +28 -0
- data/spec/fixtures/templates/rb/cfndsl/sample.rb +16 -0
- data/spec/fixtures/templates/yml/valid_myapp_vpc.yml +35 -0
- data/spec/stack_master/command_spec.rb +18 -0
- data/spec/stack_master/config_spec.rb +11 -1
- data/spec/stack_master/template_compiler_spec.rb +10 -0
- data/spec/stack_master/template_compilers/cfndsl_spec.rb +17 -0
- data/spec/stack_master/template_compilers/yaml_spec.rb +18 -0
- data/stack_master.gemspec +1 -0
- metadata +31 -3
    
        checksums.yaml
    CHANGED
    
    | @@ -1,7 +1,7 @@ | |
| 1 1 | 
             
            ---
         | 
| 2 2 | 
             
            SHA1:
         | 
| 3 | 
            -
              metadata.gz:  | 
| 4 | 
            -
              data.tar.gz:  | 
| 3 | 
            +
              metadata.gz: 134af119f4a1e7ac352e26c21921f3b1c31cdd4f
         | 
| 4 | 
            +
              data.tar.gz: b2945a13aa2168a9f4b2c8c4ae60883fa10d0f49
         | 
| 5 5 | 
             
            SHA512:
         | 
| 6 | 
            -
              metadata.gz:  | 
| 7 | 
            -
              data.tar.gz:  | 
| 6 | 
            +
              metadata.gz: d2fb9a998fc5ac28093551d67b3fe5832ba3c0ce411812590070cff1a87552f1ff30d8d9ea30b82d2c94e40961598a0dc15ac911d1672484a2bc85d209a71a94
         | 
| 7 | 
            +
              data.tar.gz: b6f3477bdaaa9f42d8a75367a55c1b40938e7550eb9ce37f2c1bea11fa093e57064732c2b5919b2a0d215981fd9a08706fd574418ac5a079aa1b844865b2f968
         | 
    
        data/README.md
    CHANGED
    
    | @@ -1,17 +1,29 @@ | |
| 1 1 | 
             
            
         | 
| 2 2 |  | 
| 3 | 
            -
            StackMaster is a  | 
| 4 | 
            -
             | 
| 5 | 
            -
             | 
| 6 | 
            -
             | 
| 7 | 
            -
            -  | 
| 8 | 
            -
            -  | 
| 9 | 
            -
             | 
| 10 | 
            -
             | 
| 11 | 
            -
             | 
| 12 | 
            -
             | 
| 13 | 
            -
             | 
| 14 | 
            -
             | 
| 3 | 
            +
            StackMaster is a CLI tool to manage CloudFormation stacks, with the following features:
         | 
| 4 | 
            +
             | 
| 5 | 
            +
            - Synchronous visibility into stack updates. See exactly what is changing and
         | 
| 6 | 
            +
              what will happen before agreeing to apply a change.
         | 
| 7 | 
            +
            - Dynamic parameter resolvers.
         | 
| 8 | 
            +
            - Template compiler support for YAML and [SparkleFormation](http://www.sparkleformation.io).
         | 
| 9 | 
            +
             | 
| 10 | 
            +
            Stack updates can cause a lot of damage if applied blindly. StackMaster helps
         | 
| 11 | 
            +
            with this by providing the operator with as much information about the proposed
         | 
| 12 | 
            +
            change as possible before asking for confirmation to continue. That information
         | 
| 13 | 
            +
            includes:
         | 
| 14 | 
            +
             | 
| 15 | 
            +
            - Template body and parameter diffs.
         | 
| 16 | 
            +
            - [Change
         | 
| 17 | 
            +
              sets](https://aws.amazon.com/blogs/aws/new-change-sets-for-aws-cloudformation/)
         | 
| 18 | 
            +
            are displayed for review.
         | 
| 19 | 
            +
            - Once the diffs & change set have been reviewed, the change can be applied and
         | 
| 20 | 
            +
              stack events monitored.
         | 
| 21 | 
            +
            - Stack events will be displayed until an end state is reached.
         | 
| 22 | 
            +
             | 
| 23 | 
            +
            Stack parameters can be dynamically resolved at runtime using one of the
         | 
| 24 | 
            +
            built in parameter resolvers. Parameters can be sourced from GPG encrypted YAML
         | 
| 25 | 
            +
            files, other stacks outputs, by querying various AWS API's to get resource ARNs
         | 
| 26 | 
            +
            etc.
         | 
| 15 27 |  | 
| 16 28 | 
             
            ## Installation
         | 
| 17 29 |  | 
| @@ -71,18 +83,34 @@ stacks: | |
| 71 83 |  | 
| 72 84 | 
             
            ## Directories
         | 
| 73 85 |  | 
| 74 | 
            -
            - `templates` - CloudFormation or  | 
| 86 | 
            +
            - `templates` - CloudFormation, SparkleFormation or CfnDsl templates.
         | 
| 75 87 | 
             
            - `polices` - Stack policies.
         | 
| 76 88 | 
             
            - `parameters` - Parameters as YAML files.
         | 
| 77 89 | 
             
            - `secrets` - GPG encrypted secret files.
         | 
| 90 | 
            +
            - `policies` - Stack policy JSON files.
         | 
| 91 | 
            +
             | 
| 92 | 
            +
            ## Templates
         | 
| 93 | 
            +
             | 
| 94 | 
            +
            StackMaster supports CloudFormation templates in plain JSON or YAML. Any `.yml` or `.yaml` file will be processed as
         | 
| 95 | 
            +
            YAML. While any `.json` file will be processed as JSON.
         | 
| 96 | 
            +
             | 
| 97 | 
            +
            ### Ruby DSLs
         | 
| 98 | 
            +
            By default, any template ending with `.rb` will be processed as a [SparkleFormation](https://github.com/sparkleformation/sparkle_formation)
         | 
| 99 | 
            +
            template. However, if you want to use [CfnDsl](https://github.com/stevenjack/cfndsl) templates you can add
         | 
| 100 | 
            +
            the following lines to your `stack_master.yml`.
         | 
| 101 | 
            +
             | 
| 102 | 
            +
            ```
         | 
| 103 | 
            +
            template_compilers:
         | 
| 104 | 
            +
              rb: cfndsl
         | 
| 105 | 
            +
            ```
         | 
| 78 106 |  | 
| 79 107 | 
             
            ## Parameters
         | 
| 80 108 |  | 
| 81 109 | 
             
            Parameters are loaded from multiple YAML files, merged from the following lookup paths:
         | 
| 82 110 |  | 
| 83 111 | 
             
            - parameters/[stack_name].yml
         | 
| 84 | 
            -
            - parameters/[region]/[ | 
| 85 | 
            -
            - parameters/[region_alias]/[ | 
| 112 | 
            +
            - parameters/[region]/[underscored_stack_name].yml
         | 
| 113 | 
            +
            - parameters/[region_alias]/[underscored_stack_name].yml
         | 
| 86 114 |  | 
| 87 115 | 
             
            A simple parameter file could look like this:
         | 
| 88 116 |  | 
| @@ -94,13 +122,11 @@ Keys in parameter files are automatically converted to camel case. | |
| 94 122 |  | 
| 95 123 | 
             
            ## Parameter Resolvers
         | 
| 96 124 |  | 
| 97 | 
            -
            Parameter  | 
| 98 | 
            -
            using a resolver will be a hash with one key where the key is the name of the
         | 
| 99 | 
            -
            resolver.
         | 
| 125 | 
            +
            Parameter values can be sourced dynamically using parameter resolvers.
         | 
| 100 126 |  | 
| 101 | 
            -
            One benefit of using resolvers instead of hard coding values like VPC | 
| 102 | 
            -
            resource ARNs is that the same configuration works cross | 
| 103 | 
            -
            the resolved values will be different.
         | 
| 127 | 
            +
            One benefit of using parameter resolvers instead of hard coding values like VPC
         | 
| 128 | 
            +
            ID's and resource ARNs is that the same configuration works cross
         | 
| 129 | 
            +
            region/account, even though the resolved values will be different.
         | 
| 104 130 |  | 
| 105 131 | 
             
            ### Stack Output
         | 
| 106 132 |  | 
| @@ -112,6 +138,10 @@ vpc_id: | |
| 112 138 | 
             
              stack_output: my-vpc-stack/VpcId
         | 
| 113 139 | 
             
            ```
         | 
| 114 140 |  | 
| 141 | 
            +
            This is the most used parameter resolver because it enables stacks to be split
         | 
| 142 | 
            +
            up into their separated concerns (VPC, web, database etc) with outputs feeding
         | 
| 143 | 
            +
            into parameters of dependent stacks.
         | 
| 144 | 
            +
             | 
| 115 145 | 
             
            ### Secret
         | 
| 116 146 |  | 
| 117 147 | 
             
            The secret parameters resolver expects a `secret_file` to be defined in the
         | 
| @@ -269,11 +299,13 @@ stack_master status # Displays the status of each stack | |
| 269 299 |  | 
| 270 300 | 
             
            The apply command does the following:
         | 
| 271 301 |  | 
| 272 | 
            -
            -  | 
| 302 | 
            +
            - Compiles the proposed stack template and resolves parameters.
         | 
| 273 303 | 
             
            - Fetches the current state of the stack from CloudFormation.
         | 
| 274 304 | 
             
            - Displays a diff of the current stack and the proposed stack.
         | 
| 305 | 
            +
            - Creates a change set and displays the actions that CloudFormation will take
         | 
| 306 | 
            +
              to perform the update (if the stack already exists).
         | 
| 275 307 | 
             
            - Asks if the update should continue.
         | 
| 276 | 
            -
            - If yes, the API  | 
| 308 | 
            +
            - If yes, the API calls are made to update or create the stack.
         | 
| 277 309 | 
             
            - Stack events are displayed until CloudFormation has finished applying the changes.
         | 
| 278 310 |  | 
| 279 311 | 
             
            Demo:
         | 
    
        data/lib/stack_master.rb
    CHANGED
    
    | @@ -40,6 +40,8 @@ require "stack_master/stack_definition" | |
| 40 40 | 
             
            require "stack_master/template_compiler"
         | 
| 41 41 | 
             
            require "stack_master/template_compilers/sparkle_formation"
         | 
| 42 42 | 
             
            require "stack_master/template_compilers/json"
         | 
| 43 | 
            +
            require "stack_master/template_compilers/yaml"
         | 
| 44 | 
            +
            require "stack_master/template_compilers/cfndsl"
         | 
| 43 45 | 
             
            require "stack_master/commands/terminal_helper"
         | 
| 44 46 | 
             
            require "stack_master/commands/apply"
         | 
| 45 47 | 
             
            require "stack_master/change_set"
         | 
    
        data/lib/stack_master/command.rb
    CHANGED
    
    | @@ -22,8 +22,8 @@ module StackMaster | |
| 22 22 | 
             
                    catch(:halt) do
         | 
| 23 23 | 
             
                      super
         | 
| 24 24 | 
             
                    end
         | 
| 25 | 
            -
                  rescue Aws::CloudFormation::Errors::ServiceError => e
         | 
| 26 | 
            -
                    failed  | 
| 25 | 
            +
                  rescue Aws::CloudFormation::Errors::ServiceError, TemplateCompiler::TemplateCompilationFailed => e
         | 
| 26 | 
            +
                    failed error_message(e)
         | 
| 27 27 | 
             
                  end
         | 
| 28 28 | 
             
                end
         | 
| 29 29 |  | 
| @@ -33,6 +33,12 @@ module StackMaster | |
| 33 33 |  | 
| 34 34 | 
             
                private
         | 
| 35 35 |  | 
| 36 | 
            +
                def error_message(e)
         | 
| 37 | 
            +
                  msg = "#{e.class} #{e.message}"
         | 
| 38 | 
            +
                  msg << "\n Caused by: #{e.cause.class} #{e.cause.message}" if e.cause
         | 
| 39 | 
            +
                  msg
         | 
| 40 | 
            +
                end
         | 
| 41 | 
            +
             | 
| 36 42 | 
             
                def failed(message = nil)
         | 
| 37 43 | 
             
                  StackMaster.stderr.puts(message) if message
         | 
| 38 44 | 
             
                  @failed = true
         | 
    
        data/lib/stack_master/config.rb
    CHANGED
    
    | @@ -42,7 +42,7 @@ module StackMaster | |
| 42 42 | 
             
                  end
         | 
| 43 43 | 
             
                  @region_defaults = normalise_region_defaults(config.fetch('region_defaults', {}))
         | 
| 44 44 | 
             
                  @stacks = []
         | 
| 45 | 
            -
                   | 
| 45 | 
            +
                  load_template_compilers(config)
         | 
| 46 46 | 
             
                  load_config
         | 
| 47 47 | 
             
                end
         | 
| 48 48 |  | 
| @@ -62,11 +62,28 @@ module StackMaster | |
| 62 62 | 
             
                end
         | 
| 63 63 |  | 
| 64 64 | 
             
                private
         | 
| 65 | 
            +
                def load_template_compilers(config)
         | 
| 66 | 
            +
                  @template_compilers = {}
         | 
| 67 | 
            +
                  populate_template_compilers(config.fetch('template_compilers', {}))
         | 
| 68 | 
            +
                  merge_defaults_to_user_defined_compilers
         | 
| 69 | 
            +
                end
         | 
| 70 | 
            +
             | 
| 71 | 
            +
                def merge_defaults_to_user_defined_compilers
         | 
| 72 | 
            +
                  @template_compilers = default_template_compilers.merge(@template_compilers)
         | 
| 73 | 
            +
                end
         | 
| 74 | 
            +
             | 
| 75 | 
            +
                def populate_template_compilers user_defined_compilers
         | 
| 76 | 
            +
                  user_defined_compilers.each do |key, val|
         | 
| 77 | 
            +
                    @template_compilers[key.to_sym] = val.to_sym
         | 
| 78 | 
            +
                  end
         | 
| 79 | 
            +
                end
         | 
| 65 80 |  | 
| 66 81 | 
             
                def default_template_compilers
         | 
| 67 82 | 
             
                  {
         | 
| 68 83 | 
             
                    rb: :sparkle_formation,
         | 
| 69 84 | 
             
                    json: :json,
         | 
| 85 | 
            +
                    yml:  :yaml,
         | 
| 86 | 
            +
                    yaml: :yaml,
         | 
| 70 87 | 
             
                  }
         | 
| 71 88 | 
             
                end
         | 
| 72 89 |  | 
| @@ -1,8 +1,11 @@ | |
| 1 1 | 
             
            module StackMaster
         | 
| 2 2 | 
             
              class TemplateCompiler
         | 
| 3 | 
            +
                TemplateCompilationFailed = Class.new(RuntimeError)
         | 
| 3 4 |  | 
| 4 5 | 
             
                def self.compile(config, template_file_path)
         | 
| 5 6 | 
             
                  template_compiler_for_file(template_file_path, config).compile(template_file_path)
         | 
| 7 | 
            +
                rescue
         | 
| 8 | 
            +
                  raise TemplateCompilationFailed.new("Failed to compile #{template_file_path}.")
         | 
| 6 9 | 
             
                end
         | 
| 7 10 |  | 
| 8 11 | 
             
                def self.register(name, klass)
         | 
    
        data/lib/stack_master/version.rb
    CHANGED
    
    
| @@ -0,0 +1,53 @@ | |
| 1 | 
            +
            {
         | 
| 2 | 
            +
              "Description": "A test VPC template",
         | 
| 3 | 
            +
              "Resources": {
         | 
| 4 | 
            +
                "Vpc": {
         | 
| 5 | 
            +
                  "Type": "AWS::EC2::VPC",
         | 
| 6 | 
            +
                  "Properties": {
         | 
| 7 | 
            +
                    "CidrBlock": "10.200.0.0/16"
         | 
| 8 | 
            +
                  }
         | 
| 9 | 
            +
                },
         | 
| 10 | 
            +
                "PublicSubnet": {
         | 
| 11 | 
            +
                  "Type": "AWS::EC2::Subnet",
         | 
| 12 | 
            +
                  "Properties": {
         | 
| 13 | 
            +
                    "VpcId": {
         | 
| 14 | 
            +
                      "Ref": "Vpc"
         | 
| 15 | 
            +
                    },
         | 
| 16 | 
            +
                    "CidrBlock": "10.200.1.0/24",
         | 
| 17 | 
            +
                    "AvailabilityZone": {
         | 
| 18 | 
            +
                      "Ref": "VpcAz1"
         | 
| 19 | 
            +
                    },
         | 
| 20 | 
            +
                    "Tags": [
         | 
| 21 | 
            +
                      {
         | 
| 22 | 
            +
                        "Key": "Name",
         | 
| 23 | 
            +
                        "Value": "PublicSubnet"
         | 
| 24 | 
            +
                      },
         | 
| 25 | 
            +
                      {
         | 
| 26 | 
            +
                        "Key": "network",
         | 
| 27 | 
            +
                        "Value": "public"
         | 
| 28 | 
            +
                      }
         | 
| 29 | 
            +
                    ]
         | 
| 30 | 
            +
                  }
         | 
| 31 | 
            +
                }
         | 
| 32 | 
            +
              },
         | 
| 33 | 
            +
              "Parameters": {
         | 
| 34 | 
            +
                "VpcAz1": {
         | 
| 35 | 
            +
                  "Description": "VPC AZ 1",
         | 
| 36 | 
            +
                  "Type": "AWS::EC2::AvailabilityZone::Name"
         | 
| 37 | 
            +
                }
         | 
| 38 | 
            +
              },
         | 
| 39 | 
            +
              "Outputs": {
         | 
| 40 | 
            +
                "VpcId": {
         | 
| 41 | 
            +
                  "Description": "VPC ID",
         | 
| 42 | 
            +
                  "Value": {
         | 
| 43 | 
            +
                    "Ref": "Vpc"
         | 
| 44 | 
            +
                  }
         | 
| 45 | 
            +
                },
         | 
| 46 | 
            +
                "PublicSubnet": {
         | 
| 47 | 
            +
                  "Description": "Public subnet",
         | 
| 48 | 
            +
                  "Value": {
         | 
| 49 | 
            +
                    "Ref": "PublicSubnet"
         | 
| 50 | 
            +
                  }
         | 
| 51 | 
            +
                }
         | 
| 52 | 
            +
              }
         | 
| 53 | 
            +
            }
         | 
| @@ -0,0 +1,28 @@ | |
| 1 | 
            +
            {
         | 
| 2 | 
            +
              "Parameters" : {
         | 
| 3 | 
            +
                "One" : {
         | 
| 4 | 
            +
                  "Type" : "String",
         | 
| 5 | 
            +
                  "Default" : "Test",
         | 
| 6 | 
            +
                  "MaxLength" : 15
         | 
| 7 | 
            +
                }
         | 
| 8 | 
            +
              },
         | 
| 9 | 
            +
              "Resources" : {
         | 
| 10 | 
            +
                "MyInstance" : {
         | 
| 11 | 
            +
                  "Type" : "AWS::EC2::Instance",
         | 
| 12 | 
            +
                  "Properties" : {
         | 
| 13 | 
            +
                    "ImageId" : "ami-12345678"
         | 
| 14 | 
            +
                  }
         | 
| 15 | 
            +
                }
         | 
| 16 | 
            +
              },
         | 
| 17 | 
            +
              "AWSTemplateFormatVersion" : "2010-09-09",
         | 
| 18 | 
            +
              "Outputs" : {
         | 
| 19 | 
            +
                "One" : {
         | 
| 20 | 
            +
                  "Value" : {
         | 
| 21 | 
            +
                    "Fn::Base64" : {
         | 
| 22 | 
            +
                      "Ref" : "One"
         | 
| 23 | 
            +
                    }
         | 
| 24 | 
            +
                  }
         | 
| 25 | 
            +
                }
         | 
| 26 | 
            +
              },
         | 
| 27 | 
            +
              "Description" : "Test"
         | 
| 28 | 
            +
            }
         | 
| @@ -0,0 +1,35 @@ | |
| 1 | 
            +
            ---
         | 
| 2 | 
            +
              Description: "A test VPC template"
         | 
| 3 | 
            +
              Resources:
         | 
| 4 | 
            +
                Vpc:
         | 
| 5 | 
            +
                  Type: "AWS::EC2::VPC"
         | 
| 6 | 
            +
                  Properties:
         | 
| 7 | 
            +
                    CidrBlock: "10.200.0.0/16"
         | 
| 8 | 
            +
                PublicSubnet:
         | 
| 9 | 
            +
                  Type: "AWS::EC2::Subnet"
         | 
| 10 | 
            +
                  Properties:
         | 
| 11 | 
            +
                    VpcId:
         | 
| 12 | 
            +
                      Ref: "Vpc"
         | 
| 13 | 
            +
                    CidrBlock: "10.200.1.0/24"
         | 
| 14 | 
            +
                    AvailabilityZone:
         | 
| 15 | 
            +
                      Ref: "VpcAz1"
         | 
| 16 | 
            +
                    Tags:
         | 
| 17 | 
            +
                      -
         | 
| 18 | 
            +
                        Key: "Name"
         | 
| 19 | 
            +
                        Value: "PublicSubnet"
         | 
| 20 | 
            +
                      -
         | 
| 21 | 
            +
                        Key: "network"
         | 
| 22 | 
            +
                        Value: "public"
         | 
| 23 | 
            +
              Parameters:
         | 
| 24 | 
            +
                VpcAz1:
         | 
| 25 | 
            +
                  Description: "VPC AZ 1"
         | 
| 26 | 
            +
                  Type: "AWS::EC2::AvailabilityZone::Name"
         | 
| 27 | 
            +
              Outputs:
         | 
| 28 | 
            +
                VpcId:
         | 
| 29 | 
            +
                  Description: "VPC ID"
         | 
| 30 | 
            +
                  Value:
         | 
| 31 | 
            +
                    Ref: "Vpc"
         | 
| 32 | 
            +
                PublicSubnet:
         | 
| 33 | 
            +
                  Description: "Public subnet"
         | 
| 34 | 
            +
                  Value:
         | 
| 35 | 
            +
                    Ref: "PublicSubnet"
         | 
| @@ -45,4 +45,22 @@ RSpec.describe StackMaster::Command do | |
| 45 45 | 
             
                  expect { command_class.perform(error_proc) }.to output(/the message/).to_stderr
         | 
| 46 46 | 
             
                end
         | 
| 47 47 | 
             
              end
         | 
| 48 | 
            +
             | 
| 49 | 
            +
              context 'when a template compilation error occurs' do
         | 
| 50 | 
            +
                it 'outputs the message' do
         | 
| 51 | 
            +
                  error_proc = proc {
         | 
| 52 | 
            +
                    raise StackMaster::TemplateCompiler::TemplateCompilationFailed.new('the message')
         | 
| 53 | 
            +
                  }
         | 
| 54 | 
            +
                  expect { command_class.perform(error_proc) }.to output(/the message/).to_stderr
         | 
| 55 | 
            +
                end
         | 
| 56 | 
            +
             | 
| 57 | 
            +
                it 'outputs the exception\'s cause' do
         | 
| 58 | 
            +
                  exception_with_cause = StackMaster::TemplateCompiler::TemplateCompilationFailed.new('the message')
         | 
| 59 | 
            +
                  allow(exception_with_cause).to receive(:cause).and_return(RuntimeError.new('the cause message'))
         | 
| 60 | 
            +
                  error_proc = proc {
         | 
| 61 | 
            +
                    raise exception_with_cause
         | 
| 62 | 
            +
                  }
         | 
| 63 | 
            +
                  expect { command_class.perform(error_proc) }.to output(/Caused by: RuntimeError the cause message/).to_stderr
         | 
| 64 | 
            +
                end
         | 
| 65 | 
            +
              end
         | 
| 48 66 | 
             
            end
         | 
| @@ -15,7 +15,7 @@ RSpec.describe StackMaster::Config do | |
| 15 15 | 
             
                )
         | 
| 16 16 | 
             
              }
         | 
| 17 17 |  | 
| 18 | 
            -
               | 
| 18 | 
            +
              describe ".load!" do
         | 
| 19 19 | 
             
                it "fails to load the config if no stack_master.yml in parent directories" do
         | 
| 20 20 | 
             
                  expect { StackMaster::Config.load!('stack_master.yml') }.to raise_error Errno::ENOENT
         | 
| 21 21 | 
             
                end
         | 
| @@ -70,6 +70,16 @@ RSpec.describe StackMaster::Config do | |
| 70 70 | 
             
                })
         | 
| 71 71 | 
             
              end
         | 
| 72 72 |  | 
| 73 | 
            +
              it 'loads template compiler mappings' do
         | 
| 74 | 
            +
                expect(loaded_config.template_compilers).to eq({
         | 
| 75 | 
            +
                                                                 rb: :ruby_dsl,
         | 
| 76 | 
            +
                                                                 json: :json,
         | 
| 77 | 
            +
                                                                 yml: :yaml,
         | 
| 78 | 
            +
                                                                 yaml: :yaml,
         | 
| 79 | 
            +
             | 
| 80 | 
            +
                                                               })
         | 
| 81 | 
            +
              end
         | 
| 82 | 
            +
             | 
| 73 83 | 
             
              it 'loads region defaults' do
         | 
| 74 84 | 
             
                expect(loaded_config.region_defaults).to eq({
         | 
| 75 85 | 
             
                  'us-east-1' => {
         | 
| @@ -16,6 +16,16 @@ RSpec.describe StackMaster::TemplateCompiler do | |
| 16 16 | 
             
                    expect(TestTemplateCompiler).to receive(:compile).with(template_file_path)
         | 
| 17 17 | 
             
                    StackMaster::TemplateCompiler.compile(config, template_file_path)
         | 
| 18 18 | 
             
                  end
         | 
| 19 | 
            +
             | 
| 20 | 
            +
                  context 'when template compilation fails' do
         | 
| 21 | 
            +
                    before { allow(TestTemplateCompiler).to receive(:compile).and_raise(RuntimeError) }
         | 
| 22 | 
            +
             | 
| 23 | 
            +
                    it 'raise TemplateCompilationFailed exception' do
         | 
| 24 | 
            +
                      expect{ StackMaster::TemplateCompiler.compile(config, template_file_path)
         | 
| 25 | 
            +
                      }.to raise_error(
         | 
| 26 | 
            +
                             StackMaster::TemplateCompiler::TemplateCompilationFailed,"Failed to compile #{template_file_path}.")
         | 
| 27 | 
            +
                    end
         | 
| 28 | 
            +
                  end
         | 
| 19 29 | 
             
                end
         | 
| 20 30 | 
             
              end
         | 
| 21 31 | 
             
            end
         | 
| @@ -0,0 +1,17 @@ | |
| 1 | 
            +
            RSpec.describe StackMaster::TemplateCompilers::Cfndsl do
         | 
| 2 | 
            +
              describe '.compile' do
         | 
| 3 | 
            +
                def compile
         | 
| 4 | 
            +
                  described_class.compile(template_file_path)
         | 
| 5 | 
            +
                end
         | 
| 6 | 
            +
             | 
| 7 | 
            +
                context 'valid cfndsl template' do
         | 
| 8 | 
            +
                  let(:template_file_path) { 'spec/fixtures/templates/rb/cfndsl/sample.rb' }
         | 
| 9 | 
            +
                  let(:valid_compiled_json_path) { 'spec/fixtures/templates/rb/cfndsl/sample.json' }
         | 
| 10 | 
            +
             | 
| 11 | 
            +
                  it 'produces valid JSON' do
         | 
| 12 | 
            +
                    valid_compiled_json = File.read(valid_compiled_json_path)
         | 
| 13 | 
            +
                    expect(JSON.parse(compile)).to eq(JSON.parse(valid_compiled_json))
         | 
| 14 | 
            +
                  end
         | 
| 15 | 
            +
                end
         | 
| 16 | 
            +
              end
         | 
| 17 | 
            +
            end
         | 
| @@ -0,0 +1,18 @@ | |
| 1 | 
            +
            RSpec.describe StackMaster::TemplateCompilers::Yaml do
         | 
| 2 | 
            +
              describe '.compile' do
         | 
| 3 | 
            +
                def compile
         | 
| 4 | 
            +
                  described_class.compile(template_file_path)
         | 
| 5 | 
            +
                end
         | 
| 6 | 
            +
             | 
| 7 | 
            +
                context 'valid YAML template' do
         | 
| 8 | 
            +
                  let(:template_file_path) { 'spec/fixtures/templates/yml/valid_myapp_vpc.yml' }
         | 
| 9 | 
            +
             | 
| 10 | 
            +
                  it 'produces valid JSON' do
         | 
| 11 | 
            +
                    valid_myapp_vpc_as_json = File.read('spec/fixtures/templates/json/valid_myapp_vpc.json')
         | 
| 12 | 
            +
                    valid_myapp_vpc_as_hash = JSON.parse(valid_myapp_vpc_as_json)
         | 
| 13 | 
            +
             | 
| 14 | 
            +
                    expect(JSON.parse(compile)).to eq(valid_myapp_vpc_as_hash)
         | 
| 15 | 
            +
                  end
         | 
| 16 | 
            +
                end
         | 
| 17 | 
            +
              end
         | 
| 18 | 
            +
            end
         | 
    
        data/stack_master.gemspec
    CHANGED
    
    
    
        metadata
    CHANGED
    
    | @@ -1,7 +1,7 @@ | |
| 1 1 | 
             
            --- !ruby/object:Gem::Specification
         | 
| 2 2 | 
             
            name: stack_master
         | 
| 3 3 | 
             
            version: !ruby/object:Gem::Version
         | 
| 4 | 
            -
              version: 0. | 
| 4 | 
            +
              version: 0.4.1
         | 
| 5 5 | 
             
            platform: ruby
         | 
| 6 6 | 
             
            authors:
         | 
| 7 7 | 
             
            - Steve Hodgkiss
         | 
| @@ -9,7 +9,7 @@ authors: | |
| 9 9 | 
             
            autorequire: 
         | 
| 10 10 | 
             
            bindir: bin
         | 
| 11 11 | 
             
            cert_chain: []
         | 
| 12 | 
            -
            date: 2016-04- | 
| 12 | 
            +
            date: 2016-04-07 00:00:00.000000000 Z
         | 
| 13 13 | 
             
            dependencies:
         | 
| 14 14 | 
             
            - !ruby/object:Gem::Dependency
         | 
| 15 15 | 
             
              name: bundler
         | 
| @@ -263,6 +263,20 @@ dependencies: | |
| 263 263 | 
             
                - - ">="
         | 
| 264 264 | 
             
                  - !ruby/object:Gem::Version
         | 
| 265 265 | 
             
                    version: '0'
         | 
| 266 | 
            +
            - !ruby/object:Gem::Dependency
         | 
| 267 | 
            +
              name: cfndsl
         | 
| 268 | 
            +
              requirement: !ruby/object:Gem::Requirement
         | 
| 269 | 
            +
                requirements:
         | 
| 270 | 
            +
                - - ">="
         | 
| 271 | 
            +
                  - !ruby/object:Gem::Version
         | 
| 272 | 
            +
                    version: '0'
         | 
| 273 | 
            +
              type: :runtime
         | 
| 274 | 
            +
              prerelease: false
         | 
| 275 | 
            +
              version_requirements: !ruby/object:Gem::Requirement
         | 
| 276 | 
            +
                requirements:
         | 
| 277 | 
            +
                - - ">="
         | 
| 278 | 
            +
                  - !ruby/object:Gem::Version
         | 
| 279 | 
            +
                    version: '0'
         | 
| 266 280 | 
             
            description: ''
         | 
| 267 281 | 
             
            email:
         | 
| 268 282 | 
             
            - steve@hodgkiss.me
         | 
| @@ -339,8 +353,10 @@ files: | |
| 339 353 | 
             
            - lib/stack_master/stack_states.rb
         | 
| 340 354 | 
             
            - lib/stack_master/stack_status.rb
         | 
| 341 355 | 
             
            - lib/stack_master/template_compiler.rb
         | 
| 356 | 
            +
            - lib/stack_master/template_compilers/cfndsl.rb
         | 
| 342 357 | 
             
            - lib/stack_master/template_compilers/json.rb
         | 
| 343 358 | 
             
            - lib/stack_master/template_compilers/sparkle_formation.rb
         | 
| 359 | 
            +
            - lib/stack_master/template_compilers/yaml.rb
         | 
| 344 360 | 
             
            - lib/stack_master/test_driver/cloud_formation.rb
         | 
| 345 361 | 
             
            - lib/stack_master/testing.rb
         | 
| 346 362 | 
             
            - lib/stack_master/utils.rb
         | 
| @@ -352,7 +368,11 @@ files: | |
| 352 368 | 
             
            - script/buildkite_rspec.sh
         | 
| 353 369 | 
             
            - spec/fixtures/parameters/myapp_vpc.yml
         | 
| 354 370 | 
             
            - spec/fixtures/stack_master.yml
         | 
| 371 | 
            +
            - spec/fixtures/templates/json/valid_myapp_vpc.json
         | 
| 355 372 | 
             
            - spec/fixtures/templates/myapp_vpc.json
         | 
| 373 | 
            +
            - spec/fixtures/templates/rb/cfndsl/sample.json
         | 
| 374 | 
            +
            - spec/fixtures/templates/rb/cfndsl/sample.rb
         | 
| 375 | 
            +
            - spec/fixtures/templates/yml/valid_myapp_vpc.yml
         | 
| 356 376 | 
             
            - spec/spec_helper.rb
         | 
| 357 377 | 
             
            - spec/stack_master/change_set_spec.rb
         | 
| 358 378 | 
             
            - spec/stack_master/command_spec.rb
         | 
| @@ -382,8 +402,10 @@ files: | |
| 382 402 | 
             
            - spec/stack_master/stack_events/streamer_spec.rb
         | 
| 383 403 | 
             
            - spec/stack_master/stack_spec.rb
         | 
| 384 404 | 
             
            - spec/stack_master/template_compiler_spec.rb
         | 
| 405 | 
            +
            - spec/stack_master/template_compilers/cfndsl_spec.rb
         | 
| 385 406 | 
             
            - spec/stack_master/template_compilers/json_spec.rb
         | 
| 386 407 | 
             
            - spec/stack_master/template_compilers/sparkle_formation_spec.rb
         | 
| 408 | 
            +
            - spec/stack_master/template_compilers/yaml_spec.rb
         | 
| 387 409 | 
             
            - spec/stack_master/test_driver/cloud_formation_spec.rb
         | 
| 388 410 | 
             
            - spec/stack_master/utils_spec.rb
         | 
| 389 411 | 
             
            - spec/stack_master/validator_spec.rb
         | 
| @@ -413,7 +435,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement | |
| 413 435 | 
             
                  version: '0'
         | 
| 414 436 | 
             
            requirements: []
         | 
| 415 437 | 
             
            rubyforge_project: 
         | 
| 416 | 
            -
            rubygems_version: 2.5.1
         | 
| 438 | 
            +
            rubygems_version: 2.4.5.1
         | 
| 417 439 | 
             
            signing_key: 
         | 
| 418 440 | 
             
            specification_version: 4
         | 
| 419 441 | 
             
            summary: StackMaster is a sure-footed way of creating, updating and keeping track
         | 
| @@ -434,7 +456,11 @@ test_files: | |
| 434 456 | 
             
            - features/validate.feature
         | 
| 435 457 | 
             
            - spec/fixtures/parameters/myapp_vpc.yml
         | 
| 436 458 | 
             
            - spec/fixtures/stack_master.yml
         | 
| 459 | 
            +
            - spec/fixtures/templates/json/valid_myapp_vpc.json
         | 
| 437 460 | 
             
            - spec/fixtures/templates/myapp_vpc.json
         | 
| 461 | 
            +
            - spec/fixtures/templates/rb/cfndsl/sample.json
         | 
| 462 | 
            +
            - spec/fixtures/templates/rb/cfndsl/sample.rb
         | 
| 463 | 
            +
            - spec/fixtures/templates/yml/valid_myapp_vpc.yml
         | 
| 438 464 | 
             
            - spec/spec_helper.rb
         | 
| 439 465 | 
             
            - spec/stack_master/change_set_spec.rb
         | 
| 440 466 | 
             
            - spec/stack_master/command_spec.rb
         | 
| @@ -464,8 +490,10 @@ test_files: | |
| 464 490 | 
             
            - spec/stack_master/stack_events/streamer_spec.rb
         | 
| 465 491 | 
             
            - spec/stack_master/stack_spec.rb
         | 
| 466 492 | 
             
            - spec/stack_master/template_compiler_spec.rb
         | 
| 493 | 
            +
            - spec/stack_master/template_compilers/cfndsl_spec.rb
         | 
| 467 494 | 
             
            - spec/stack_master/template_compilers/json_spec.rb
         | 
| 468 495 | 
             
            - spec/stack_master/template_compilers/sparkle_formation_spec.rb
         | 
| 496 | 
            +
            - spec/stack_master/template_compilers/yaml_spec.rb
         | 
| 469 497 | 
             
            - spec/stack_master/test_driver/cloud_formation_spec.rb
         | 
| 470 498 | 
             
            - spec/stack_master/utils_spec.rb
         | 
| 471 499 | 
             
            - spec/stack_master/validator_spec.rb
         |