producer-core 0.1.6 → 0.1.7

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 69bc1d881cfd85eea00037b60c396d9b09bf7bdd
4
- data.tar.gz: 6d440b7bd0beb137b073d00c2096222bb7f2b58a
3
+ metadata.gz: 459e9b701305da92f97559b14552a99a244d3df2
4
+ data.tar.gz: 9803a517b543aba2e7f7eb23de3eb59eee7696df
5
5
  SHA512:
6
- metadata.gz: 837737ed2a5bc77959a9c0e7c8295acdc7a997884a63fd286035cb9d811191ac7097d93ed5fb3e24c0c8c0afe22db4d05ca6b45afefcc4f5a69af34da3595e74
7
- data.tar.gz: 098654fa4620affd4eac4b89fb8906a57537c13b134b9ab8c1a47e48cff83cce96d48b8cdbeed4cd50df2de4e95fbdfa7cd9589c4f5be04dedee3810630cc26d
6
+ metadata.gz: 027259efb32585c69b5f05c8aac66a8b5917037b33f4d82ea727eb8946a897229e4e546c1e395b27a7dd501321fdc247bccb475a03146c4227ed850045cdc5ca
7
+ data.tar.gz: 2aa5aa800650d057e0a6b13aca136c56c615c8d572879dc56d010bacf97fe4b5d0607b8b96af3f576d6b002eac3b045a07d4f2ba90dce6d6771f9823001b1a8b
@@ -0,0 +1,40 @@
1
+ Feature: `macro' recipe keyword
2
+
3
+ Scenario: declares new keyword accepting task code
4
+ Given a recipe with:
5
+ """
6
+ macro :hello do
7
+ echo 'hello macro'
8
+ end
9
+
10
+ hello
11
+ """
12
+ When I successfully execute the recipe
13
+ Then the output must contain "hello macro"
14
+
15
+ Scenario: supports arguments
16
+ Given a recipe with:
17
+ """
18
+ macro :my_echo do |kind, message|
19
+ echo "#{kind}: #{message}"
20
+ end
21
+
22
+ my_echo 'my', 'hello'
23
+ """
24
+ When I successfully execute the recipe
25
+ Then the output must contain "my: hello"
26
+
27
+ Scenario: supports arguments in conditions
28
+ Given a recipe with:
29
+ """
30
+ macro :my_echo do |message|
31
+ condition { message =~ /bar/ }
32
+
33
+ echo message
34
+ end
35
+
36
+ %w[foo bar].each { |e| my_echo e }
37
+ """
38
+ When I successfully execute the recipe
39
+ Then the output must not contain "foo"
40
+ And the output must contain "bar"
@@ -1,10 +1,10 @@
1
1
  module Producer
2
2
  module Core
3
3
  class CLI
4
- attr_reader :arguments
5
-
6
4
  USAGE = "Usage: #{File.basename $0} recipe_file"
7
5
 
6
+ attr_reader :arguments
7
+
8
8
  def initialize(arguments, stdout = $stdout)
9
9
  @stdout = stdout
10
10
  @arguments = arguments
@@ -3,7 +3,9 @@ module Producer
3
3
  class Condition
4
4
  class << self
5
5
  def evaluate(env, &block)
6
- DSL.evaluate(env, &block)
6
+ dsl = DSL.new(env, &block)
7
+ return_value = dsl.evaluate
8
+ Condition.new(dsl.tests, return_value)
7
9
  end
8
10
  end
9
11
 
@@ -3,12 +3,6 @@ module Producer
3
3
  class Condition
4
4
  class DSL
5
5
  class << self
6
- def evaluate(env, &block)
7
- dsl = new(env, &block)
8
- return_value = dsl.evaluate
9
- Condition.new(dsl.tests, return_value)
10
- end
11
-
12
6
  def define_test(keyword, klass)
13
7
  define_method(keyword) do |*args|
14
8
  @tests << klass.new(@env, *args)
@@ -1,12 +1,15 @@
1
1
  module Producer
2
2
  module Core
3
3
  class Recipe
4
- attr_accessor :tasks
5
-
6
- def self.evaluate_from_file(filepath, env)
7
- DSL.evaluate(File.read(filepath), env)
4
+ class << self
5
+ def evaluate_from_file(filepath, env)
6
+ dsl = DSL.new(File.read(filepath)).evaluate(env)
7
+ Recipe.new(dsl.tasks)
8
+ end
8
9
  end
9
10
 
11
+ attr_accessor :tasks
12
+
10
13
  def initialize(tasks = [])
11
14
  @tasks = tasks
12
15
  end
@@ -4,11 +4,6 @@ module Producer
4
4
  class DSL
5
5
  attr_reader :tasks
6
6
 
7
- def self.evaluate(code, env)
8
- dsl = new(code).evaluate(env)
9
- Recipe.new(dsl.tasks)
10
- end
11
-
12
7
  def initialize(code = nil, &block)
13
8
  @code = code
14
9
  @block = block
@@ -39,8 +34,14 @@ module Producer
39
34
  env.target = hostname
40
35
  end
41
36
 
42
- def task(name, &block)
43
- @tasks << Task.evaluate(name, env, &block)
37
+ def task(name, *args, &block)
38
+ @tasks << Task.evaluate(name, env, *args, &block)
39
+ end
40
+
41
+ def macro(name, &block)
42
+ define_singleton_method(name) do |*args|
43
+ task("#{name}", *args, &block)
44
+ end
44
45
  end
45
46
  end
46
47
  end
@@ -34,7 +34,7 @@ module Producer
34
34
  output << data
35
35
  end
36
36
 
37
- ch.on_request('exit-status') do |c, data|
37
+ ch.on_request 'exit-status' do |c, data|
38
38
  exit_status = data.read_long
39
39
  raise RemoteCommandExecutionError if exit_status != 0
40
40
  end
@@ -1,12 +1,16 @@
1
1
  module Producer
2
2
  module Core
3
3
  class Task
4
- attr_reader :name, :actions, :condition
5
-
6
- def self.evaluate(name, env, &block)
7
- DSL.evaluate(name, env, &block)
4
+ class << self
5
+ def evaluate(name, env, *args, &block)
6
+ dsl = DSL.new(&block)
7
+ dsl.evaluate(env, *args)
8
+ Task.new(name, dsl.actions, dsl.condition)
9
+ end
8
10
  end
9
11
 
12
+ attr_reader :name, :actions, :condition
13
+
10
14
  def initialize(name, actions = [], condition = true)
11
15
  @name = name
12
16
  @actions = actions
@@ -3,12 +3,6 @@ module Producer
3
3
  class Task
4
4
  class DSL
5
5
  class << self
6
- def evaluate(name, env, &block)
7
- dsl = new(&block)
8
- dsl.evaluate(env)
9
- Task.new(name, dsl.actions, dsl.condition)
10
- end
11
-
12
6
  def define_action(keyword, klass)
13
7
  define_method(keyword) do |*args|
14
8
  @actions << klass.new(@env, *args)
@@ -29,9 +23,9 @@ module Producer
29
23
  @condition = true
30
24
  end
31
25
 
32
- def evaluate(env)
26
+ def evaluate(env, *args)
33
27
  @env = env
34
- instance_eval &@block
28
+ instance_exec *args, &@block
35
29
  end
36
30
 
37
31
  def condition(&block)
@@ -1,5 +1,5 @@
1
1
  module Producer
2
2
  module Core
3
- VERSION = '0.1.6'
3
+ VERSION = '0.1.7'
4
4
  end
5
5
  end
@@ -12,33 +12,6 @@ module Producer::Core
12
12
  end
13
13
  end
14
14
 
15
- describe '.evaluate' do
16
- it 'builds a new DSL sandbox with given env and code' do
17
- expect(Condition::DSL)
18
- .to receive(:new).with(env, &block).and_call_original
19
- Condition::DSL.evaluate(env, &block)
20
- end
21
-
22
- it 'evaluates the DSL sandbox code' do
23
- dsl = double('dsl').as_null_object
24
- allow(Condition::DSL).to receive(:new) { dsl }
25
- expect(dsl).to receive :evaluate
26
- Condition::DSL.evaluate(env, &block)
27
- end
28
-
29
- it 'builds a condition with its test and block return value' do
30
- expect(Condition)
31
- .to receive(:new).with(dsl.tests, :some_condition_code)
32
- Condition::DSL.evaluate(env, &block)
33
- end
34
-
35
- it 'returns the condition' do
36
- condition = double 'task'
37
- allow(Condition).to receive(:new) { condition }
38
- expect(Condition::DSL.evaluate(env, &block)).to be condition
39
- end
40
- end
41
-
42
15
  describe '.define_test' do
43
16
  let(:some_test_class) { double 'SomeTest class' }
44
17
 
@@ -11,17 +11,28 @@ module Producer::Core
11
11
  let(:env) { double 'env' }
12
12
  let(:block) { proc { :some_condition_code } }
13
13
 
14
- it 'delegates to DSL.evaluate' do
14
+ it 'builds a new DSL sandbox with given env and code' do
15
15
  expect(Condition::DSL)
16
- .to receive(:evaluate).with(env) do |&b|
17
- expect(b).to be block
18
- end
16
+ .to receive(:new).with(env, &block).and_call_original
17
+ Condition.evaluate(env, &block)
18
+ end
19
+
20
+ it 'evaluates the DSL sandbox code' do
21
+ dsl = double('dsl').as_null_object
22
+ allow(Condition::DSL).to receive(:new) { dsl }
23
+ expect(dsl).to receive :evaluate
24
+ Condition.evaluate(env, &block)
25
+ end
26
+
27
+ it 'builds a condition with its test and block return value' do
28
+ expect(Condition)
29
+ .to receive(:new).with([], :some_condition_code)
19
30
  Condition.evaluate(env, &block)
20
31
  end
21
32
 
22
- it 'returns the evaluated condition' do
23
- condition = double 'condition'
24
- allow(Condition::DSL).to receive(:evaluate) { condition }
33
+ it 'returns the condition' do
34
+ condition = double 'task'
35
+ allow(Condition).to receive(:new) { condition }
25
36
  expect(Condition.evaluate(env, &block)).to be condition
26
37
  end
27
38
  end
@@ -8,35 +8,6 @@ module Producer::Core
8
8
  let(:env) { double('env').as_null_object }
9
9
  subject(:dsl) { Recipe::DSL.new(&code) }
10
10
 
11
- describe '.evaluate' do
12
- let(:code) { 'nil' }
13
-
14
- it 'builds a new DSL sandbox with given code as string' do
15
- expect(Recipe::DSL).to receive(:new).with(code).and_call_original
16
- Recipe::DSL.evaluate(code, env)
17
- end
18
-
19
- it 'evaluates the DSL sandbox code with given environment' do
20
- dsl = double('dsl').as_null_object
21
- allow(Recipe::DSL).to receive(:new) { dsl }
22
- expect(dsl).to receive(:evaluate).with(env)
23
- Recipe::DSL.evaluate(code, env)
24
- end
25
-
26
- it 'builds a recipe with evaluated tasks' do
27
- dsl = Recipe::DSL.new { task(:some_task) { } }
28
- allow(Recipe::DSL).to receive(:new) { dsl }
29
- expect(Recipe).to receive(:new).with(dsl.tasks)
30
- Recipe::DSL.evaluate(code, env)
31
- end
32
-
33
- it 'returns the recipe' do
34
- recipe = double('recipe').as_null_object
35
- allow(Recipe).to receive(:new) { recipe }
36
- expect(Recipe::DSL.evaluate(code, env)).to be recipe
37
- end
38
- end
39
-
40
11
  describe '#initialize' do
41
12
  it 'assigns no task' do
42
13
  expect(dsl.instance_eval { @tasks }).to be_empty
@@ -110,11 +81,11 @@ module Producer::Core
110
81
  end
111
82
 
112
83
  describe '#task' do
113
- let(:code) { proc { task(:some_task) { :some_value } } }
84
+ let(:code) { proc { task(:some_task, :some, :arg) { :some_value } } }
114
85
 
115
86
  it 'builds a new evaluated task' do
116
87
  expect(Task)
117
- .to receive(:evaluate).with(:some_task, env) do |&b|
88
+ .to receive(:evaluate).with(:some_task, env, :some, :arg) do |&b|
118
89
  expect(b.call).to eq :some_value
119
90
  end
120
91
  dsl
@@ -126,6 +97,30 @@ module Producer::Core
126
97
  expect(dsl.tasks).to include(task)
127
98
  end
128
99
  end
100
+
101
+ describe '#macro' do
102
+ let(:code) { proc { macro(:hello) { echo 'hello' } } }
103
+
104
+ it 'defines the new recipe keyword' do
105
+ expect(dsl).to respond_to(:hello)
106
+ end
107
+
108
+ context 'when the new keyword is called' do
109
+ let(:code) { proc { macro(:hello) { echo 'hello' }; hello } }
110
+
111
+ it 'registers the new task' do
112
+ expect(dsl.tasks.first.actions.first).to be_an Actions::Echo
113
+ end
114
+ end
115
+
116
+ context 'when macro takes arguments' do
117
+ let(:code) { proc { macro(:hello) { |e| echo e }; hello :arg } }
118
+
119
+ it 'evaluates task code with arguments' do
120
+ expect(dsl.tasks.first.actions.first.arguments.first).to be :arg
121
+ end
122
+ end
123
+ end
129
124
  end
130
125
  end
131
126
  end
@@ -9,18 +9,33 @@ module Producer::Core
9
9
  describe '.evaluate_from_file' do
10
10
  let(:env) { double 'env' }
11
11
  let(:filepath) { fixture_path_for 'recipes/empty.rb' }
12
+ let(:code) { File.read(filepath) }
12
13
 
13
- it 'delegates to DSL.evaluate with the recipe file content' do
14
- expect(Recipe::DSL)
15
- .to receive(:evaluate).with(File.read(filepath), env)
14
+ it 'builds a new DSL sandbox with code read from given file path' do
15
+ expect(Recipe::DSL).to receive(:new).with(code).and_call_original
16
16
  Recipe.evaluate_from_file(filepath, env)
17
17
  end
18
18
 
19
- it 'returns the evaluated recipe' do
20
- recipe = double 'recipe'
21
- allow(Recipe::DSL).to receive(:evaluate) { recipe }
19
+ it 'evaluates the DSL sandbox code with given environment' do
20
+ dsl = double('dsl').as_null_object
21
+ allow(Recipe::DSL).to receive(:new) { dsl }
22
+ expect(dsl).to receive(:evaluate).with(env)
23
+ Recipe.evaluate_from_file(filepath, env)
24
+ end
25
+
26
+ it 'builds a recipe with evaluated tasks' do
27
+ dsl = Recipe::DSL.new { task(:some_task) { } }
28
+ allow(Recipe::DSL).to receive(:new) { dsl }
29
+ expect(Recipe).to receive(:new).with(dsl.tasks)
30
+ Recipe.evaluate_from_file(filepath, env)
31
+ end
32
+
33
+ it 'returns the recipe' do
34
+ recipe = double('recipe').as_null_object
35
+ allow(Recipe).to receive(:new) { recipe }
22
36
  expect(Recipe.evaluate_from_file(filepath, env)).to be recipe
23
37
  end
38
+
24
39
  end
25
40
 
26
41
  describe '#initialize' do
@@ -12,42 +12,6 @@ module Producer::Core
12
12
  end
13
13
  end
14
14
 
15
- describe '.evaluate' do
16
- let(:name) { :some_task }
17
-
18
- it 'builds a new DSL sandbox with given code' do
19
- dsl = double('dsl').as_null_object
20
- expect(Task::DSL).to receive(:new).with(no_args) do |&b|
21
- expect(b).to be block
22
- dsl
23
- end
24
- Task::DSL.evaluate(name, env, &block)
25
- end
26
-
27
- it 'evaluates the DSL sandbox code with given environment' do
28
- dsl = double('dsl').as_null_object
29
- allow(Task::DSL).to receive(:new) { dsl }
30
- expect(dsl).to receive(:evaluate).with(env)
31
- Task::DSL.evaluate(name, env, &block)
32
- end
33
-
34
- it 'builds a task with its name, actions and condition' do
35
- dsl = double(
36
- 'dsl', actions: [:some_action], condition: :some_condition
37
- ).as_null_object
38
- allow(Task::DSL).to receive(:new) { dsl }
39
- expect(Task)
40
- .to receive(:new).with(:some_task, [:some_action], :some_condition)
41
- Task::DSL.evaluate(name, env, &block)
42
- end
43
-
44
- it 'returns the task' do
45
- task = double 'task'
46
- allow(Task).to receive(:new) { task }
47
- expect(Task::DSL.evaluate(name, env, &block)).to be task
48
- end
49
- end
50
-
51
15
  describe '.define_action' do
52
16
  it 'defines a new action keyword' do
53
17
  Task::DSL.define_action(:some_action, Object)
@@ -89,6 +53,15 @@ module Producer::Core
89
53
  .to throw_symbol :task_code
90
54
  end
91
55
 
56
+ context 'when arguments are given' do
57
+ let(:block) { proc { |e| throw e } }
58
+
59
+ it 'passes arguments as block parameters' do
60
+ expect { dsl.evaluate env, :some_argument }
61
+ .to throw_symbol :some_argument
62
+ end
63
+ end
64
+
92
65
  context 'when a defined keyword action is called' do
93
66
  let(:some_action_class) { Class.new(Action) }
94
67
  let(:block) { proc { some_action } }
@@ -9,20 +9,39 @@ module Producer::Core
9
9
 
10
10
  describe '.evaluate' do
11
11
  let(:env) { double 'env' }
12
+ let(:args) { [:some, :arguments] }
12
13
  let(:block) { proc { :some_task_code } }
13
14
 
14
- it 'delegates to DSL.evaluate' do
15
- expect(Task::DSL)
16
- .to receive(:evaluate).with(name, env) do |&b|
17
- expect(b).to be block
18
- end
19
- Task.evaluate(name, env, &block)
15
+ it 'builds a new DSL sandbox with given code' do
16
+ dsl = double('dsl').as_null_object
17
+ expect(Task::DSL).to receive(:new).with(no_args) do |&b|
18
+ expect(b).to be block
19
+ dsl
20
+ end
21
+ Task.evaluate(name, env, *args, &block)
22
+ end
23
+
24
+ it 'evaluates the DSL sandbox code with given environment' do
25
+ dsl = double('dsl').as_null_object
26
+ allow(Task::DSL).to receive(:new) { dsl }
27
+ expect(dsl).to receive(:evaluate).with(env, *args)
28
+ Task.evaluate(name, env, *args, &block)
29
+ end
30
+
31
+ it 'builds the task with its name, actions and condition' do
32
+ dsl = double(
33
+ 'dsl', actions: [:some_action], condition: :some_condition
34
+ ).as_null_object
35
+ allow(Task::DSL).to receive(:new) { dsl }
36
+ expect(Task)
37
+ .to receive(:new).with(:some_task, [:some_action], :some_condition)
38
+ Task.evaluate(name, env, *args, &block)
20
39
  end
21
40
 
22
- it 'returns the evaluated task' do
41
+ it 'returns the task' do
23
42
  task = double 'task'
24
- allow(Task::DSL).to receive(:evaluate) { task }
25
- expect(Task.evaluate(name, env, &block)).to be task
43
+ allow(Task).to receive(:new) { task }
44
+ expect(Task.evaluate(name, env, *args, &block)).to be task
26
45
  end
27
46
  end
28
47
 
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: producer-core
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.6
4
+ version: 0.1.7
5
5
  platform: ruby
6
6
  authors:
7
7
  - Thibault Jouan
@@ -114,6 +114,7 @@ files:
114
114
  - features/cli/usage.feature
115
115
  - features/recipes/env.feature
116
116
  - features/recipes/evaluation.feature
117
+ - features/recipes/macro.feature
117
118
  - features/recipes/source.feature
118
119
  - features/recipes/target.feature
119
120
  - features/ssh/config.feature
@@ -200,7 +201,7 @@ rubyforge_project:
200
201
  rubygems_version: 2.4.5
201
202
  signing_key:
202
203
  specification_version: 4
203
- summary: producer-core-0.1.6
204
+ summary: producer-core-0.1.7
204
205
  test_files:
205
206
  - features/actions/echo.feature
206
207
  - features/actions/file_write.feature
@@ -208,6 +209,7 @@ test_files:
208
209
  - features/cli/usage.feature
209
210
  - features/recipes/env.feature
210
211
  - features/recipes/evaluation.feature
212
+ - features/recipes/macro.feature
211
213
  - features/recipes/source.feature
212
214
  - features/recipes/target.feature
213
215
  - features/ssh/config.feature