config_templates 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 5de2246c3e82a63bc34895e45b8a985ff1150745
4
+ data.tar.gz: 8282e90119c9857e119e8a0d73c3134f46a0171c
5
+ SHA512:
6
+ metadata.gz: 9b4e153ab13492fe3a75954fab318987d91ce2f23ceffddac93eabc22e2d4bf76ae1eee43052ee5188e67f0e7dcefc172843298e01fe922b405f5a8e592f1c33
7
+ data.tar.gz: d973e1a75bdf5457420d68a0c5f6448e82709c1450d4d17c52b0a4f7e2a3a027ea141113158fecf3f00f924099013838d11c0907646bd0b4441de3020a5e97cf
data/lib/autoload.rb ADDED
@@ -0,0 +1,14 @@
1
+ require 'yaml'
2
+ require 'fileutils'
3
+
4
+ module ConfigTemplates
5
+ module Contexts; end
6
+ module Criteria; end
7
+ module Engines; end
8
+ module Models; end
9
+ module Outputs; end
10
+ module Repositories; end
11
+ module Validators; end
12
+ end
13
+
14
+ Dir[File.join(File.dirname(__FILE__), 'config_templates', '**', '*.rb')].each { |path| require path }
@@ -0,0 +1,38 @@
1
+ module ConfigTemplates
2
+ class Config
3
+ attr_accessor :templates_path, :destination_path
4
+ attr_accessor :settings_path, :settings_file_basename
5
+ attr_accessor :stage, :stages
6
+
7
+ def initialize
8
+ @stages = []
9
+ @outputs = ::ConfigTemplates::Repositories::Outputs.new
10
+ @engines = ::ConfigTemplates::Repositories::Engines.new
11
+ @validators = ::ConfigTemplates::Repositories::Validators.new
12
+ end
13
+
14
+ def output(name)
15
+ @outputs.find_by_name name
16
+ end
17
+
18
+ def outputs(outputs)
19
+ @outputs.add outputs
20
+ end
21
+
22
+ def engine(extension)
23
+ @engines.find_by_extension extension
24
+ end
25
+
26
+ def engines(engines)
27
+ @engines.add engines
28
+ end
29
+
30
+ def validator(file_name)
31
+ @validators.find_by_file_name file_name
32
+ end
33
+
34
+ def validators(validators)
35
+ @validators.add validators
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,25 @@
1
+ module ConfigTemplates::Contexts
2
+ class Compilation
3
+ def initialize
4
+ @templates = ::ConfigTemplates::Repositories::Templates.new
5
+ @settings = ::ConfigTemplates::Repositories::Settings.new
6
+ @criteria = ::ConfigTemplates::Criteria::Composite.new
7
+ end
8
+
9
+ def criteria(criteria)
10
+ @criteria = ::ConfigTemplates::Criteria::Composite.new @criteria, criteria
11
+ end
12
+
13
+ def renderers
14
+ @templates.find_all_by(@criteria).map do |template|
15
+ ::ConfigTemplates::Models::Renderer.new template, renderer_context
16
+ end
17
+ end
18
+
19
+ private
20
+
21
+ def renderer_context
22
+ ::ConfigTemplates::Contexts::Renderer.new @settings
23
+ end
24
+ end
25
+ end
@@ -0,0 +1,34 @@
1
+ module ConfigTemplates::Contexts
2
+ class Renderer
3
+ def initialize(settings)
4
+ @settings = settings
5
+ @config = ::ConfigTemplates.config
6
+ end
7
+
8
+ def param(path, default = nil)
9
+ path.split('.').inject(@settings.find_all) { |value, current| value[current] }
10
+ rescue
11
+ default
12
+ end
13
+
14
+ def method_missing(method_name)
15
+ stage_request = method_name[-1] == '?'
16
+ stage = method_name[0..-2] if stage_request
17
+ stage.nil? ? super : stage?(stage)
18
+ end
19
+
20
+ def respond_to_missing?(method_name)
21
+ method_name[-1] == '?' || super
22
+ end
23
+
24
+ private
25
+
26
+ def stage?(stage)
27
+ if @config.stages.include?(stage.to_sym)
28
+ @config.stage == stage.to_sym
29
+ else
30
+ raise ::ConfigTemplates::Errors::StageNotFound, stage
31
+ end
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,13 @@
1
+ module ConfigTemplates::Criteria
2
+ class Composite
3
+ def initialize(*criteria)
4
+ @criteria = criteria
5
+ end
6
+
7
+ def matches?(target)
8
+ @criteria.inject(true) do |result, criteria|
9
+ result && criteria.matches?(target)
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,12 @@
1
+ module ConfigTemplates::Criteria
2
+ class Name
3
+ def initialize(pattern, override = true)
4
+ @pattern = pattern
5
+ @override = override
6
+ end
7
+
8
+ def matches?(target)
9
+ @pattern.match?(target) && @override
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,7 @@
1
+ module ConfigTemplates::Engines
2
+ class ERB
3
+ def evaluate(template, context)
4
+ ::ERB.new(template).result(context.instance_eval { binding })
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,7 @@
1
+ module ConfigTemplates::Engines
2
+ class Text
3
+ def evaluate(template, _)
4
+ template
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,5 @@
1
+ module ConfigTemplates::Errors
2
+ class EngineNotFound < RuntimeError; end
3
+ class StageNotFound < RuntimeError; end
4
+ class InvalidTemplate < RuntimeError; end
5
+ end
@@ -0,0 +1,18 @@
1
+ module ConfigTemplates
2
+ class FileLocator
3
+ def initialize
4
+ @config = ::ConfigTemplates.config
5
+ end
6
+
7
+ def templates
8
+ ::Dir[::File.join(@config.templates_path, '**', '*')].lazy.select { |path| ::File.file? path }
9
+ end
10
+
11
+ def settings
12
+ ::Dir[
13
+ ::File.join(@config.settings_path, "#{@config.settings_file_basename}.yml"),
14
+ ::File.join(@config.settings_path, "#{@config.settings_file_basename}.#{@config.stage}.yml")
15
+ ]
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,26 @@
1
+ module ConfigTemplates::Models
2
+ class Compilation
3
+ def initialize
4
+ @config = ::ConfigTemplates.config
5
+ @context = ::ConfigTemplates::Contexts::Compilation.new
6
+ end
7
+
8
+ def select(expression)
9
+ @context.criteria ::ConfigTemplates::Criteria::Name.new expression
10
+ self
11
+ end
12
+
13
+ def reject(expression)
14
+ @context.criteria ::ConfigTemplates::Criteria::Name.new expression, false
15
+ self
16
+ end
17
+
18
+ def send_to(output_name)
19
+ @context.renderers.each do |renderer|
20
+ renderer.validate!
21
+ output = @config.output output_name
22
+ output.print renderer
23
+ end
24
+ end
25
+ end
26
+ end
@@ -0,0 +1,18 @@
1
+ module ConfigTemplates::Models
2
+ class Renderer
3
+ attr_reader :template
4
+
5
+ def initialize(template, context)
6
+ @template = template
7
+ @context = context
8
+ end
9
+
10
+ def validate!
11
+ @template.validator.validate! render
12
+ end
13
+
14
+ def render
15
+ @render ||= @template.engine.evaluate @template.content, @context
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,32 @@
1
+ module ConfigTemplates::Models
2
+ class Template
3
+ def initialize(path)
4
+ @path = path
5
+ @config = ::ConfigTemplates.config
6
+ end
7
+
8
+ def content
9
+ @content ||= ::File.read @path
10
+ end
11
+
12
+ def extension
13
+ ::File.extname @path
14
+ end
15
+
16
+ def destination
17
+ ::File.join(
18
+ @config.destination_path,
19
+ @config.stage.to_s,
20
+ @path.sub(@config.templates_path, '').sub(extension, '')
21
+ )
22
+ end
23
+
24
+ def validator
25
+ @config.validator @path
26
+ end
27
+
28
+ def engine
29
+ @config.engine extension
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,9 @@
1
+ module ConfigTemplates::Outputs
2
+ class Filesystem
3
+ def print(renderer)
4
+ destination = renderer.template.destination
5
+ ::FileUtils.mkdir_p ::File.dirname destination
6
+ ::File.write destination, renderer.render
7
+ end
8
+ end
9
+ end
@@ -0,0 +1,7 @@
1
+ module ConfigTemplates::Outputs
2
+ class Stdout
3
+ def print(renderer)
4
+ ::Kernel.puts renderer.render
5
+ end
6
+ end
7
+ end
@@ -0,0 +1,22 @@
1
+ module ConfigTemplates::Repositories
2
+ class Engines
3
+ def initialize
4
+ @default = ::ConfigTemplates::Engines::Text.new
5
+ @engines = { /^.*\.erb$/ => ::ConfigTemplates::Engines::ERB.new }
6
+ end
7
+
8
+ def add(engines)
9
+ @engines.merge! engines
10
+ end
11
+
12
+ def find_by_extension(extension)
13
+ find_by ::ConfigTemplates::Criteria::Name.new extension
14
+ end
15
+
16
+ def find_by(criteria)
17
+ @engines.select { |(k, _)| criteria.matches?(k) }.first.last
18
+ rescue
19
+ @default
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,19 @@
1
+ module ConfigTemplates::Repositories
2
+ class Outputs
3
+ def initialize
4
+ @default = :stdout
5
+ @outputs = {
6
+ stdout: ::ConfigTemplates::Outputs::Stdout.new,
7
+ filesystem: ::ConfigTemplates::Outputs::Filesystem.new
8
+ }
9
+ end
10
+
11
+ def add(outputs)
12
+ @outputs.merge! outputs
13
+ end
14
+
15
+ def find_by_name(name)
16
+ @outputs.fetch(name) { @outputs[@default] }
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,13 @@
1
+ module ConfigTemplates::Repositories
2
+ class Settings
3
+ def initialize
4
+ @locator = ::ConfigTemplates::FileLocator.new
5
+ end
6
+
7
+ def find_all
8
+ @find_all ||= @locator.settings.reduce({}) {
9
+ |result, current| result.merge ::YAML.load_file current
10
+ }
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,13 @@
1
+ module ConfigTemplates::Repositories
2
+ class Templates
3
+ def initialize
4
+ @locator = ::ConfigTemplates::FileLocator.new
5
+ end
6
+
7
+ def find_all_by(criteria)
8
+ @locator.templates
9
+ .select { |filename| criteria.matches? filename }
10
+ .map { |filename| ::ConfigTemplates::Models::Template.new filename }
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,22 @@
1
+ module ConfigTemplates::Repositories
2
+ class Validators
3
+ def initialize
4
+ @default = ::ConfigTemplates::Validators::Composite.new
5
+ @validators = {}
6
+ end
7
+
8
+ def add(validators)
9
+ @validators.merge! validators
10
+ end
11
+
12
+ def find_by_file_name(file_name)
13
+ ::ConfigTemplates::Validators::Composite.new(
14
+ *find_all_by(::ConfigTemplates::Criteria::Name.new(file_name))
15
+ )
16
+ end
17
+
18
+ def find_all_by(criteria)
19
+ @validators.select { |(k, _)| criteria.matches?(k) }.values
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,11 @@
1
+ module ConfigTemplates::Validators
2
+ class Composite
3
+ def initialize(*validators)
4
+ @validators = validators
5
+ end
6
+
7
+ def validate!(result)
8
+ @validators.each { |validator| validator.validate! result }
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,3 @@
1
+ module ConfigTemplates
2
+ VERSION = '0.0.1'.freeze
3
+ end
@@ -0,0 +1,13 @@
1
+ require_relative 'autoload'
2
+
3
+ module ConfigTemplates
4
+ class << self
5
+ def configure
6
+ yield config
7
+ end
8
+
9
+ def config
10
+ @config ||= Config.new
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,2 @@
1
+ test:
2
+ value: true
@@ -0,0 +1,2 @@
1
+ test:
2
+ value: false
@@ -0,0 +1,3 @@
1
+ <% if production? %>
2
+ <%= param('test.value') %>
3
+ <% end %>
@@ -0,0 +1,11 @@
1
+ module Mocks
2
+ module Outputs
3
+ class Test
4
+ attr_accessor :result
5
+
6
+ def print(renderer)
7
+ @result = renderer.render
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,14 @@
1
+ require_relative './mocks/outputs/test'
2
+
3
+ RSpec.configure do |spec|
4
+ spec.before(:all) do
5
+ ::ConfigTemplates.configure do |config|
6
+ config.templates_path = 'spec/fixtures/src'
7
+ config.destination_path = 'spec/fixtures/dest'
8
+ config.settings_path = 'spec/fixtures/settings'
9
+ config.settings_file_basename = 'settings'
10
+ config.stage = :production
11
+ config.stages = %i[production prerel staging]
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,29 @@
1
+ require 'config_templates'
2
+ require 'spec_helper'
3
+
4
+ RSpec.describe ::ConfigTemplates do
5
+ before(:all) { @output_mock = ::Mocks::Outputs::Test.new }
6
+ before(:all) do
7
+ ::ConfigTemplates.configure { |config| config.outputs test: @output_mock }
8
+ end
9
+
10
+ before(:each) { @output_mock.result = nil }
11
+
12
+ it 'renders selected template using configs and environment metadata' do
13
+ compilation = ::ConfigTemplates::Models::Compilation.new
14
+ compilation.select(/.*/).send_to(:test)
15
+ expect(@output_mock.result.strip).to eq('true')
16
+ end
17
+
18
+ it 'doesnt render not selected template' do
19
+ compilation = ::ConfigTemplates::Models::Compilation.new
20
+ compilation.reject(/.*/).send_to(:test)
21
+ expect(@output_mock.result).to be_nil
22
+ end
23
+
24
+ it 'renders without explicitly selected templates' do
25
+ compilation = ::ConfigTemplates::Models::Compilation.new
26
+ compilation.send_to(:test)
27
+ expect(@output_mock.result.strip).to eq('true')
28
+ end
29
+ end
metadata ADDED
@@ -0,0 +1,134 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: config_templates
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1
5
+ platform: ruby
6
+ authors:
7
+ - g.ivanov
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2018-03-29 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: bundler
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: '0'
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: '0'
27
+ - !ruby/object:Gem::Dependency
28
+ name: rake
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :runtime
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rspec
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '0'
48
+ type: :runtime
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ - !ruby/object:Gem::Dependency
56
+ name: rspec_junit_formatter
57
+ requirement: !ruby/object:Gem::Requirement
58
+ requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: '0'
62
+ type: :runtime
63
+ prerelease: false
64
+ version_requirements: !ruby/object:Gem::Requirement
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: '0'
69
+ description: config_templates
70
+ email:
71
+ - g.ivanov@fun-box.ru
72
+ executables: []
73
+ extensions: []
74
+ extra_rdoc_files: []
75
+ files:
76
+ - lib/autoload.rb
77
+ - lib/config_templates.rb
78
+ - lib/config_templates/config.rb
79
+ - lib/config_templates/contexts/compilation.rb
80
+ - lib/config_templates/contexts/renderer.rb
81
+ - lib/config_templates/criteria/composite.rb
82
+ - lib/config_templates/criteria/name.rb
83
+ - lib/config_templates/engines/erb.rb
84
+ - lib/config_templates/engines/text.rb
85
+ - lib/config_templates/errors.rb
86
+ - lib/config_templates/file_locator.rb
87
+ - lib/config_templates/models/compilation.rb
88
+ - lib/config_templates/models/renderer.rb
89
+ - lib/config_templates/models/template.rb
90
+ - lib/config_templates/outputs/filesystem.rb
91
+ - lib/config_templates/outputs/stdout.rb
92
+ - lib/config_templates/repositories/engines.rb
93
+ - lib/config_templates/repositories/outputs.rb
94
+ - lib/config_templates/repositories/settings.rb
95
+ - lib/config_templates/repositories/templates.rb
96
+ - lib/config_templates/repositories/validators.rb
97
+ - lib/config_templates/validators/composite.rb
98
+ - lib/config_templates/version.rb
99
+ - spec/fixtures/settings/settings.production.yml
100
+ - spec/fixtures/settings/settings.yml
101
+ - spec/fixtures/src/kapacitor/config.erb
102
+ - spec/mocks/outputs/test.rb
103
+ - spec/spec_helper.rb
104
+ - spec/templates_spec.rb
105
+ homepage:
106
+ licenses: []
107
+ metadata: {}
108
+ post_install_message:
109
+ rdoc_options: []
110
+ require_paths:
111
+ - lib
112
+ required_ruby_version: !ruby/object:Gem::Requirement
113
+ requirements:
114
+ - - ">="
115
+ - !ruby/object:Gem::Version
116
+ version: '0'
117
+ required_rubygems_version: !ruby/object:Gem::Requirement
118
+ requirements:
119
+ - - ">="
120
+ - !ruby/object:Gem::Version
121
+ version: '0'
122
+ requirements: []
123
+ rubyforge_project:
124
+ rubygems_version: 2.6.13
125
+ signing_key:
126
+ specification_version: 4
127
+ summary: config_templates
128
+ test_files:
129
+ - spec/fixtures/src/kapacitor/config.erb
130
+ - spec/fixtures/settings/settings.yml
131
+ - spec/fixtures/settings/settings.production.yml
132
+ - spec/mocks/outputs/test.rb
133
+ - spec/templates_spec.rb
134
+ - spec/spec_helper.rb