lono 8.0.0.pre.rc2 → 8.0.0.pre.rc3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +15 -2
- data/Gemfile +1 -3
- data/lib/lono/app/callable_option/concern.rb +12 -0
- data/lib/lono/app/callable_option.rb +56 -0
- data/lib/lono/app.rb +22 -23
- data/lib/lono/autoloader.rb +1 -0
- data/lib/lono/aws_services/helper.rb +0 -2
- data/lib/lono/blueprint.rb +1 -18
- data/lib/lono/builder/allow/base.rb +54 -0
- data/lib/lono/builder/allow/env.rb +17 -0
- data/lib/lono/builder/allow/region.rb +20 -0
- data/lib/lono/builder/allow.rb +8 -0
- data/lib/lono/builder/configset/combiner.rb +145 -0
- data/lib/lono/builder/configset/definition/base.rb +47 -0
- data/lib/lono/builder/configset/definition/context.rb +29 -0
- data/lib/lono/{configset/strategy/helpers/dsl → builder/configset/definition/dsl/syntax}/auth.rb +1 -1
- data/lib/lono/{configset/strategy/helpers/dsl/core.rb → builder/configset/definition/dsl/syntax/content.rb} +12 -4
- data/lib/lono/{configset/strategy/helpers/dsl/syntax.rb → builder/configset/definition/dsl/syntax/core.rb} +15 -9
- data/lib/lono/{configset/strategy/helpers/dsl → builder/configset/definition/dsl/syntax}/package.rb +1 -1
- data/lib/lono/builder/configset/definition/dsl/syntax.rb +5 -0
- data/lib/lono/{configset/strategy → builder/configset/definition}/dsl.rb +10 -14
- data/lib/lono/{configset/strategy → builder/configset/definition}/erb.rb +13 -16
- data/lib/lono/builder/configset/definition.rb +18 -0
- data/lib/lono/builder/configset/evaluator.rb +10 -0
- data/lib/lono/builder/configset/registration.rb +35 -0
- data/lib/lono/builder/context.rb +40 -0
- data/lib/lono/builder/dsl/evaluator.rb +6 -55
- data/lib/lono/builder/dsl/finalizer/base.rb +8 -0
- data/lib/lono/builder/dsl/finalizer/configsets.rb +7 -28
- data/lib/lono/builder/dsl/finalizer/files/base.rb +4 -0
- data/lib/lono/builder/dsl/finalizer/files/build.rb +58 -0
- data/lib/lono/builder/dsl/finalizer/files/replace.rb +31 -0
- data/lib/lono/builder/dsl/finalizer/files.rb +9 -0
- data/lib/lono/builder/dsl/finalizer/parameter_groups.rb +4 -3
- data/lib/lono/builder/dsl/finalizer.rb +4 -2
- data/lib/lono/builder/dsl/helpers/files.rb +7 -0
- data/lib/lono/builder/dsl/helpers/partials.rb +48 -53
- data/lib/lono/builder/dsl/helpers/s3.rb +1 -1
- data/lib/lono/builder/dsl/helpers/ssm/fetcher.rb +3 -1
- data/lib/lono/builder/dsl/helpers/template_file.rb +18 -6
- data/lib/lono/builder/dsl/helpers.rb +1 -11
- data/lib/lono/builder/dsl/syntax/core/resource/property_mover.rb +11 -1
- data/lib/lono/builder/dsl/syntax/core/squeezer.rb +16 -2
- data/lib/lono/builder/dsl.rb +1 -1
- data/lib/lono/builder/param.rb +4 -1
- data/lib/lono/builder/template/upload.rb +2 -15
- data/lib/lono/cfn/cancel.rb +5 -5
- data/lib/lono/cfn/deploy/iam.rb +1 -1
- data/lib/lono/cfn/deploy.rb +32 -3
- data/lib/lono/cfn/download.rb +0 -1
- data/lib/lono/cfn/plan/changeset.rb +2 -2
- data/lib/lono/cfn/plan/diff/data.rb +11 -1
- data/lib/lono/cfn/plan/param.rb +1 -1
- data/lib/lono/cfn/plan/template.rb +2 -2
- data/lib/lono/cfn/plan.rb +1 -0
- data/lib/lono/cli/abstract.rb +0 -6
- data/lib/lono/cli/base.rb +5 -3
- data/lib/lono/cli/build.rb +16 -60
- data/lib/lono/cli/clean.rb +3 -2
- data/lib/lono/cli/code.rb +12 -12
- data/lib/lono/cli/help/new/helper/blueprint.md +17 -0
- data/lib/lono/cli/help/new/helper/project.md +16 -0
- data/lib/lono/cli/list.rb +3 -6
- data/lib/lono/cli/new/blueprint.rb +3 -7
- data/lib/lono/cli/new/configset.rb +11 -44
- data/lib/lono/cli/new/helper/blueprint.rb +26 -0
- data/lib/lono/cli/new/helper/project.rb +24 -0
- data/lib/lono/cli/new/helper.rb +8 -27
- data/lib/lono/cli/new/sequence.rb +6 -1
- data/lib/lono/cli/new.rb +8 -12
- data/lib/lono/cli/status.rb +18 -0
- data/lib/lono/cli.rb +6 -9
- data/lib/lono/command.rb +0 -1
- data/lib/lono/component.rb +29 -0
- data/lib/lono/concerns/aws_info.rb +14 -0
- data/lib/lono/concerns/names.rb +9 -0
- data/lib/lono/configset.rb +17 -0
- data/lib/lono/core.rb +1 -1
- data/lib/lono/ext/bundler.rb +7 -0
- data/lib/lono/ext/core/module.rb +31 -0
- data/lib/lono/ext/core/object.rb +32 -0
- data/lib/lono/ext/core/string.rb +9 -0
- data/lib/lono/ext.rb +4 -0
- data/lib/lono/files/base.rb +12 -0
- data/lib/lono/files/builder.rb +37 -0
- data/lib/lono/files/compressor.rb +53 -0
- data/lib/lono/files/concerns/post_processing.rb +35 -0
- data/lib/lono/files/concerns/registration.rb +13 -0
- data/lib/lono/files/registry.rb +6 -0
- data/lib/lono/files.rb +37 -0
- data/lib/lono/importer/base.rb +1 -1
- data/lib/lono/inspector/summary.rb +0 -3
- data/lib/lono/layering/layer.rb +3 -17
- data/lib/lono/logger.rb +1 -3
- data/lib/lono/names.rb +1 -1
- data/lib/lono/s3/uploader.rb +29 -28
- data/lib/lono/seeder.rb +18 -27
- data/lib/lono/user_data.rb +3 -1
- data/lib/lono/version.rb +1 -1
- data/lib/lono/yamler/validator.rb +7 -22
- data/lib/lono.rb +8 -0
- data/lib/templates/configset/configset.rb +2 -16
- data/lib/templates/examples/configset/configset.rb +16 -0
- data/lib/templates/helper/%underscore_name%_helper.rb.tt +1 -1
- data/lono.gemspec +1 -1
- metadata +52 -39
- data/lib/lono/app_file/base.rb +0 -28
- data/lib/lono/app_file/build/lambda_layer/ruby_packager.rb +0 -153
- data/lib/lono/app_file/build/lambda_layer.rb +0 -20
- data/lib/lono/app_file/build.rb +0 -79
- data/lib/lono/app_file/registry/item.rb +0 -24
- data/lib/lono/app_file/registry.rb +0 -16
- data/lib/lono/app_file/upload.rb +0 -12
- data/lib/lono/builder/context/generic.rb +0 -11
- data/lib/lono/builder/context/loaders/load_files.rb +0 -23
- data/lib/lono/builder/context/loaders.rb +0 -35
- data/lib/lono/builder/context/params.rb +0 -6
- data/lib/lono/builder/context/template.rb +0 -4
- data/lib/lono/configset/builder.rb +0 -59
- data/lib/lono/configset/combiner.rb +0 -164
- data/lib/lono/configset/evaluate_file.rb +0 -8
- data/lib/lono/configset/meta/dsl.rb +0 -12
- data/lib/lono/configset/meta.rb +0 -19
- data/lib/lono/configset/s3_file/build.rb +0 -34
- data/lib/lono/configset/s3_file/item.rb +0 -38
- data/lib/lono/configset/s3_file/registry.rb +0 -12
- data/lib/lono/configset/s3_file/upload.rb +0 -12
- data/lib/lono/configset/strategy/base.rb +0 -83
- data/lib/lono/configset/strategy/helpers/dsl.rb +0 -8
- data/lib/lono/configset/strategy/helpers/erb.rb +0 -9
- data/lib/lono/lookup.rb +0 -12
- data/lib/lono/seeder/service_role.rb +0 -11
- data/lib/lono/utils/contexts.rb +0 -15
- data/lib/lono/utils/item/file_methods.rb +0 -29
- data/lib/lono/utils/item/zip.rb +0 -42
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 99ed66c36726e513ebe394291384f039d6dbbc7beef5a376b28b3b84121f1a42
|
4
|
+
data.tar.gz: ec1902278f840c29539d54fffa9167565a27f1837a4ee2795d8db86badf0030d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 522056fb098c360c2ad59d99dfabaa723aeec157ca5012938c36efcb130e1bf6c2974d158e3c2f864e258c5d4b065d8e949667291f6af7d779bad91d2b451a0f
|
7
|
+
data.tar.gz: 18d17bbf1fcdd0f9d7c59f87b83e463f277958fb34cfb07d5918904b76ae44ecd2995f7e36f09d0a99c15d01070b469abf44bcfc95ec8f413aa54fdb0058fc6c
|
data/CHANGELOG.md
CHANGED
@@ -1,7 +1,20 @@
|
|
1
1
|
# Change Log
|
2
2
|
|
3
|
-
|
4
|
-
|
3
|
+
## [8.0.0.rc3] - 2022-03-06
|
4
|
+
|
5
|
+
* lono files support for lambda functions
|
6
|
+
* new structure: remove Appfile
|
7
|
+
* allow regions and envs support
|
8
|
+
* print friend message with exact line of yaml code in case of aws
|
9
|
+
* cloudformation yaml validation error
|
10
|
+
* improve cli help
|
11
|
+
* configsets new structure
|
12
|
+
* lono new helper blueprint and project commands
|
13
|
+
* project helpers support
|
14
|
+
* include_modules improvements
|
15
|
+
* support vendor level helpers
|
16
|
+
* improve plan params diff
|
17
|
+
* lono plan build all first
|
5
18
|
|
6
19
|
## [8.0.0.rc2] - 2022-02-23
|
7
20
|
|
data/Gemfile
CHANGED
@@ -3,8 +3,6 @@ source "https://rubygems.org"
|
|
3
3
|
# Specify your gem dependencies in lono.gemspec
|
4
4
|
gemspec
|
5
5
|
|
6
|
-
|
7
|
-
gem "rspec-lono", path: "~/boltops-tools/rspec-lono"
|
8
|
-
else
|
6
|
+
group :test do
|
9
7
|
gem "rspec-lono", git: "https://github.com/boltops-tools/rspec-lono", branch: "master"
|
10
8
|
end
|
@@ -0,0 +1,12 @@
|
|
1
|
+
class Lono::App::CallableOption
|
2
|
+
module Concern
|
3
|
+
def callable_option(options={})
|
4
|
+
callable_option = Lono::App::CallableOption.new(
|
5
|
+
config_name: options[:config_name],
|
6
|
+
config_value: options[:config_value],
|
7
|
+
passed_args: options[:passed_args],
|
8
|
+
)
|
9
|
+
callable_option.object
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
@@ -0,0 +1,56 @@
|
|
1
|
+
# Class represents a lono option that is possibly callable. Examples:
|
2
|
+
#
|
3
|
+
# config.allow.envs
|
4
|
+
# config.allow.regions
|
5
|
+
# config.deny.envs
|
6
|
+
# config.deny.regions
|
7
|
+
#
|
8
|
+
# Abstraction is definitely obtuse. Using it to get rid of duplication.
|
9
|
+
#
|
10
|
+
class Lono::App
|
11
|
+
class CallableOption
|
12
|
+
include Lono::Utils::Logging
|
13
|
+
|
14
|
+
def initialize(options={})
|
15
|
+
@options = options
|
16
|
+
# Example:
|
17
|
+
# config_name: config.allow.envs
|
18
|
+
# config_value: ["dev"]
|
19
|
+
# args: [@stack_name] # passed to object.call
|
20
|
+
@config_name = options[:config_name]
|
21
|
+
@config_value = options[:config_value]
|
22
|
+
@passed_args = options[:passed_args]
|
23
|
+
end
|
24
|
+
|
25
|
+
# Returns either an Array or nil
|
26
|
+
def object
|
27
|
+
case @config_value
|
28
|
+
when nil
|
29
|
+
return nil
|
30
|
+
when Array
|
31
|
+
return @config_value
|
32
|
+
when -> (c) { c.respond_to?(:public_instance_methods) && c.public_instance_methods.include?(:call) }
|
33
|
+
object= @config_value.new
|
34
|
+
when -> (c) { c.respond_to?(:call) }
|
35
|
+
object = @config_value
|
36
|
+
else
|
37
|
+
raise "Invalid option for #{@config_name}"
|
38
|
+
end
|
39
|
+
|
40
|
+
if object
|
41
|
+
result = @passed_args.empty? ? object.call : object.call(*@passed_args)
|
42
|
+
unless result.is_a?(Array) || result.is_a?(NilClass)
|
43
|
+
message = "ERROR: The #{@config_name} needs to return an Array or nil"
|
44
|
+
logger.info message.color(:yellow)
|
45
|
+
logger.info <<~EOL
|
46
|
+
The #{@config_name} when assigned a class, object, or proc must implement
|
47
|
+
the call method and return an Array or nil.
|
48
|
+
The current return value is a #{result.class}
|
49
|
+
EOL
|
50
|
+
raise message
|
51
|
+
end
|
52
|
+
end
|
53
|
+
result
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
data/lib/lono/app.rb
CHANGED
@@ -13,6 +13,16 @@ module Lono
|
|
13
13
|
def defaults
|
14
14
|
config = ActiveSupport::OrderedOptions.new
|
15
15
|
|
16
|
+
config.allow = ActiveSupport::OrderedOptions.new
|
17
|
+
config.allow.envs = nil
|
18
|
+
config.allow.regions = nil
|
19
|
+
config.deny = ActiveSupport::OrderedOptions.new
|
20
|
+
config.deny.envs = nil
|
21
|
+
config.deny.regions = nil
|
22
|
+
|
23
|
+
config.layering = ActiveSupport::OrderedOptions.new
|
24
|
+
config.layering.names = {}
|
25
|
+
|
16
26
|
config.log = ActiveSupport::OrderedOptions.new
|
17
27
|
config.log.root = Lono.log_root
|
18
28
|
config.logger = lono_logger
|
@@ -20,16 +30,21 @@ module Lono
|
|
20
30
|
config.logger.level = ENV['LONO_LOG_LEVEL'] || :info
|
21
31
|
|
22
32
|
config.names = ActiveSupport::OrderedOptions.new
|
23
|
-
config.names.stack = ":APP-:BLUEPRINT-:ENV"
|
24
33
|
config.names.output = ActiveSupport::OrderedOptions.new
|
25
|
-
config.names.output.stack = ":BLUEPRINT-:ENV" # does not include APP by default. Think this is more common
|
26
34
|
config.names.output.expand = true
|
35
|
+
config.names.output.stack = ":BLUEPRINT-:ENV" # does not include APP by default. Think this is more common
|
36
|
+
config.names.stack = ":APP-:BLUEPRINT-:ENV"
|
37
|
+
|
38
|
+
config.plan = ActiveSupport::OrderedOptions.new
|
39
|
+
config.plan.changeset = true
|
40
|
+
config.plan.params = "full"
|
41
|
+
config.plan.template = "summary" # summary is same as true
|
27
42
|
|
28
|
-
config.
|
29
|
-
config.
|
30
|
-
|
31
|
-
config.
|
32
|
-
config.
|
43
|
+
config.seed = ActiveSupport::OrderedOptions.new
|
44
|
+
config.seed.where = "config"
|
45
|
+
|
46
|
+
config.test = ActiveSupport::OrderedOptions.new
|
47
|
+
config.test.framework = "rspec"
|
33
48
|
|
34
49
|
config.up = ActiveSupport::OrderedOptions.new
|
35
50
|
config.up.capabilities = nil
|
@@ -37,22 +52,6 @@ module Lono
|
|
37
52
|
config.up.rollback = true
|
38
53
|
config.up.tags = nil
|
39
54
|
|
40
|
-
config.diff = ActiveSupport::OrderedOptions.new
|
41
|
-
config.diff.changeset = true
|
42
|
-
config.diff.params = "full"
|
43
|
-
config.diff.template = "summary" # summary is same as true
|
44
|
-
|
45
|
-
config.extract_scripts = {}
|
46
|
-
|
47
|
-
config.test = ActiveSupport::OrderedOptions.new
|
48
|
-
config.test.framework = "rspec"
|
49
|
-
|
50
|
-
config.layering = ActiveSupport::OrderedOptions.new
|
51
|
-
config.layering.names = {}
|
52
|
-
|
53
|
-
config.seed = ActiveSupport::OrderedOptions.new
|
54
|
-
config.seed.where = "config"
|
55
|
-
|
56
55
|
config
|
57
56
|
end
|
58
57
|
|
data/lib/lono/autoloader.rb
CHANGED
data/lib/lono/blueprint.rb
CHANGED
@@ -1,22 +1,5 @@
|
|
1
1
|
module Lono
|
2
|
-
class Blueprint
|
3
|
-
attr_reader :name
|
4
|
-
def initialize(options={})
|
5
|
-
@options = options
|
6
|
-
@name = options[:blueprint]
|
7
|
-
end
|
8
|
-
|
9
|
-
def exist?
|
10
|
-
!root.nil?
|
11
|
-
end
|
12
|
-
|
13
|
-
def root
|
14
|
-
paths = Dir.glob("#{Lono.root}/{app,vendor}/blueprints/*")
|
15
|
-
paths.find do |path|
|
16
|
-
path.include?("blueprints/#{@name}")
|
17
|
-
end
|
18
|
-
end
|
19
|
-
|
2
|
+
class Blueprint < Component
|
20
3
|
def output_path
|
21
4
|
"#{Lono.root}/output/#{@name}/template.yml"
|
22
5
|
end
|
@@ -0,0 +1,54 @@
|
|
1
|
+
class Lono::Builder::Allow
|
2
|
+
class Base < Lono::CLI::Base
|
3
|
+
include Lono::App::CallableOption::Concern
|
4
|
+
|
5
|
+
def check!
|
6
|
+
messages = []
|
7
|
+
unless allowed?
|
8
|
+
messages << message # message is interface method
|
9
|
+
end
|
10
|
+
unless messages.empty?
|
11
|
+
puts "ERROR: The configs do not allow this.".color(:red)
|
12
|
+
puts messages
|
13
|
+
exit 1
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
def allowed?
|
18
|
+
if allows.nil? && denys.nil?
|
19
|
+
true
|
20
|
+
elsif denys.nil?
|
21
|
+
allows.include?(check_value)
|
22
|
+
elsif allows.nil?
|
23
|
+
!denys.include?(check_value)
|
24
|
+
else
|
25
|
+
allows.include?(check_value) && !denys.include?(check_value)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def allows
|
30
|
+
callable_option(
|
31
|
+
config_name: "config.allow.#{config_name}",
|
32
|
+
config_value: config.dig(:allow, config_name),
|
33
|
+
passed_args: [@blueprint],
|
34
|
+
)
|
35
|
+
end
|
36
|
+
|
37
|
+
def denys
|
38
|
+
callable_option(
|
39
|
+
config_name: "config.deny.#{config_name}",
|
40
|
+
config_value: config.dig(:deny, config_name),
|
41
|
+
passed_args: [@blueprint],
|
42
|
+
)
|
43
|
+
end
|
44
|
+
|
45
|
+
private
|
46
|
+
def config
|
47
|
+
Lono.config
|
48
|
+
end
|
49
|
+
|
50
|
+
def config_name
|
51
|
+
self.class.to_s.split('::').last.underscore.pluralize.to_sym # ActiveSuport::HashWithIndifferentAccess#dig requires symbol
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
class Lono::Builder::Allow
|
2
|
+
class Env < Base
|
3
|
+
# interface method
|
4
|
+
def message
|
5
|
+
messages = []
|
6
|
+
messages << "This env is not allowed to be used: LONO_ENV=#{Lono.env}"
|
7
|
+
messages << "Allow envs: #{allows.join(', ')}" if allows
|
8
|
+
messages << "Deny envs: #{denys.join(', ')}" if denys
|
9
|
+
messages.join("\n")
|
10
|
+
end
|
11
|
+
|
12
|
+
# interface method
|
13
|
+
def check_value
|
14
|
+
Lono.env
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
class Lono::Builder::Allow
|
2
|
+
class Region < Base
|
3
|
+
include Lono::Concerns::AwsInfo
|
4
|
+
|
5
|
+
# interface method
|
6
|
+
def message
|
7
|
+
messages = []
|
8
|
+
word = config_name.to_s # IE: regions or locations
|
9
|
+
messages << "This #{word.singularize} is not allowed to be used: Detected current #{word.singularize}=#{current_region}"
|
10
|
+
messages << "Allow #{word}: #{allows.join(', ')}" if allows
|
11
|
+
messages << "Deny #{word}: #{denys.join(', ')}" if denys
|
12
|
+
messages.join("\n")
|
13
|
+
end
|
14
|
+
|
15
|
+
# interface method
|
16
|
+
def check_value
|
17
|
+
region
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
@@ -0,0 +1,145 @@
|
|
1
|
+
module Lono::Builder::Configset
|
2
|
+
class Combiner < Lono::CLI::Base
|
3
|
+
def initialize(options={})
|
4
|
+
super
|
5
|
+
@cfn = options[:cfn] # merge from Dsl::Finalizer::Configsets#run
|
6
|
+
@metas = options[:metas] # merge from Configset::Evaluator#evaluate
|
7
|
+
@configsets = []
|
8
|
+
@map = {} # stores resource logical id => metadata cfn-init
|
9
|
+
end
|
10
|
+
|
11
|
+
# Returns metadata map structure
|
12
|
+
#
|
13
|
+
# {"Instance"=>
|
14
|
+
# {"Metadata"=>
|
15
|
+
# {"AWS::CloudFormation::Init"=>
|
16
|
+
#
|
17
|
+
def combine
|
18
|
+
return @map if metas_empty?
|
19
|
+
add_existing
|
20
|
+
add_built
|
21
|
+
build_map # metadata map
|
22
|
+
end
|
23
|
+
|
24
|
+
def metas_empty?
|
25
|
+
@metas.empty?
|
26
|
+
end
|
27
|
+
|
28
|
+
def add_existing
|
29
|
+
existing_configsets.each do |configset|
|
30
|
+
add(configset)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def add_built
|
35
|
+
@metas.each do |meta|
|
36
|
+
definition = Definition.new(@options.merge(meta: meta))
|
37
|
+
configset = definition.evaluate
|
38
|
+
add(configset)
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
# Useful for specs
|
43
|
+
def add(configset)
|
44
|
+
found = @configsets.detect { |c| c.name == configset.name && c.resource == configset.resource }
|
45
|
+
@configsets << configset unless found
|
46
|
+
end
|
47
|
+
|
48
|
+
# Each metadata has this structure:
|
49
|
+
#
|
50
|
+
# {"Metadata"=>
|
51
|
+
# {"AWS::CloudFormation::Init"=>
|
52
|
+
# {"configSets"=>{"default"=>["aaa1", "aaa2"]},
|
53
|
+
# "aaa1"=>{"commands"=>{"test"=>{"command"=>"echo from-aaa1 > test1.txt"}}},
|
54
|
+
# "aaa2"=>
|
55
|
+
# {"commands"=>{"test"=>{"command"=>"echo from-aaa2 > test1.txt"}}}}}}
|
56
|
+
#
|
57
|
+
def build_map
|
58
|
+
metadata_map = {}
|
59
|
+
configsets_map = {}
|
60
|
+
|
61
|
+
@configsets.each_with_index do |configset, i|
|
62
|
+
padded_i = "%03d" % i
|
63
|
+
|
64
|
+
name, resource, metadata = configset.name, configset.resource, configset.metadata
|
65
|
+
configsets = configsets_map[resource] ||= {}
|
66
|
+
|
67
|
+
validate_structure!(name, metadata)
|
68
|
+
|
69
|
+
new_metadata = metadata["Metadata"].dup
|
70
|
+
init = new_metadata["AWS::CloudFormation::Init"] # important: adjust data by reference
|
71
|
+
|
72
|
+
if init.key?("configSets")
|
73
|
+
# validate_simple!(name, new_metadata["AWS::CloudFormation::Init"]["configSets"]) # validate original configset for only simple elements
|
74
|
+
|
75
|
+
# 1. expand each config as its own config, flattening to top-level
|
76
|
+
cs = init.delete("configSets") # Only support configSets with simple Array of Strings
|
77
|
+
new_config_set = {}
|
78
|
+
new_config_set[name] = cs["default"].map {|c| "#{padded_i}_#{c}" }
|
79
|
+
init.transform_keys! { |c| "#{padded_i}_#{c}" }
|
80
|
+
|
81
|
+
# Rebuild default configSet, append the new complex ConfigSet structure with each iteration
|
82
|
+
configsets["default"] ||= []
|
83
|
+
configsets["default"] << {"ConfigSet" => name}
|
84
|
+
configsets.merge!(new_config_set) # add each config from #1 to the top-level
|
85
|
+
|
86
|
+
init["configSets"] = configsets # replace new configset
|
87
|
+
else # simple config
|
88
|
+
init["configSets"] = configsets # adjust data by reference
|
89
|
+
configsets["default"] ||= []
|
90
|
+
configsets["default"] << {"ConfigSet" => name}
|
91
|
+
|
92
|
+
# build new config
|
93
|
+
config_key = "#{padded_i}_single_generated"
|
94
|
+
configsets[name] = [config_key]
|
95
|
+
new_config = {config_key => init["config"]}
|
96
|
+
# replace old config with new one
|
97
|
+
init.delete("config") # delete original simple config
|
98
|
+
init.merge!(new_config)
|
99
|
+
end
|
100
|
+
|
101
|
+
metadata_map[resource] ||= {"Metadata" => {}}
|
102
|
+
metadata_map[resource]["Metadata"].deep_merge!(new_metadata)
|
103
|
+
@map[resource] = metadata_map[resource]
|
104
|
+
end
|
105
|
+
@map
|
106
|
+
end
|
107
|
+
|
108
|
+
# Normalized/convert cfn template to mimic the registry format
|
109
|
+
def existing_configsets
|
110
|
+
configsets = []
|
111
|
+
@cfn["Resources"].each do |logical_id, attributes|
|
112
|
+
cloudformation_init = attributes.dig("Metadata", "AWS::CloudFormation::Init")
|
113
|
+
next unless cloudformation_init
|
114
|
+
|
115
|
+
configset = Lono::Configset.new(name: "#{logical_id}OriginalConfigset", resource: logical_id)
|
116
|
+
configset.metadata = {"Metadata" => attributes["Metadata"]} # wrap metadata to create right structure
|
117
|
+
configsets << configset
|
118
|
+
end
|
119
|
+
configsets
|
120
|
+
end
|
121
|
+
|
122
|
+
def validate_structure!(name, metadata)
|
123
|
+
return if metadata.is_a?(Hash) && metadata.dig("Metadata", "AWS::CloudFormation::Init")
|
124
|
+
|
125
|
+
puts "ERROR: The #{name} configset does not appear to have a AWS::CloudFormation::Init key".color(:red)
|
126
|
+
puts "Please double check the #{name} configset.yml structure"
|
127
|
+
exit 1
|
128
|
+
end
|
129
|
+
|
130
|
+
def validate_simple!(name, cs)
|
131
|
+
has_complex_type = cs["default"].detect { |s| !s.is_a?(String) }
|
132
|
+
return unless has_complex_type
|
133
|
+
message =<<~EOL
|
134
|
+
ERROR: The configset #{name} has a configSets property with a complex type.
|
135
|
+
configSets:
|
136
|
+
|
137
|
+
#{cs}
|
138
|
+
|
139
|
+
lono configsets only supports combining configSets with an Array of Strings.
|
140
|
+
EOL
|
141
|
+
puts message.color(:red)
|
142
|
+
exit 1
|
143
|
+
end
|
144
|
+
end
|
145
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
class Lono::Builder::Configset::Definition
|
2
|
+
class Base < Lono::CLI::Base
|
3
|
+
include DslEvaluator
|
4
|
+
include Lono::Builder::Dsl::Syntax
|
5
|
+
include Lono::Utils::Pretty
|
6
|
+
include Context
|
7
|
+
|
8
|
+
# Really only use @path in Configset DSL and ERB evaluation.
|
9
|
+
# However, configsets are built within the CloudFormation template and can use
|
10
|
+
# things instrinic functions like `ref` like would normally have access to.
|
11
|
+
# So configsets need the same context
|
12
|
+
#
|
13
|
+
# Configset::Definition::Base < Lono::CLI::Base
|
14
|
+
#
|
15
|
+
# for
|
16
|
+
#
|
17
|
+
# include Lono::Builder::Dsl::Syntax
|
18
|
+
#
|
19
|
+
def initialize(options={})
|
20
|
+
super
|
21
|
+
@meta = @options[:meta]
|
22
|
+
@configset = Lono::Configset.new(@meta)
|
23
|
+
expose_instance_variables
|
24
|
+
end
|
25
|
+
|
26
|
+
# This context is used by the DSL evaluation. Expose variables so user can use them in configset definitions.
|
27
|
+
# Example:
|
28
|
+
#
|
29
|
+
# "/etc/cfn/hooks.d/cfn-auto-reloader.conf":
|
30
|
+
# content:
|
31
|
+
# Fn::Sub:
|
32
|
+
# ...
|
33
|
+
# path=Resources.<%= @resource %>.Metadata.AWS::CloudFormation::Init
|
34
|
+
#
|
35
|
+
def expose_instance_variables
|
36
|
+
@name = @meta[:name]
|
37
|
+
@resource = @meta[:resource]
|
38
|
+
end
|
39
|
+
|
40
|
+
def wrap_with_metadata(cloudformation_init)
|
41
|
+
full = {"Metadata" => {}}
|
42
|
+
full["Metadata"]["AWS::CloudFormation::Init"] = cloudformation_init["AWS::CloudFormation::Init"]
|
43
|
+
full["Metadata"]["AWS::CloudFormation::Authentication"] = authentication if authentication # only on dsl
|
44
|
+
full.deep_stringify_keys.dup # metadata
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
@@ -0,0 +1,29 @@
|
|
1
|
+
class Lono::Builder::Configset::Definition
|
2
|
+
module Context
|
3
|
+
include DslEvaluator
|
4
|
+
|
5
|
+
def load_context
|
6
|
+
load_vars
|
7
|
+
load_helpers
|
8
|
+
end
|
9
|
+
|
10
|
+
# Docs: https://lono.cloud/docs/configsets/layering/
|
11
|
+
# Layering is simple enough to keep in this method.
|
12
|
+
def load_vars
|
13
|
+
logger.debug "Layers for configset #{@configset.name}:"
|
14
|
+
evaluate_layer("#{@configset.root}/vars.rb") # source defaults
|
15
|
+
evaluate_layer("#{Lono.root}/config/configsets/#{@configset.name}/vars.rb") # source overrides
|
16
|
+
evaluate_layer("#{@blueprint.root}/config/configsets/vars/#{@configset.name}.rb") # blueprint overrides
|
17
|
+
evaluate_layer("#{Lono.root}/config/blueprints/#{@blueprint.name}/configsets/vars/#{@configset.name}.rb") # user overrides
|
18
|
+
end
|
19
|
+
|
20
|
+
def evaluate_layer(path)
|
21
|
+
logger.debug " #{pretty_path(path)}" if File.exist?(path) || ENV['LONO_SHOW_ALL_LAYERS']
|
22
|
+
evaluate_file(path)
|
23
|
+
end
|
24
|
+
|
25
|
+
def load_helpers
|
26
|
+
load_helper_files("#{@configset.root}/helpers", type: :configset)
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
@@ -1,7 +1,7 @@
|
|
1
|
-
module Lono::Configset::
|
2
|
-
module
|
1
|
+
module Lono::Builder::Configset::Definition::Dsl::Syntax
|
2
|
+
module Content
|
3
3
|
def content_file(path)
|
4
|
-
content_path = "#{
|
4
|
+
content_path = "#{file_root}/content"
|
5
5
|
file = "#{content_path}/#{path}"
|
6
6
|
if File.exist?(file)
|
7
7
|
IO.read(file)
|
@@ -10,8 +10,16 @@ module Lono::Configset::Strategy::Helpers::Dsl
|
|
10
10
|
end
|
11
11
|
end
|
12
12
|
|
13
|
+
def file_root
|
14
|
+
if @configset
|
15
|
+
@configset.root
|
16
|
+
else
|
17
|
+
@blueprint.root
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
13
21
|
def s3_key(name)
|
14
|
-
Lono::Configset::S3File::Registry.register(name, blueprint: @blueprint
|
22
|
+
Lono::Configset::S3File::Registry.register(name, blueprint: @blueprint, configset: @configset, root: @root)
|
15
23
|
"file://configset/#{@configset}/#{name}"
|
16
24
|
end
|
17
25
|
end
|
@@ -1,7 +1,20 @@
|
|
1
|
-
module Lono::Configset::
|
2
|
-
module
|
1
|
+
module Lono::Builder::Configset::Definition::Dsl::Syntax
|
2
|
+
module Core
|
3
3
|
extend Memoist
|
4
4
|
|
5
|
+
#
|
6
|
+
# The configset method is different with configset registration vs configset definition
|
7
|
+
#
|
8
|
+
# definition: app/configsets/httpd/configset.rb
|
9
|
+
# registration: app/blueprints/demo/configsets.rb
|
10
|
+
#
|
11
|
+
def configset(current)
|
12
|
+
@tracked << current
|
13
|
+
previous, @current = @current, current
|
14
|
+
yield
|
15
|
+
@current = previous
|
16
|
+
end
|
17
|
+
|
5
18
|
%w[package group user file service].each do |meth|
|
6
19
|
section = meth.pluralize
|
7
20
|
define_method(meth) do |k, props={}|
|
@@ -53,13 +66,6 @@ module Lono::Configset::Strategy::Helpers::Dsl
|
|
53
66
|
current_structure(@current)["sources"].deep_merge!(item)
|
54
67
|
end
|
55
68
|
|
56
|
-
def configset(current)
|
57
|
-
@tracked << current
|
58
|
-
previous, @current = @current, current
|
59
|
-
yield
|
60
|
-
@current = previous
|
61
|
-
end
|
62
|
-
|
63
69
|
private
|
64
70
|
def current_structure(configset)
|
65
71
|
@structure[configset] ||= {}
|