bumbleworks 0.0.51 → 0.0.52
Sign up to get free protection for your applications and to get access to all the features.
- data/lib/bumbleworks.rb +2 -0
- data/lib/bumbleworks/entity.rb +22 -15
- data/lib/bumbleworks/process.rb +12 -0
- data/lib/bumbleworks/task/finder.rb +33 -2
- data/lib/bumbleworks/version.rb +1 -1
- data/lib/bumbleworks/workitem.rb +52 -0
- data/lib/bumbleworks/workitem_entity_storage.rb +4 -43
- data/spec/fixtures/entities/{furby.rb → rainbow_loom.rb} +5 -2
- data/spec/integration/entity_spec.rb +18 -16
- data/spec/lib/bumbleworks/entity_spec.rb +69 -22
- data/spec/lib/bumbleworks/process_spec.rb +41 -0
- data/spec/lib/bumbleworks/task/finder_spec.rb +27 -0
- data/spec/lib/bumbleworks/task_spec.rb +35 -3
- data/spec/lib/bumbleworks/workitem_entity_storage_spec.rb +18 -106
- data/spec/lib/bumbleworks/workitem_spec.rb +88 -0
- metadata +9 -6
data/lib/bumbleworks.rb
CHANGED
@@ -11,6 +11,7 @@ require "bumbleworks/hash_storage"
|
|
11
11
|
require "bumbleworks/error_handler"
|
12
12
|
require "bumbleworks/entity"
|
13
13
|
require "bumbleworks/participant"
|
14
|
+
require "bumbleworks/workitem"
|
14
15
|
|
15
16
|
# default implementations
|
16
17
|
require "bumbleworks/simple_logger"
|
@@ -21,6 +22,7 @@ module Bumbleworks
|
|
21
22
|
class UndefinedSetting < StandardError; end
|
22
23
|
class InvalidSetting < StandardError; end
|
23
24
|
class InvalidEntity < StandardError; end
|
25
|
+
class EntityNotFound < StandardError; end
|
24
26
|
|
25
27
|
class << self
|
26
28
|
extend Forwardable
|
data/lib/bumbleworks/entity.rb
CHANGED
@@ -5,19 +5,19 @@ module Bumbleworks
|
|
5
5
|
end
|
6
6
|
|
7
7
|
def launch_process(process_name, options = {})
|
8
|
-
|
9
|
-
if (options[:force] == true || (process_identifier = self.send(
|
10
|
-
workitem_fields = process_fields(process_name.to_sym)
|
11
|
-
variables = process_variables(process_name.to_sym)
|
8
|
+
identifier_attribute = attribute_for_process_name(process_name.to_sym)
|
9
|
+
if (options[:force] == true || (process_identifier = self.send(identifier_attribute)).nil?)
|
10
|
+
workitem_fields = process_fields(process_name.to_sym).merge(options[:fields] || {})
|
11
|
+
variables = process_variables(process_name.to_sym).merge(options[:variables] || {})
|
12
12
|
process_identifier = Bumbleworks.launch!(process_name.to_s, workitem_fields, variables).wfid
|
13
|
-
persist_process_identifier(
|
13
|
+
persist_process_identifier(identifier_attribute.to_sym, process_identifier)
|
14
14
|
end
|
15
15
|
Bumbleworks::Process.new(process_identifier)
|
16
16
|
end
|
17
17
|
|
18
|
-
def persist_process_identifier(
|
18
|
+
def persist_process_identifier(identifier_attribute, process_identifier)
|
19
19
|
if self.respond_to?(:update)
|
20
|
-
update(
|
20
|
+
update(identifier_attribute => process_identifier)
|
21
21
|
else
|
22
22
|
raise "Entity must define #persist_process_identifier method if missing #update method."
|
23
23
|
end
|
@@ -27,7 +27,7 @@ module Bumbleworks
|
|
27
27
|
return {} unless self.class.processes
|
28
28
|
process_names = self.class.processes.keys
|
29
29
|
process_names.inject({}) do |memo, name|
|
30
|
-
pid = self.send(
|
30
|
+
pid = self.send(attribute_for_process_name(name))
|
31
31
|
memo[name] = pid ? Bumbleworks::Process.new(pid) : nil
|
32
32
|
memo
|
33
33
|
end
|
@@ -38,11 +38,18 @@ module Bumbleworks
|
|
38
38
|
end
|
39
39
|
|
40
40
|
def cancel_all_processes!
|
41
|
-
|
41
|
+
processes_by_name.each do |name, process|
|
42
|
+
next unless process
|
43
|
+
identifier_attribute = attribute_for_process_name(name)
|
42
44
|
process.cancel!
|
45
|
+
persist_process_identifier(identifier_attribute, nil)
|
43
46
|
end
|
44
47
|
end
|
45
48
|
|
49
|
+
def attribute_for_process_name(name)
|
50
|
+
self.class.processes[name][:attribute]
|
51
|
+
end
|
52
|
+
|
46
53
|
def tasks(nickname = nil)
|
47
54
|
finder = Bumbleworks::Task.for_entity(self)
|
48
55
|
finder = finder.by_nickname(nickname) if nickname
|
@@ -69,7 +76,7 @@ module Bumbleworks
|
|
69
76
|
attr_reader :processes
|
70
77
|
|
71
78
|
def process(process_name, options = {})
|
72
|
-
options[:
|
79
|
+
options[:attribute] ||= default_process_identifier_attribute(process_name)
|
73
80
|
(@processes ||= {})[process_name.to_sym] = options
|
74
81
|
end
|
75
82
|
|
@@ -77,11 +84,11 @@ module Bumbleworks
|
|
77
84
|
Bumbleworks::Support.tokenize(name)
|
78
85
|
end
|
79
86
|
|
80
|
-
def
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
87
|
+
def default_process_identifier_attribute(process_name)
|
88
|
+
identifier_attribute = "#{process_name}_process_identifier"
|
89
|
+
identifier_attribute.gsub!(/^#{entity_type}_/, '')
|
90
|
+
identifier_attribute.gsub!(/process_process/, 'process')
|
91
|
+
identifier_attribute.to_sym
|
85
92
|
end
|
86
93
|
end
|
87
94
|
end
|
data/lib/bumbleworks/process.rb
CHANGED
@@ -1,5 +1,7 @@
|
|
1
1
|
module Bumbleworks
|
2
2
|
class Process
|
3
|
+
class EntityConflict < StandardError; end
|
4
|
+
|
3
5
|
attr_reader :id
|
4
6
|
|
5
7
|
def initialize(wfid)
|
@@ -12,6 +14,16 @@ module Bumbleworks
|
|
12
14
|
wfid == other.wfid
|
13
15
|
end
|
14
16
|
|
17
|
+
def entity
|
18
|
+
return nil unless process_status
|
19
|
+
workitems = leaves.map(&:applied_workitem).map { |wi| Bumbleworks::Workitem.new(wi) }
|
20
|
+
if workitems.map(&:entity_fields).uniq.length == 1
|
21
|
+
workitems.first.entity
|
22
|
+
else
|
23
|
+
raise EntityConflict
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
15
27
|
def tasks
|
16
28
|
Bumbleworks::Task.for_process(wfid)
|
17
29
|
end
|
@@ -11,6 +11,32 @@ module Bumbleworks
|
|
11
11
|
@wfids = nil
|
12
12
|
end
|
13
13
|
|
14
|
+
def where(filters)
|
15
|
+
key_method_map = {
|
16
|
+
:available => :available,
|
17
|
+
:nickname => :by_nickname,
|
18
|
+
:roles => :for_roles,
|
19
|
+
:role => :for_role,
|
20
|
+
:unclaimed => :unclaimed,
|
21
|
+
:claimed => :claimed,
|
22
|
+
:fields => :with_fields,
|
23
|
+
:claimant => :for_claimant,
|
24
|
+
:entity => :for_entity,
|
25
|
+
:processes => :for_processes,
|
26
|
+
:process => :for_process,
|
27
|
+
:completable => :completable
|
28
|
+
}
|
29
|
+
fields = filters.select { |k,v| !key_method_map.keys.include? k }
|
30
|
+
methods = filters.select { |k,v| key_method_map.keys.include? k }
|
31
|
+
query = methods.inject(self) { |query, (method, args)|
|
32
|
+
query.send(key_method_map[method], args)
|
33
|
+
}
|
34
|
+
unless fields.empty?
|
35
|
+
query.with_fields(fields)
|
36
|
+
end
|
37
|
+
query
|
38
|
+
end
|
39
|
+
|
14
40
|
def available
|
15
41
|
unclaimed.completable
|
16
42
|
end
|
@@ -39,6 +65,11 @@ module Bumbleworks
|
|
39
65
|
unclaimed(false)
|
40
66
|
end
|
41
67
|
|
68
|
+
def with_fields(field_hash)
|
69
|
+
@queries << proc { |wi| field_hash.all? { |k, v| wi['fields'][k.to_s] == v } }
|
70
|
+
self
|
71
|
+
end
|
72
|
+
|
42
73
|
def for_claimant(token)
|
43
74
|
@queries << proc { |wi| wi['fields']['params']['claimant'] == token }
|
44
75
|
self
|
@@ -75,8 +106,8 @@ module Bumbleworks
|
|
75
106
|
from_workitems(workitems)
|
76
107
|
end
|
77
108
|
|
78
|
-
def completable
|
79
|
-
@task_filters << proc { |task| task.completable? }
|
109
|
+
def completable(true_or_false = true)
|
110
|
+
@task_filters << proc { |task| task.completable? == true_or_false }
|
80
111
|
self
|
81
112
|
end
|
82
113
|
|
data/lib/bumbleworks/version.rb
CHANGED
@@ -0,0 +1,52 @@
|
|
1
|
+
module Bumbleworks
|
2
|
+
class Workitem
|
3
|
+
def initialize(raw_workitem)
|
4
|
+
@raw_workitem = raw_workitem
|
5
|
+
end
|
6
|
+
|
7
|
+
def entity(options = {})
|
8
|
+
@entity = nil if options[:reload] == true
|
9
|
+
@entity ||= if has_entity_fields?
|
10
|
+
klass = Bumbleworks::Support.constantize(entity_type)
|
11
|
+
entity = klass.first_by_identifier(entity_id)
|
12
|
+
end
|
13
|
+
raise EntityNotFound, {:entity_id => entity_id, :entity_type => entity_type} unless @entity
|
14
|
+
@entity
|
15
|
+
end
|
16
|
+
|
17
|
+
def has_entity?
|
18
|
+
!entity.nil?
|
19
|
+
rescue EntityNotFound
|
20
|
+
false
|
21
|
+
end
|
22
|
+
|
23
|
+
def has_entity_fields?
|
24
|
+
entity_id && entity_type
|
25
|
+
end
|
26
|
+
|
27
|
+
def entity_fields(options = {})
|
28
|
+
return {} unless has_entity_fields?
|
29
|
+
type = if options[:humanize] == true
|
30
|
+
Bumbleworks::Support.humanize(entity_type)
|
31
|
+
elsif options[:titleize] == true
|
32
|
+
Bumbleworks::Support.titleize(entity_type)
|
33
|
+
else
|
34
|
+
entity_type
|
35
|
+
end
|
36
|
+
{
|
37
|
+
:type => type,
|
38
|
+
:identifier => entity_id
|
39
|
+
}
|
40
|
+
end
|
41
|
+
|
42
|
+
private
|
43
|
+
|
44
|
+
def entity_id
|
45
|
+
@raw_workitem.fields[:entity_id] || @raw_workitem.fields['entity_id']
|
46
|
+
end
|
47
|
+
|
48
|
+
def entity_type
|
49
|
+
@raw_workitem.fields[:entity_type] || @raw_workitem.fields['entity_type']
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
@@ -1,50 +1,11 @@
|
|
1
1
|
module Bumbleworks
|
2
2
|
module WorkitemEntityStorage
|
3
|
-
|
3
|
+
extend Forwardable
|
4
4
|
|
5
|
-
|
6
|
-
@entity = nil if options[:reload] == true
|
7
|
-
@entity ||= if has_entity_fields?
|
8
|
-
klass = Bumbleworks::Support.constantize(entity_type)
|
9
|
-
entity = klass.first_by_identifier(entity_id)
|
10
|
-
end
|
11
|
-
raise EntityNotFound, {:entity_id => entity_id, :entity_type => entity_type} unless @entity
|
12
|
-
@entity
|
13
|
-
end
|
14
|
-
|
15
|
-
def has_entity?
|
16
|
-
!entity.nil?
|
17
|
-
rescue EntityNotFound
|
18
|
-
false
|
19
|
-
end
|
20
|
-
|
21
|
-
def has_entity_fields?
|
22
|
-
entity_id && entity_type
|
23
|
-
end
|
24
|
-
|
25
|
-
def entity_fields(options = {})
|
26
|
-
return {} unless has_entity_fields?
|
27
|
-
type = if options[:humanize] == true
|
28
|
-
Bumbleworks::Support.humanize(entity_type)
|
29
|
-
elsif options[:titleize] == true
|
30
|
-
Bumbleworks::Support.titleize(entity_type)
|
31
|
-
else
|
32
|
-
entity_type
|
33
|
-
end
|
34
|
-
{
|
35
|
-
:type => type,
|
36
|
-
:identifier => entity_id
|
37
|
-
}
|
38
|
-
end
|
39
|
-
|
40
|
-
private
|
41
|
-
|
42
|
-
def entity_id
|
43
|
-
workitem.fields[:entity_id] || workitem.fields['entity_id']
|
44
|
-
end
|
5
|
+
delegate [:entity, :has_entity?, :has_entity_fields?, :entity_fields] => :entity_storage_workitem
|
45
6
|
|
46
|
-
def
|
47
|
-
|
7
|
+
def entity_storage_workitem
|
8
|
+
@entity_storage_workitem ||= Bumbleworks::Workitem.new(workitem)
|
48
9
|
end
|
49
10
|
end
|
50
11
|
end
|
@@ -1,10 +1,12 @@
|
|
1
|
-
class
|
1
|
+
class RainbowLoom
|
2
2
|
include Bumbleworks::Entity
|
3
3
|
|
4
4
|
process :make_honey
|
5
|
+
process :make_molasses, :attribute => :molasses_pid
|
5
6
|
|
6
|
-
|
7
|
+
attr_accessor :identifier
|
7
8
|
attr_accessor :make_honey_process_identifier
|
9
|
+
attr_accessor :molasses_pid
|
8
10
|
|
9
11
|
def initialize(identifier)
|
10
12
|
@identifier = identifier
|
@@ -24,6 +26,7 @@ class Furby
|
|
24
26
|
|
25
27
|
class << self
|
26
28
|
def first_by_identifier(identifier)
|
29
|
+
return nil unless identifier
|
27
30
|
new(identifier)
|
28
31
|
end
|
29
32
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
require File.expand_path(File.join(fixtures_path, 'entities', '
|
1
|
+
require File.expand_path(File.join(fixtures_path, 'entities', 'rainbow_loom'))
|
2
2
|
|
3
3
|
describe 'Entity Module' do
|
4
4
|
let(:app_root) {
|
@@ -10,27 +10,29 @@ describe 'Entity Module' do
|
|
10
10
|
load File.join(app_root, 'full_initializer.rb')
|
11
11
|
end
|
12
12
|
|
13
|
-
describe '
|
14
|
-
it 'assigns entity to process and subsequent tasks' do
|
15
|
-
|
16
|
-
|
13
|
+
describe 'process control' do
|
14
|
+
it 'launching assigns entity to process and subsequent tasks' do
|
15
|
+
rainbow_loom = RainbowLoom.new('12345')
|
16
|
+
process = rainbow_loom.launch_process(:make_honey)
|
17
17
|
Bumbleworks.dashboard.wait_for(:dave)
|
18
18
|
task = Bumbleworks::Task.for_role('dave').first
|
19
|
-
task.entity.should ==
|
19
|
+
task.entity.should == rainbow_loom
|
20
|
+
process.entity.should == rainbow_loom
|
20
21
|
end
|
21
22
|
|
22
|
-
it 'links processes with identifiers' do
|
23
|
-
|
24
|
-
process =
|
25
|
-
|
26
|
-
:make_honey => process
|
23
|
+
it 'launching links processes with identifiers' do
|
24
|
+
rainbow_loom = RainbowLoom.new('12345')
|
25
|
+
process = rainbow_loom.launch_process(:make_honey)
|
26
|
+
rainbow_loom.processes_by_name.should == {
|
27
|
+
:make_honey => process,
|
28
|
+
:make_molasses => nil
|
27
29
|
}
|
28
30
|
end
|
29
31
|
|
30
32
|
it 'persists process identifier' do
|
31
|
-
|
32
|
-
process =
|
33
|
-
|
33
|
+
rainbow_loom = RainbowLoom.new('12345')
|
34
|
+
process = rainbow_loom.launch_process(:make_honey)
|
35
|
+
rainbow_loom.make_honey_process_identifier.should == process.wfid
|
34
36
|
end
|
35
37
|
end
|
36
38
|
|
@@ -40,8 +42,8 @@ describe 'Entity Module' do
|
|
40
42
|
tell_entity :to => 'cook_it_up', :with => [2, 'orange'], :and_save_as => 'yum'
|
41
43
|
critic :task => 'checkit_that_foods'
|
42
44
|
end
|
43
|
-
|
44
|
-
process = Bumbleworks.launch!('here_we_go', :entity =>
|
45
|
+
rainbow_loom = RainbowLoom.new('12345')
|
46
|
+
process = Bumbleworks.launch!('here_we_go', :entity => rainbow_loom)
|
45
47
|
Bumbleworks.dashboard.wait_for(:critic)
|
46
48
|
process.tasks.first['yum'].should == "2 and orange"
|
47
49
|
end
|
@@ -5,7 +5,7 @@ describe Bumbleworks::Entity do
|
|
5
5
|
it 'returns hash of process names and process instances' do
|
6
6
|
[:zoom, :foof, :nook].each do |pname|
|
7
7
|
entity_class.send(:attr_accessor, :"#{pname}_pid")
|
8
|
-
entity_class.process pname, :
|
8
|
+
entity_class.process pname, :attribute => :"#{pname}_pid"
|
9
9
|
end
|
10
10
|
|
11
11
|
entity = entity_class.new
|
@@ -27,7 +27,7 @@ describe Bumbleworks::Entity do
|
|
27
27
|
it 'returns array of process instances for all running processes' do
|
28
28
|
[:zoom, :foof, :nook].each do |pname|
|
29
29
|
entity_class.send(:attr_accessor, :"#{pname}_pid")
|
30
|
-
entity_class.process pname, :
|
30
|
+
entity_class.process pname, :attribute => :"#{pname}_pid"
|
31
31
|
end
|
32
32
|
entity = entity_class.new
|
33
33
|
entity.foof_pid = '1234'
|
@@ -45,12 +45,21 @@ describe Bumbleworks::Entity do
|
|
45
45
|
|
46
46
|
describe '#cancel_all_processes!' do
|
47
47
|
it 'cancels all processes with registered identifiers' do
|
48
|
+
[:zoom, :foof, :nook].each do |pname|
|
49
|
+
entity_class.send(:attr_accessor, :"#{pname}_pid")
|
50
|
+
entity_class.process pname, :attribute => :"#{pname}_pid"
|
51
|
+
end
|
48
52
|
entity = entity_class.new
|
49
|
-
|
50
|
-
|
51
|
-
entity.stub(:
|
53
|
+
entity.foof_pid = '1234'
|
54
|
+
entity.nook_pid = 'pickles'
|
55
|
+
entity.stub(:processes_by_name => {
|
56
|
+
:foof => bp1 = Bumbleworks::Process.new('1234'),
|
57
|
+
:nook => bp2 = Bumbleworks::Process.new('pickles')
|
58
|
+
})
|
52
59
|
bp1.should_receive(:cancel!)
|
53
60
|
bp2.should_receive(:cancel!)
|
61
|
+
entity.should_receive(:update).with(:foof_pid => nil)
|
62
|
+
entity.should_receive(:update).with(:nook_pid => nil)
|
54
63
|
entity.cancel_all_processes!
|
55
64
|
end
|
56
65
|
end
|
@@ -80,8 +89,8 @@ describe Bumbleworks::Entity do
|
|
80
89
|
describe '#persist_process_identifier' do
|
81
90
|
it 'calls #update if method exists' do
|
82
91
|
entity = entity_class.new
|
83
|
-
entity.should_receive(:update).with(:
|
84
|
-
entity.persist_process_identifier(:
|
92
|
+
entity.should_receive(:update).with(:a_attribute => :a_value)
|
93
|
+
entity.persist_process_identifier(:a_attribute, :a_value)
|
85
94
|
end
|
86
95
|
|
87
96
|
it 'raises exception if #update method does not exist' do
|
@@ -89,7 +98,7 @@ describe Bumbleworks::Entity do
|
|
89
98
|
entity.stub(:respond_to?).with(:update).and_return(false)
|
90
99
|
entity.should_receive(:update).never
|
91
100
|
expect {
|
92
|
-
entity.persist_process_identifier(:
|
101
|
+
entity.persist_process_identifier(:a_attribute, :a_value)
|
93
102
|
}.to raise_error("Entity must define #persist_process_identifier method if missing #update method.")
|
94
103
|
end
|
95
104
|
end
|
@@ -97,34 +106,72 @@ describe Bumbleworks::Entity do
|
|
97
106
|
describe '#launch_process' do
|
98
107
|
it 'launches process and return process if identifier not set' do
|
99
108
|
bp = Bumbleworks::Process.new('12345')
|
100
|
-
entity_class.process :noodles, :
|
109
|
+
entity_class.process :noodles, :attribute => :noodles_pid
|
101
110
|
entity = entity_class.new
|
102
111
|
entity.stub(:noodles_pid)
|
103
|
-
entity.stub(:process_fields).with(:noodles).and_return(
|
104
|
-
entity.stub(:process_variables).with(:noodles).and_return(
|
105
|
-
Bumbleworks.stub(:launch!).with('noodles',
|
112
|
+
entity.stub(:process_fields).with(:noodles).and_return({:f => 1})
|
113
|
+
entity.stub(:process_variables).with(:noodles).and_return({:v => 2})
|
114
|
+
Bumbleworks.stub(:launch!).with('noodles', {:f => 1}, {:v => 2}).and_return(bp)
|
106
115
|
entity.should_receive(:persist_process_identifier).with(:noodles_pid, '12345')
|
107
116
|
entity.launch_process('noodles').should == bp
|
108
117
|
end
|
109
118
|
|
110
|
-
it 'does nothing but returns existing process if identifier
|
119
|
+
it 'does nothing but returns existing process if identifier attribute already set' do
|
111
120
|
bp = Bumbleworks::Process.new('already set')
|
112
|
-
entity_class.process :noodles, :
|
121
|
+
entity_class.process :noodles, :attribute => :noodles_pid
|
113
122
|
entity = entity_class.new
|
114
123
|
entity.stub(:noodles_pid => 'already set')
|
115
124
|
Bumbleworks.should_receive(:launch!).never
|
116
125
|
entity.launch_process('noodles').should == bp
|
117
126
|
end
|
118
127
|
|
119
|
-
it 'launches new process anyway if identifier
|
128
|
+
it 'launches new process anyway if identifier attribute already set but force is true' do
|
120
129
|
bp = Bumbleworks::Process.new('12345')
|
121
|
-
entity_class.process :noodles, :
|
130
|
+
entity_class.process :noodles, :attribute => :noodles_pid
|
122
131
|
entity = entity_class.new
|
123
132
|
entity.stub(:noodles_pid => 'already set')
|
124
133
|
Bumbleworks.stub(:launch! => bp)
|
125
134
|
entity.should_receive(:persist_process_identifier).with(:noodles_pid, '12345')
|
126
135
|
entity.launch_process('noodles', :force => true).should == bp
|
127
136
|
end
|
137
|
+
|
138
|
+
it 'sends additional fields and variables to launch' do
|
139
|
+
entity_class.process :noodles, :attribute => :noodles_pid
|
140
|
+
entity = entity_class.new
|
141
|
+
entity.stub(:noodles_pid)
|
142
|
+
entity.stub(:persist_process_identifier)
|
143
|
+
Bumbleworks.should_receive(:launch!).with(
|
144
|
+
'noodles',
|
145
|
+
{ :entity => entity, :drink => 'apathy smoothie', :berry => 'black' },
|
146
|
+
{ :so_you_said => :well_so_did_i }
|
147
|
+
).and_return(Bumbleworks::Process.new(1))
|
148
|
+
entity.launch_process(:noodles,
|
149
|
+
:fields => { :drink => 'apathy smoothie', :berry => 'black' },
|
150
|
+
:variables => { :so_you_said => :well_so_did_i }
|
151
|
+
)
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
155
|
+
describe '#attribute_for_process_name' do
|
156
|
+
it 'returns attribute set for given process' do
|
157
|
+
entity_class.stub(:processes).and_return({
|
158
|
+
:goose => { :attribute => :goose_pid },
|
159
|
+
:the_punisher => { :attribute => :your_skin }
|
160
|
+
})
|
161
|
+
entity = entity_class.new
|
162
|
+
entity.attribute_for_process_name(:goose).should == :goose_pid
|
163
|
+
entity.attribute_for_process_name(:the_punisher).should == :your_skin
|
164
|
+
end
|
165
|
+
|
166
|
+
it 'raises exception if no process found for given name' do
|
167
|
+
entity_class.stub(:processes).and_return({
|
168
|
+
:goose => { :attribute => :goose_pid },
|
169
|
+
})
|
170
|
+
entity = entity_class.new
|
171
|
+
expect {
|
172
|
+
entity.attribute_for_process_name(:the_punisher)
|
173
|
+
}.to raise_error
|
174
|
+
end
|
128
175
|
end
|
129
176
|
|
130
177
|
describe '#subscribed_events' do
|
@@ -174,28 +221,28 @@ describe Bumbleworks::Entity do
|
|
174
221
|
|
175
222
|
describe '.process' do
|
176
223
|
it 'registers a new process' do
|
177
|
-
entity_class.stub(:
|
224
|
+
entity_class.stub(:default_process_identifier_attribute).with(:whatever).and_return('loob')
|
178
225
|
entity_class.process :whatever
|
179
226
|
entity_class.processes.should == {
|
180
227
|
:whatever => {
|
181
|
-
:
|
228
|
+
:attribute => 'loob'
|
182
229
|
}
|
183
230
|
}
|
184
231
|
end
|
185
232
|
end
|
186
233
|
|
187
|
-
describe '.
|
234
|
+
describe '.default_process_identifier_attribute' do
|
188
235
|
it 'adds _process_identifier to end of given process name' do
|
189
|
-
entity_class.
|
236
|
+
entity_class.default_process_identifier_attribute('zoof').should == :zoof_process_identifier
|
190
237
|
end
|
191
238
|
|
192
239
|
it 'ensures no duplication of _process' do
|
193
|
-
entity_class.
|
240
|
+
entity_class.default_process_identifier_attribute('zoof_process').should == :zoof_process_identifier
|
194
241
|
end
|
195
242
|
|
196
243
|
it 'removes entity_type from beginning of identifier' do
|
197
244
|
entity_class.stub(:entity_type).and_return('zoof')
|
198
|
-
entity_class.
|
245
|
+
entity_class.default_process_identifier_attribute('zoof_process').should == :process_identifier
|
199
246
|
end
|
200
247
|
end
|
201
248
|
|
@@ -1,3 +1,5 @@
|
|
1
|
+
require File.expand_path(File.join(fixtures_path, 'entities', 'rainbow_loom'))
|
2
|
+
|
1
3
|
describe Bumbleworks::Process do
|
2
4
|
before :each do
|
3
5
|
Bumbleworks.reset!
|
@@ -119,6 +121,45 @@ describe Bumbleworks::Process do
|
|
119
121
|
end
|
120
122
|
end
|
121
123
|
|
124
|
+
describe '#entity' do
|
125
|
+
it 'returns nil if process not ready yet' do
|
126
|
+
bp = described_class.new('nothing')
|
127
|
+
bp.entity.should be_nil
|
128
|
+
end
|
129
|
+
|
130
|
+
it 'returns entity provided at launch' do
|
131
|
+
rainbow_loom = RainbowLoom.new('1234')
|
132
|
+
bp = Bumbleworks.launch!('going_to_the_dance', :entity => rainbow_loom)
|
133
|
+
wait_until { bp.trackers.count > 0 }
|
134
|
+
bp.entity.should == rainbow_loom
|
135
|
+
end
|
136
|
+
|
137
|
+
it 'raises exception if multiple workitems have conflicting entity info' do
|
138
|
+
Bumbleworks.define_process 'conflict_this' do
|
139
|
+
concurrence do
|
140
|
+
sequence do
|
141
|
+
set 'entity_id' => 'swoo'
|
142
|
+
just_wait
|
143
|
+
end
|
144
|
+
sequence do
|
145
|
+
set 'entity_id' => 'fwee'
|
146
|
+
just_wait
|
147
|
+
end
|
148
|
+
end
|
149
|
+
end
|
150
|
+
bp = Bumbleworks.launch!('conflict_this', :entity => RainbowLoom.new('1234'))
|
151
|
+
Bumbleworks.dashboard.wait_for(:just_wait)
|
152
|
+
expect {
|
153
|
+
bp.entity
|
154
|
+
}.to raise_error(Bumbleworks::Process::EntityConflict)
|
155
|
+
end
|
156
|
+
|
157
|
+
it 'returns nil if no entity' do
|
158
|
+
bp = Bumbleworks.launch!('going_to_the_dance')
|
159
|
+
bp.entity.should be_nil
|
160
|
+
end
|
161
|
+
end
|
162
|
+
|
122
163
|
describe '#process_status' do
|
123
164
|
it 'returns a process_status instance for the wfid' do
|
124
165
|
bp = described_class.new('frogheads')
|
@@ -40,4 +40,31 @@ describe Bumbleworks::Task::Finder do
|
|
40
40
|
query.available
|
41
41
|
end
|
42
42
|
end
|
43
|
+
|
44
|
+
describe '#where' do
|
45
|
+
it 'compiles a finder' do
|
46
|
+
query = Bumbleworks::Task::Finder.new
|
47
|
+
query.should_receive(:available).and_return(query)
|
48
|
+
query.should_receive(:by_nickname).with(:nicholas).and_return(query)
|
49
|
+
query.should_receive(:for_roles).with([:dinner, :barca]).and_return(query)
|
50
|
+
query.should_receive(:unclaimed).and_return(query)
|
51
|
+
query.should_receive(:for_claimant).with(:dr_clam).and_return(query)
|
52
|
+
query.should_receive(:for_entity).with(:a_luffly_pirate).and_return(query)
|
53
|
+
query.should_receive(:for_processes).with([:jasmine, :mulan]).and_return(query)
|
54
|
+
query.should_receive(:completable).with(true).and_return(query)
|
55
|
+
query.should_receive(:with_fields).with({ :horse => :giant_pony, :pie => :silly_cake }).and_return(query)
|
56
|
+
query.where({
|
57
|
+
:available => true,
|
58
|
+
:nickname => :nicholas,
|
59
|
+
:roles => [:dinner, :barca],
|
60
|
+
:unclaimed => true,
|
61
|
+
:claimant => :dr_clam,
|
62
|
+
:entity => :a_luffly_pirate,
|
63
|
+
:processes => [:jasmine, :mulan],
|
64
|
+
:completable => true,
|
65
|
+
:horse => :giant_pony,
|
66
|
+
:pie => :silly_cake
|
67
|
+
})
|
68
|
+
end
|
69
|
+
end
|
43
70
|
end
|
@@ -371,7 +371,7 @@ describe Bumbleworks::Task do
|
|
371
371
|
end
|
372
372
|
|
373
373
|
describe '.completable' do
|
374
|
-
it '
|
374
|
+
it 'filters by completability' do
|
375
375
|
module WuggleHandsTask
|
376
376
|
def completable?
|
377
377
|
false
|
@@ -393,6 +393,11 @@ describe Bumbleworks::Task do
|
|
393
393
|
['a_fella', 'waggle_hands'],
|
394
394
|
['a_lady', 'wiggle_hands']
|
395
395
|
]
|
396
|
+
tasks = described_class.completable(false)
|
397
|
+
tasks.should have(1).item
|
398
|
+
tasks.map { |t| [t.role, t.nickname] }.should == [
|
399
|
+
['a_monkey', 'wuggle_hands']
|
400
|
+
]
|
396
401
|
end
|
397
402
|
end
|
398
403
|
|
@@ -469,7 +474,7 @@ describe Bumbleworks::Task do
|
|
469
474
|
end
|
470
475
|
end
|
471
476
|
|
472
|
-
|
477
|
+
describe '.for_claimant' do
|
473
478
|
it 'returns all tasks claimed by given claimant' do
|
474
479
|
Bumbleworks.define_process 'dog-lifecycle' do
|
475
480
|
concurrence do
|
@@ -493,7 +498,34 @@ describe Bumbleworks::Task do
|
|
493
498
|
end
|
494
499
|
end
|
495
500
|
|
496
|
-
|
501
|
+
describe '.with_fields' do
|
502
|
+
it 'returns all tasks with given fields' do
|
503
|
+
Bumbleworks.define_process 'divergination' do
|
504
|
+
concurrence do
|
505
|
+
sequence do
|
506
|
+
set 'bumby' => 'fancy'
|
507
|
+
bumber :task => 'wear_monocle'
|
508
|
+
end
|
509
|
+
sequence do
|
510
|
+
set 'bumby' => 'not_fancy'
|
511
|
+
concurrence do
|
512
|
+
bumber :task => 'wear_natties'
|
513
|
+
loofer :task => 'snuffle'
|
514
|
+
end
|
515
|
+
end
|
516
|
+
end
|
517
|
+
end
|
518
|
+
Bumbleworks.launch!('divergination', :grumbles => true)
|
519
|
+
Bumbleworks.dashboard.wait_for(:loofer)
|
520
|
+
described_class.with_fields(:grumbles => true).count.should == 3
|
521
|
+
described_class.with_fields(:bumby => 'fancy').count.should == 1
|
522
|
+
described_class.with_fields(:bumby => 'not_fancy').count.should == 2
|
523
|
+
described_class.with_fields(:grumbles => false, :bumby => 'not_fancy').should be_empty
|
524
|
+
described_class.with_fields(:what => 'ever').should be_empty
|
525
|
+
end
|
526
|
+
end
|
527
|
+
|
528
|
+
describe '.for_entity' do
|
497
529
|
it 'returns all tasks associated with given entity' do
|
498
530
|
fake_sandwich = OpenStruct.new(:identifier => 'rubies')
|
499
531
|
Bumbleworks.define_process 'existential_pb_and_j' do
|
@@ -3,121 +3,33 @@ require "bumbleworks/workitem_entity_storage"
|
|
3
3
|
describe Bumbleworks::WorkitemEntityStorage do
|
4
4
|
class FakeEntityHolder
|
5
5
|
include Bumbleworks::WorkitemEntityStorage
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
def workitem
|
11
|
-
OpenStruct.new(:fields => @fields)
|
12
|
-
end
|
13
|
-
end
|
14
|
-
|
15
|
-
describe '#has_entity_fields?' do
|
16
|
-
it 'returns true if workitem fields include entity fields' do
|
17
|
-
feh = FakeEntityHolder.new('entity_id' => '1', 'entity_type' => 'SomeEntity')
|
18
|
-
feh.should have_entity_fields
|
19
|
-
end
|
20
|
-
|
21
|
-
it 'returns true if workitem fields include symbolized version of entity fields' do
|
22
|
-
feh = FakeEntityHolder.new(:entity_id => '1', :entity_type => 'SomeEntity')
|
23
|
-
feh.should have_entity_fields
|
24
|
-
end
|
25
|
-
|
26
|
-
it 'returns false if workitem fields do not include entity fields' do
|
27
|
-
feh = FakeEntityHolder.new
|
28
|
-
feh.should_not have_entity_fields
|
6
|
+
attr_reader :workitem
|
7
|
+
def initialize(workitem)
|
8
|
+
@workitem = workitem
|
29
9
|
end
|
30
10
|
end
|
31
11
|
|
32
|
-
describe '#
|
33
|
-
it 'returns
|
34
|
-
|
35
|
-
feh.
|
36
|
-
feh.
|
12
|
+
describe '#entity_storage_workitem' do
|
13
|
+
it 'returns new Bumbleworks::Workitem instance with workitem' do
|
14
|
+
Bumbleworks::Workitem.stub(:new).with(:a_workitem).and_return(:the_workitem)
|
15
|
+
feh = FakeEntityHolder.new(:a_workitem)
|
16
|
+
feh.entity_storage_workitem.should == :the_workitem
|
37
17
|
end
|
38
18
|
|
39
|
-
it '
|
40
|
-
feh = FakeEntityHolder.new
|
41
|
-
feh.
|
42
|
-
feh.
|
19
|
+
it 'is memoized' do
|
20
|
+
feh = FakeEntityHolder.new(:a_workitem)
|
21
|
+
esw = feh.entity_storage_workitem
|
22
|
+
feh.entity_storage_workitem.should be esw
|
43
23
|
end
|
44
24
|
end
|
45
25
|
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
end
|
53
|
-
|
54
|
-
def self.first_by_identifier(identifier)
|
55
|
-
return nil unless identifier
|
56
|
-
new(identifier)
|
57
|
-
end
|
26
|
+
[:has_entity_fields?, :has_entity?, :entity, :entity_fields].each do |method|
|
27
|
+
describe "##{method}" do
|
28
|
+
it 'delegates to entity storage workitem' do
|
29
|
+
feh = FakeEntityHolder.new(:a_workitem)
|
30
|
+
feh.entity_storage_workitem.stub(method).with(1, 2, 3).and_return(:yay_for_bikes)
|
31
|
+
feh.send(method, 1, 2, 3).should == :yay_for_bikes
|
58
32
|
end
|
59
33
|
end
|
60
|
-
|
61
|
-
after :all do
|
62
|
-
Object.send(:remove_const, :LovelyEntity)
|
63
|
-
end
|
64
|
-
|
65
|
-
it 'attempts to instantiate business entity from _id and _type fields' do
|
66
|
-
feh = FakeEntityHolder.new('entity_id' => '15', 'entity_type' => 'LovelyEntity')
|
67
|
-
feh.entity.identifier.should == '15'
|
68
|
-
end
|
69
|
-
|
70
|
-
it 'works with symbolized _id and _type fields' do
|
71
|
-
feh = FakeEntityHolder.new(:entity_id => '15', :entity_type => 'LovelyEntity')
|
72
|
-
feh.entity.identifier.should == '15'
|
73
|
-
end
|
74
|
-
|
75
|
-
it 'throw exception if entity fields not present' do
|
76
|
-
feh = FakeEntityHolder.new
|
77
|
-
expect {
|
78
|
-
feh.entity
|
79
|
-
}.to raise_error Bumbleworks::WorkitemEntityStorage::EntityNotFound
|
80
|
-
end
|
81
|
-
|
82
|
-
it 'throw exception if entity returns nil' do
|
83
|
-
feh = FakeEntityHolder.new('entity_id' => nil, 'entity_type' => 'LovelyEntity')
|
84
|
-
expect {
|
85
|
-
feh.entity
|
86
|
-
}.to raise_error Bumbleworks::WorkitemEntityStorage::EntityNotFound, '{:entity_id=>nil, :entity_type=>"LovelyEntity"}'
|
87
|
-
end
|
88
|
-
|
89
|
-
it 'returns same instance when called twice' do
|
90
|
-
feh = FakeEntityHolder.new('entity_id' => '15', 'entity_type' => 'LovelyEntity')
|
91
|
-
feh.entity.identifier = 'pickles'
|
92
|
-
feh.entity.identifier.should == 'pickles'
|
93
|
-
end
|
94
|
-
|
95
|
-
it 'reloads instance when called with reload option' do
|
96
|
-
feh = FakeEntityHolder.new('entity_id' => '15', 'entity_type' => 'LovelyEntity')
|
97
|
-
feh.entity.identifier = 'pickles'
|
98
|
-
feh.entity(:reload => true).identifier.should == '15'
|
99
|
-
end
|
100
|
-
end
|
101
|
-
|
102
|
-
describe "#entity_fields" do
|
103
|
-
it 'returns empty hash if no entity' do
|
104
|
-
feh = FakeEntityHolder.new
|
105
|
-
feh.entity_fields.should == {}
|
106
|
-
end
|
107
|
-
|
108
|
-
it 'returns class name and identifier by default' do
|
109
|
-
feh = FakeEntityHolder.new('entity_id' => '15', 'entity_type' => 'LovelyEntity')
|
110
|
-
feh.entity_fields.should == { :type => 'LovelyEntity', :identifier => '15' }
|
111
|
-
end
|
112
|
-
|
113
|
-
it 'humanizes class name when requested' do
|
114
|
-
feh = FakeEntityHolder.new('entity_id' => '15', 'entity_type' => 'LovelyEntity')
|
115
|
-
feh.entity_fields(:humanize => true).should == { :type => 'Lovely entity', :identifier => '15' }
|
116
|
-
end
|
117
|
-
|
118
|
-
it 'titleizes class name when requested' do
|
119
|
-
feh = FakeEntityHolder.new('entity_id' => '15', 'entity_type' => 'LovelyEntity')
|
120
|
-
feh.entity_fields(:titleize => true).should == { :type => 'Lovely Entity', :identifier => '15' }
|
121
|
-
end
|
122
34
|
end
|
123
35
|
end
|
@@ -0,0 +1,88 @@
|
|
1
|
+
require File.expand_path(File.join(fixtures_path, 'entities', 'rainbow_loom'))
|
2
|
+
|
3
|
+
describe Bumbleworks::Workitem do
|
4
|
+
let(:ruote_workitem) { Ruote::Workitem.new('fields' => {'entity_id' => '123', 'entity_type' => 'RainbowLoom'} ) }
|
5
|
+
let(:workitem) { Bumbleworks::Workitem.new(ruote_workitem)}
|
6
|
+
|
7
|
+
describe '#has_entity_fields?' do
|
8
|
+
it 'returns true if workitem fields include entity fields' do
|
9
|
+
workitem.should have_entity_fields
|
10
|
+
end
|
11
|
+
|
12
|
+
it 'returns true if workitem fields include symbolized version of entity fields' do
|
13
|
+
ruote_workitem.fields = { :entity_id => '123', :entity_type => 'RainbowLoom' }
|
14
|
+
workitem.should have_entity_fields
|
15
|
+
end
|
16
|
+
|
17
|
+
it 'returns false if workitem fields do not include entity fields' do
|
18
|
+
ruote_workitem.fields = {}
|
19
|
+
workitem.should_not have_entity_fields
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
describe '#has_entity?' do
|
24
|
+
it 'returns true if entity is not nil' do
|
25
|
+
workitem.stub(:entity).and_return(:a_real_boy_not_a_puppet)
|
26
|
+
workitem.has_entity?.should be_true
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'returns false if EntityNotFound' do
|
30
|
+
workitem.stub(:entity).and_raise(Bumbleworks::EntityNotFound)
|
31
|
+
workitem.has_entity?.should be_false
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
describe '#entity' do
|
36
|
+
it 'attempts to instantiate business entity from _id and _type fields' do
|
37
|
+
workitem.entity.identifier.should == '123'
|
38
|
+
end
|
39
|
+
|
40
|
+
it 'works with symbolized _id and _type fields' do
|
41
|
+
ruote_workitem.fields = { :entity_id => '125', :entity_type => 'RainbowLoom' }
|
42
|
+
workitem.entity.identifier.should == '125'
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'throw exception if entity fields not present' do
|
46
|
+
ruote_workitem.fields = {}
|
47
|
+
expect {
|
48
|
+
workitem.entity
|
49
|
+
}.to raise_error Bumbleworks::EntityNotFound
|
50
|
+
end
|
51
|
+
|
52
|
+
it 'throw exception if entity returns nil' do
|
53
|
+
ruote_workitem.fields['entity_id'] = nil
|
54
|
+
expect {
|
55
|
+
workitem.entity
|
56
|
+
}.to raise_error Bumbleworks::EntityNotFound, '{:entity_id=>nil, :entity_type=>"RainbowLoom"}'
|
57
|
+
end
|
58
|
+
|
59
|
+
it 'returns same instance when called twice' do
|
60
|
+
workitem.entity.identifier = 'nerfus'
|
61
|
+
workitem.entity.identifier.should == 'nerfus'
|
62
|
+
end
|
63
|
+
|
64
|
+
it 'reloads instance when called with reload option' do
|
65
|
+
workitem.entity.identifier = 'pickles'
|
66
|
+
workitem.entity(:reload => true).identifier.should == '123'
|
67
|
+
end
|
68
|
+
end
|
69
|
+
|
70
|
+
describe "#entity_fields" do
|
71
|
+
it 'returns empty hash if no entity' do
|
72
|
+
ruote_workitem.fields = {}
|
73
|
+
workitem.entity_fields.should == {}
|
74
|
+
end
|
75
|
+
|
76
|
+
it 'returns class name and identifier by default' do
|
77
|
+
workitem.entity_fields.should == { :type => 'RainbowLoom', :identifier => '123' }
|
78
|
+
end
|
79
|
+
|
80
|
+
it 'humanizes class name when requested' do
|
81
|
+
workitem.entity_fields(:humanize => true).should == { :type => 'Rainbow loom', :identifier => '123' }
|
82
|
+
end
|
83
|
+
|
84
|
+
it 'titleizes class name when requested' do
|
85
|
+
workitem.entity_fields(:titleize => true).should == { :type => 'Rainbow Loom', :identifier => '123' }
|
86
|
+
end
|
87
|
+
end
|
88
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: bumbleworks
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.52
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -12,7 +12,7 @@ authors:
|
|
12
12
|
autorequire:
|
13
13
|
bindir: bin
|
14
14
|
cert_chain: []
|
15
|
-
date: 2013-12-
|
15
|
+
date: 2013-12-23 00:00:00.000000000 Z
|
16
16
|
dependencies:
|
17
17
|
- !ruby/object:Gem::Dependency
|
18
18
|
name: ruote
|
@@ -192,6 +192,7 @@ files:
|
|
192
192
|
- lib/bumbleworks/task/finder.rb
|
193
193
|
- lib/bumbleworks/tree_builder.rb
|
194
194
|
- lib/bumbleworks/version.rb
|
195
|
+
- lib/bumbleworks/workitem.rb
|
195
196
|
- lib/bumbleworks/workitem_entity_storage.rb
|
196
197
|
- lib/tasks/bumbleworks.rake
|
197
198
|
- spec/fixtures/apps/with_default_directories/config_initializer.rb
|
@@ -209,7 +210,7 @@ files:
|
|
209
210
|
- spec/fixtures/definitions/a_list_of_jams.rb
|
210
211
|
- spec/fixtures/definitions/nested_folder/test_nested_process.rb
|
211
212
|
- spec/fixtures/definitions/test_process.rb
|
212
|
-
- spec/fixtures/entities/
|
213
|
+
- spec/fixtures/entities/rainbow_loom.rb
|
213
214
|
- spec/integration/entity_spec.rb
|
214
215
|
- spec/integration/example_configurations_spec.rb
|
215
216
|
- spec/integration/history_storage_spec.rb
|
@@ -236,6 +237,7 @@ files:
|
|
236
237
|
- spec/lib/bumbleworks/task_spec.rb
|
237
238
|
- spec/lib/bumbleworks/tree_builder_spec.rb
|
238
239
|
- spec/lib/bumbleworks/workitem_entity_storage_spec.rb
|
240
|
+
- spec/lib/bumbleworks/workitem_spec.rb
|
239
241
|
- spec/lib/bumbleworks_spec.rb
|
240
242
|
- spec/spec_helper.rb
|
241
243
|
- spec/support/path_helpers.rb
|
@@ -256,7 +258,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
256
258
|
version: '0'
|
257
259
|
segments:
|
258
260
|
- 0
|
259
|
-
hash:
|
261
|
+
hash: -2295219259305146267
|
260
262
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
261
263
|
none: false
|
262
264
|
requirements:
|
@@ -265,7 +267,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
265
267
|
version: '0'
|
266
268
|
segments:
|
267
269
|
- 0
|
268
|
-
hash:
|
270
|
+
hash: -2295219259305146267
|
269
271
|
requirements: []
|
270
272
|
rubyforge_project:
|
271
273
|
rubygems_version: 1.8.23
|
@@ -288,7 +290,7 @@ test_files:
|
|
288
290
|
- spec/fixtures/definitions/a_list_of_jams.rb
|
289
291
|
- spec/fixtures/definitions/nested_folder/test_nested_process.rb
|
290
292
|
- spec/fixtures/definitions/test_process.rb
|
291
|
-
- spec/fixtures/entities/
|
293
|
+
- spec/fixtures/entities/rainbow_loom.rb
|
292
294
|
- spec/integration/entity_spec.rb
|
293
295
|
- spec/integration/example_configurations_spec.rb
|
294
296
|
- spec/integration/history_storage_spec.rb
|
@@ -315,6 +317,7 @@ test_files:
|
|
315
317
|
- spec/lib/bumbleworks/task_spec.rb
|
316
318
|
- spec/lib/bumbleworks/tree_builder_spec.rb
|
317
319
|
- spec/lib/bumbleworks/workitem_entity_storage_spec.rb
|
320
|
+
- spec/lib/bumbleworks/workitem_spec.rb
|
318
321
|
- spec/lib/bumbleworks_spec.rb
|
319
322
|
- spec/spec_helper.rb
|
320
323
|
- spec/support/path_helpers.rb
|