ruote-kit 2.2.0.3 → 2.3.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/CHANGELOG.txt +28 -1
- data/CREDITS.txt +8 -2
- data/LICENSE.txt +1 -1
- data/Rakefile +21 -9
- data/lib/ruote-kit.rb +13 -4
- data/lib/ruote-kit/core_ext.rb +15 -0
- data/lib/ruote-kit/helpers/json_helpers.rb +22 -7
- data/lib/ruote-kit/helpers/link_helpers.rb +9 -7
- data/lib/ruote-kit/helpers/pagination_helpers.rb +1 -2
- data/lib/ruote-kit/helpers/render_helpers.rb +1 -1
- data/lib/ruote-kit/public/_ruote/images/favicon.png +0 -0
- data/lib/ruote-kit/public/_ruote/images/{ruote_buttons.png → ruote-buttons.png} +0 -0
- data/lib/ruote-kit/public/_ruote/images/ruote.png +0 -0
- data/lib/ruote-kit/public/_ruote/javascripts/foolbox-all.min.js +3 -0
- data/lib/ruote-kit/public/_ruote/javascripts/jquery-1.9.1.min.js +5 -0
- data/lib/ruote-kit/public/_ruote/javascripts/rk.js +68 -17
- data/lib/ruote-kit/public/_ruote/javascripts/ruote-fluo-all.min.js +3 -0
- data/lib/ruote-kit/public/_ruote/stylesheets/rk.css +82 -12
- data/lib/ruote-kit/public/_ruote/stylesheets/ruote-buttons.png +0 -0
- data/lib/ruote-kit/public/_ruote/stylesheets/ruote-fluo-editor.css +9 -6
- data/lib/ruote-kit/public/_ruote/stylesheets/ruote-fluo.css +62 -0
- data/lib/ruote-kit/resources/errors.rb +8 -3
- data/lib/ruote-kit/resources/expressions.rb +38 -35
- data/lib/ruote-kit/resources/participants.rb +1 -1
- data/lib/ruote-kit/resources/processes.rb +61 -4
- data/lib/ruote-kit/resources/workitems.rb +4 -4
- data/lib/ruote-kit/version.rb +1 -1
- data/lib/ruote-kit/views/_pagination.html.haml +2 -2
- data/lib/ruote-kit/views/_tree_editor.html.haml +63 -30
- data/lib/ruote-kit/views/error.html.haml +50 -9
- data/lib/ruote-kit/views/errors.html.haml +1 -1
- data/lib/ruote-kit/views/expression.html.haml +83 -33
- data/lib/ruote-kit/views/expressions.html.haml +23 -8
- data/lib/ruote-kit/views/http_error.html.haml +9 -2
- data/lib/ruote-kit/views/layout.html.haml +14 -13
- data/lib/ruote-kit/views/process.html.haml +75 -20
- data/lib/ruote-kit/views/processes.html.haml +9 -3
- data/lib/ruote-kit/views/processes_new.html.haml +19 -2
- data/lib/ruote-kit/views/schedules.html.haml +2 -2
- data/lib/ruote-kit/views/workitem.html.haml +17 -6
- data/ruote-kit.gemspec +9 -7
- data/spec/cases/orphan_workitem_spec.rb +141 -0
- data/spec/core_ext_spec.rb +19 -0
- data/spec/resources/errors_spec.rb +182 -156
- data/spec/resources/expressions_spec.rb +497 -379
- data/spec/resources/index_spec.rb +5 -5
- data/spec/resources/participants_spec.rb +64 -75
- data/spec/resources/processes_spec.rb +396 -277
- data/spec/resources/schedules_spec.rb +92 -76
- data/spec/resources/workitems_spec.rb +352 -343
- data/spec/ruote-kit_configure_spec.rb +41 -13
- data/spec/spec_helper.rb +6 -8
- data/spec/support/link_helper.rb +11 -0
- data/spec/webapp_helpers_spec.rb +29 -23
- metadata +161 -180
- data/README.rdoc +0 -313
- data/lib/ruote-kit/public/_ruote/images/favicon.ico +0 -0
- data/lib/ruote-kit/public/_ruote/javascripts/jquery-1.4.2.min.js +0 -154
- data/lib/ruote-kit/public/_ruote/javascripts/ruote-fluo-editor.js +0 -548
- data/lib/ruote-kit/public/_ruote/javascripts/ruote-fluo.js +0 -1118
@@ -1,121 +1,137 @@
|
|
1
1
|
|
2
|
-
require
|
2
|
+
require 'spec_helper'
|
3
3
|
|
4
4
|
|
5
|
-
describe '
|
5
|
+
describe '/_ruote/schedules' do
|
6
6
|
|
7
7
|
before(:each) do
|
8
|
-
|
9
8
|
prepare_engine_with_participants
|
10
|
-
|
11
|
-
@wfid0 = RuoteKit.engine.launch(Ruote.define do
|
12
|
-
wait :for => '3d'
|
13
|
-
end)
|
14
|
-
@wfid1 = RuoteKit.engine.launch(Ruote.define do
|
15
|
-
sequence do
|
16
|
-
alpha :timeout => '2d'
|
17
|
-
end
|
18
|
-
end)
|
19
|
-
@wfid2 = RuoteKit.engine.launch(Ruote.define do
|
20
|
-
nada
|
21
|
-
end)
|
22
|
-
|
23
|
-
RuoteKit.engine.wait_for(:alpha)
|
24
9
|
end
|
25
|
-
|
26
10
|
after(:each) do
|
27
|
-
|
28
11
|
shutdown_and_purge_engine
|
29
12
|
end
|
30
13
|
|
31
|
-
|
14
|
+
describe 'GET /_ruote/schedules' do
|
32
15
|
|
33
|
-
|
16
|
+
before(:each) do
|
34
17
|
|
35
|
-
|
18
|
+
@wfid0 = RuoteKit.engine.launch(Ruote.define do
|
19
|
+
wait :for => '3d'
|
20
|
+
end)
|
21
|
+
@wfid1 = RuoteKit.engine.launch(Ruote.define do
|
22
|
+
sequence do
|
23
|
+
alpha :timeout => '2d'
|
24
|
+
end
|
25
|
+
end)
|
26
|
+
@wfid2 = RuoteKit.engine.launch(Ruote.define do
|
27
|
+
nada
|
28
|
+
end)
|
36
29
|
|
37
|
-
|
38
|
-
|
30
|
+
RuoteKit.engine.wait_for(:alpha)
|
31
|
+
end
|
39
32
|
|
40
|
-
|
41
|
-
|
33
|
+
it 'lists schedules (HTML)' do
|
34
|
+
|
35
|
+
get '/_ruote/schedules'
|
42
36
|
|
43
|
-
|
37
|
+
last_response.status.should be(200)
|
44
38
|
|
45
|
-
|
39
|
+
last_response.should have_selector(
|
40
|
+
'a[rel="http://ruote.rubyforge.org/rels.html#process_schedules"]')
|
46
41
|
|
47
|
-
|
42
|
+
last_response.should contain('1 to 2 of 2 schedules')
|
43
|
+
end
|
48
44
|
|
49
|
-
|
50
|
-
#puts Rufus::Json.pretty_encode(json)
|
45
|
+
it 'lists schedules (JSON)' do
|
51
46
|
|
52
|
-
|
47
|
+
get '/_ruote/schedules.json'
|
53
48
|
|
54
|
-
|
49
|
+
last_response.status.should be(200)
|
55
50
|
|
56
|
-
|
57
|
-
|
58
|
-
]
|
51
|
+
json = last_response.json_body
|
52
|
+
#puts Rufus::Json.pretty_encode(json)
|
59
53
|
|
60
|
-
|
61
|
-
schedules.first['owner'].should be_kind_of(Hash)
|
54
|
+
schedules = json['schedules']
|
62
55
|
|
63
|
-
|
64
|
-
prefixes = hrefs.collect { |h| h.split('!').first }.sort
|
65
|
-
suffixes = hrefs.collect { |h| h.split('!').last }.sort
|
56
|
+
schedules.size.should == 2
|
66
57
|
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
pieces = h.split('!')
|
71
|
-
pieces.first + '/' + pieces.last
|
72
|
-
}.sort
|
58
|
+
schedules.first.keys.sort.should == %w[
|
59
|
+
_id action at flavour links original owner put_at target type wfid
|
60
|
+
]
|
73
61
|
|
74
|
-
|
75
|
-
[
|
76
|
-
|
62
|
+
schedules.first['target'].should be_kind_of(Hash)
|
63
|
+
schedules.first['owner'].should be_kind_of(Hash)
|
64
|
+
|
65
|
+
hrefs = schedules.collect { |s| s['links'].first['href'] }
|
66
|
+
prefixes = hrefs.collect { |h| h.split('!').first }.sort
|
67
|
+
suffixes = hrefs.collect { |h| h.split('!').last }.sort
|
68
|
+
|
69
|
+
hrefs = schedules.collect { |s|
|
70
|
+
s['links'].first['href']
|
71
|
+
}.collect { |h|
|
72
|
+
pieces = h.split('!')
|
73
|
+
pieces.first + '/' + pieces.last
|
74
|
+
}.sort
|
75
|
+
|
76
|
+
hrefs.should ==
|
77
|
+
[ "/_ruote/expressions/0_0/#{@wfid0}",
|
78
|
+
"/_ruote/expressions/0_0_0/#{@wfid1}" ]
|
79
|
+
end
|
77
80
|
end
|
78
|
-
end
|
79
81
|
|
80
|
-
describe 'GET /_ruote/schedules
|
82
|
+
describe 'GET /_ruote/schedules/:wfid' do
|
81
83
|
|
82
|
-
|
84
|
+
before(:each) do
|
83
85
|
|
84
|
-
|
86
|
+
@wfid0 = RuoteKit.engine.launch(Ruote.define do
|
87
|
+
wait :for => '3d'
|
88
|
+
end)
|
89
|
+
@wfid1 = RuoteKit.engine.launch(Ruote.define do
|
90
|
+
sequence do
|
91
|
+
alpha :timeout => '2d'
|
92
|
+
end
|
93
|
+
end)
|
85
94
|
|
86
|
-
|
87
|
-
wait :for => '3d'
|
88
|
-
end)
|
89
|
-
@wfid1 = RuoteKit.engine.launch(Ruote.define do
|
90
|
-
sequence do
|
91
|
-
alpha :timeout => '2d'
|
92
|
-
end
|
93
|
-
end)
|
95
|
+
RuoteKit.engine.wait_for(:alpha)
|
94
96
|
|
95
|
-
|
96
|
-
|
97
|
+
@wfid2 = RuoteKit.engine.launch(Ruote.define do
|
98
|
+
bravo :timers => '1d: x, 2d: timeout'
|
99
|
+
end)
|
97
100
|
|
98
|
-
|
101
|
+
RuoteKit.engine.wait_for(:bravo)
|
102
|
+
end
|
99
103
|
|
100
|
-
|
101
|
-
end
|
104
|
+
it 'lists schedules (HTML)' do
|
102
105
|
|
103
|
-
|
106
|
+
get "/_ruote/schedules/#{@wfid1}"
|
104
107
|
|
105
|
-
|
108
|
+
last_response.status.should be(200)
|
109
|
+
end
|
106
110
|
|
107
|
-
|
108
|
-
|
111
|
+
it 'lists schedules (JSON)' do
|
112
|
+
|
113
|
+
get "/_ruote/schedules/#{@wfid0}.json"
|
114
|
+
|
115
|
+
last_response.status.should be(200)
|
116
|
+
|
117
|
+
#puts Rufus::Json.pretty_encode(last_response.json_body)
|
118
|
+
|
119
|
+
last_response.json_body['schedules'].size.should == 1
|
120
|
+
end
|
121
|
+
|
122
|
+
it 'list schedules with timers (nil target) (HTML)' do
|
109
123
|
|
110
|
-
|
124
|
+
get "/_ruote/schedules/#{@wfid2}"
|
111
125
|
|
112
|
-
|
126
|
+
last_response.status.should be(200)
|
127
|
+
end
|
113
128
|
|
114
|
-
|
129
|
+
it 'list schedules with timers (nil target) (JSON)' do
|
115
130
|
|
116
|
-
|
131
|
+
get "/_ruote/schedules/#{@wfid2}.json"
|
117
132
|
|
118
|
-
|
133
|
+
last_response.status.should be(200)
|
134
|
+
end
|
119
135
|
end
|
120
136
|
end
|
121
137
|
|
@@ -1,542 +1,551 @@
|
|
1
1
|
|
2
|
-
require
|
2
|
+
require 'spec_helper'
|
3
3
|
|
4
4
|
|
5
|
-
|
6
|
-
[
|
7
|
-
from, 'to', to, 'of', of, 'workitems'
|
8
|
-
].collect { |e|
|
9
|
-
e.to_s
|
10
|
-
}.join("\n ")
|
11
|
-
end
|
12
|
-
|
13
|
-
|
14
|
-
describe 'GET /_ruote/workitems' do
|
5
|
+
describe '/_ruote/workitems' do
|
15
6
|
|
16
7
|
before(:each) do
|
17
|
-
|
18
8
|
prepare_engine
|
19
9
|
end
|
20
|
-
|
21
10
|
after(:each) do
|
22
|
-
|
23
11
|
shutdown_and_purge_engine
|
24
12
|
end
|
25
13
|
|
26
|
-
|
14
|
+
def workitem_count(from, to, of)
|
27
15
|
|
28
|
-
|
29
|
-
|
30
|
-
get '/_ruote/workitems'
|
16
|
+
/\s#{from}\s+to\s+#{to}\s+of\s+#{of}\s/
|
17
|
+
end
|
31
18
|
|
32
|
-
|
19
|
+
describe 'GET /_ruote/workitems' do
|
33
20
|
|
34
|
-
|
35
|
-
end
|
21
|
+
context 'without any workitems' do
|
36
22
|
|
37
|
-
|
23
|
+
it 'reports no workitems (HTML)' do
|
38
24
|
|
39
|
-
|
25
|
+
get '/_ruote/workitems'
|
40
26
|
|
41
|
-
|
42
|
-
json = last_response.json_body
|
27
|
+
last_response.should be_ok
|
43
28
|
|
44
|
-
|
45
|
-
|
46
|
-
end
|
47
|
-
end
|
29
|
+
last_response.should match(workitem_count(0, 0, 0))
|
30
|
+
end
|
48
31
|
|
49
|
-
|
32
|
+
it 'reports no workitems (JSON)' do
|
50
33
|
|
51
|
-
|
34
|
+
get '/_ruote/workitems.json'
|
52
35
|
|
53
|
-
|
36
|
+
last_response.should be_ok
|
37
|
+
json = last_response.json_body
|
54
38
|
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
end
|
59
|
-
end)
|
60
|
-
|
61
|
-
RuoteKit.engine.wait_for(:nada)
|
62
|
-
RuoteKit.engine.wait_for(1)
|
39
|
+
json.should have_key('workitems')
|
40
|
+
json['workitems'].should be_empty
|
41
|
+
end
|
63
42
|
end
|
64
43
|
|
65
|
-
|
44
|
+
context 'with workitems' do
|
66
45
|
|
67
|
-
|
46
|
+
before(:each) do
|
68
47
|
|
69
|
-
|
70
|
-
end
|
48
|
+
register_participants
|
71
49
|
|
72
|
-
|
50
|
+
@wfid = RuoteKit.engine.launch(Ruote.process_definition do
|
51
|
+
sequence do
|
52
|
+
nada :activity => 'Work your magic'
|
53
|
+
end
|
54
|
+
end)
|
73
55
|
|
74
|
-
|
56
|
+
RuoteKit.engine.wait_for(:nada)
|
57
|
+
RuoteKit.engine.wait_for(1)
|
58
|
+
end
|
75
59
|
|
76
|
-
|
77
|
-
json = last_response.json_body
|
60
|
+
it 'returns a list of workitems (HTML)' do
|
78
61
|
|
79
|
-
|
62
|
+
get '/_ruote/workitems'
|
80
63
|
|
81
|
-
|
64
|
+
last_response.should match(workitem_count(1, 1, 1))
|
65
|
+
last_response.should have_selector('td', :content => @wfid)
|
66
|
+
end
|
82
67
|
|
83
|
-
|
84
|
-
wi['wfid'].should == @wfid
|
85
|
-
wi['participant_name'].should == 'nada'
|
86
|
-
wi['fields']['params']['activity'].should == 'Work your magic'
|
87
|
-
end
|
88
|
-
end
|
89
|
-
end
|
68
|
+
it 'returns a list of workitems (JSON)' do
|
90
69
|
|
91
|
-
|
70
|
+
get '/_ruote/workitems.json'
|
92
71
|
|
93
|
-
|
72
|
+
last_response.status.should == 200
|
94
73
|
|
95
|
-
|
96
|
-
end
|
74
|
+
json = last_response.json_body
|
97
75
|
|
98
|
-
|
76
|
+
json['workitems'].size.should == 1
|
99
77
|
|
100
|
-
|
101
|
-
end
|
78
|
+
wi = json['workitems'][0]
|
102
79
|
|
103
|
-
|
80
|
+
wi.keys.should include('fei', 'participant_name', 'fields')
|
81
|
+
wi['wfid'].should == @wfid
|
82
|
+
wi['participant_name'].should == 'nada'
|
83
|
+
wi['fields']['params']['activity'].should == 'Work your magic'
|
84
|
+
end
|
104
85
|
|
105
|
-
|
86
|
+
it 'respects skip and limit (HTML)' do
|
106
87
|
|
107
|
-
|
88
|
+
get '/_ruote/workitems?limit=100&skip=0'
|
108
89
|
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
nada :activity => 'Or that'
|
113
|
-
end
|
114
|
-
end)
|
90
|
+
last_response.should match(workitem_count(1, 1, 1))
|
91
|
+
last_response.should have_selector('td', :content => @wfid)
|
92
|
+
end
|
115
93
|
|
116
|
-
|
117
|
-
RuoteKit.engine.wait_for(1)
|
118
|
-
end
|
94
|
+
it 'respects skip and limit (JSON)' do
|
119
95
|
|
120
|
-
|
96
|
+
get '/_ruote/workitems.json?limit=100&skip=0'
|
121
97
|
|
122
|
-
|
98
|
+
last_response.status.should == 200
|
123
99
|
|
124
|
-
|
100
|
+
json = last_response.json_body
|
125
101
|
|
126
|
-
|
127
|
-
|
102
|
+
json['workitems'].size.should == 1
|
103
|
+
end
|
128
104
|
end
|
105
|
+
end
|
129
106
|
|
130
|
-
|
107
|
+
describe 'GET /_ruote/workitems/:wfid' do
|
131
108
|
|
132
|
-
|
109
|
+
context 'with workitems' do
|
133
110
|
|
134
|
-
|
111
|
+
before(:each) do
|
135
112
|
|
136
|
-
|
113
|
+
register_participants
|
137
114
|
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
|
115
|
+
@wfid = RuoteKit.engine.launch(Ruote.process_definition do
|
116
|
+
concurrence do
|
117
|
+
nada :activity => 'This'
|
118
|
+
nada :activity => 'Or that'
|
119
|
+
end
|
120
|
+
end)
|
142
121
|
|
143
|
-
|
122
|
+
RuoteKit.engine.wait_for(:nada)
|
123
|
+
RuoteKit.engine.wait_for(1)
|
124
|
+
end
|
144
125
|
|
145
|
-
|
126
|
+
it 'lists the workitems (HTML)' do
|
146
127
|
|
147
|
-
|
128
|
+
get "/_ruote/workitems/#{@wfid}"
|
148
129
|
|
149
|
-
|
130
|
+
last_response.should be_ok
|
150
131
|
|
151
|
-
|
152
|
-
|
153
|
-
|
132
|
+
last_response.should have_selector(
|
133
|
+
'div#pagination', :content => '2 workitems')
|
134
|
+
end
|
154
135
|
|
155
|
-
|
136
|
+
it 'lists the workitems (JSON)' do
|
156
137
|
|
157
|
-
|
138
|
+
get "/_ruote/workitems/#{@wfid}.json"
|
158
139
|
|
159
|
-
|
140
|
+
last_response.should be_ok
|
160
141
|
|
161
|
-
|
142
|
+
json = last_response.json_body
|
162
143
|
|
163
|
-
|
164
|
-
|
144
|
+
json.should have_key('workitems')
|
145
|
+
json['workitems'].should_not be_empty
|
146
|
+
end
|
165
147
|
end
|
166
|
-
end
|
167
|
-
end
|
168
148
|
|
169
|
-
|
149
|
+
context 'without workitems' do
|
170
150
|
|
171
|
-
|
151
|
+
it 'reports no workitems (HTML)' do
|
172
152
|
|
173
|
-
|
174
|
-
end
|
153
|
+
get '/_ruote/workitems/foo'
|
175
154
|
|
176
|
-
|
155
|
+
last_response.should be_ok
|
177
156
|
|
178
|
-
|
179
|
-
|
157
|
+
last_response.should have_selector(
|
158
|
+
'div#pagination', :content => '0 workitems')
|
159
|
+
end
|
180
160
|
|
181
|
-
|
161
|
+
it 'reports an empty list (JSON)' do
|
182
162
|
|
183
|
-
|
163
|
+
get '/_ruote/workitems/foo.json'
|
184
164
|
|
185
|
-
|
186
|
-
sequence do
|
187
|
-
nada :activity => 'Work your magic'
|
188
|
-
end
|
189
|
-
end)
|
165
|
+
last_response.should be_ok
|
190
166
|
|
191
|
-
|
167
|
+
json = last_response.json_body
|
192
168
|
|
193
|
-
|
169
|
+
json.should have_key('workitems')
|
170
|
+
json['workitems'].should be_empty
|
171
|
+
end
|
194
172
|
end
|
173
|
+
end
|
195
174
|
|
196
|
-
|
175
|
+
describe 'GET /_ruote/workitems/expid!subid!wfid' do
|
197
176
|
|
198
|
-
|
177
|
+
context 'with a workitem' do
|
199
178
|
|
200
|
-
|
201
|
-
end
|
179
|
+
before(:each) do
|
202
180
|
|
203
|
-
|
181
|
+
register_participants
|
204
182
|
|
205
|
-
|
183
|
+
@wfid = RuoteKit.engine.launch(
|
184
|
+
Ruote.process_definition(:name => 'x', :rev => 'y') do
|
185
|
+
sequence do
|
186
|
+
nada :activity => 'Work your magic'
|
187
|
+
end
|
188
|
+
end)
|
206
189
|
|
207
|
-
|
208
|
-
end
|
190
|
+
RuoteKit.engine.wait_for(:nada)
|
209
191
|
|
210
|
-
|
192
|
+
@fei = engine.process(@wfid).expressions.last.fei
|
193
|
+
end
|
211
194
|
|
212
|
-
|
195
|
+
it 'returns it (HTML)' do
|
213
196
|
|
214
|
-
|
215
|
-
li['rel']
|
216
|
-
}.should == %w[
|
217
|
-
self
|
218
|
-
http://ruote.rubyforge.org/rels.html#process
|
219
|
-
http://ruote.rubyforge.org/rels.html#process_expressions
|
220
|
-
http://ruote.rubyforge.org/rels.html#process_errors
|
221
|
-
]
|
222
|
-
end
|
197
|
+
get "/_ruote/workitems/#{@fei.sid}"
|
223
198
|
|
224
|
-
|
199
|
+
last_response.should be_ok
|
200
|
+
end
|
225
201
|
|
226
|
-
|
202
|
+
it 'returns it (JSON)' do
|
227
203
|
|
228
|
-
|
229
|
-
last_response.headers['ETag'].should == "\"#{find_workitem(@wfid, @nada_exp_id).to_h['_rev'].to_s}\""
|
230
|
-
end
|
204
|
+
get "/_ruote/workitems/#{@fei.sid}.json"
|
231
205
|
|
232
|
-
|
206
|
+
last_response.should be_ok
|
207
|
+
end
|
233
208
|
|
234
|
-
|
209
|
+
it 'provides a workitem with the correct links (JSON)' do
|
210
|
+
|
211
|
+
get "/_ruote/workitems/#{@fei.sid}.json"
|
212
|
+
|
213
|
+
last_response.json_body['workitem']['links'].collect { |li|
|
214
|
+
li['rel']
|
215
|
+
}.should == %w[
|
216
|
+
self
|
217
|
+
http://ruote.rubyforge.org/rels.html#process
|
218
|
+
http://ruote.rubyforge.org/rels.html#expression
|
219
|
+
http://ruote.rubyforge.org/rels.html#process_expressions
|
220
|
+
http://ruote.rubyforge.org/rels.html#process_errors
|
221
|
+
]
|
222
|
+
|
223
|
+
link_for(
|
224
|
+
last_response.json_body['workitem']['links'], 'self'
|
225
|
+
).should ==
|
226
|
+
"/_ruote/workitems/#{@fei.sid}"
|
227
|
+
|
228
|
+
link_for(
|
229
|
+
last_response.json_body['workitem']['links'], '#expression'
|
230
|
+
).should ==
|
231
|
+
"/_ruote/expressions/#{@fei.sid}"
|
232
|
+
|
233
|
+
link_for(
|
234
|
+
last_response.json_body['workitem']['links'], '#process_expressions'
|
235
|
+
).should ==
|
236
|
+
"/_ruote/expressions/#{@fei.wfid}"
|
237
|
+
end
|
235
238
|
|
236
|
-
|
237
|
-
last_response.headers['ETag'].should == "\"#{find_workitem(@wfid, @nada_exp_id).to_h['_rev'].to_s}\""
|
238
|
-
end
|
239
|
-
end
|
239
|
+
it 'includes an etag header (HTML)' do
|
240
240
|
|
241
|
-
|
241
|
+
get "/_ruote/workitems/#{@fei.sid}"
|
242
242
|
|
243
|
-
|
243
|
+
last_response.headers.should include('ETag')
|
244
|
+
last_response.headers['ETag'].should == "\"#{find_workitem(@wfid, @nada_exp_id).to_h['_rev'].to_s}\""
|
245
|
+
end
|
244
246
|
|
245
|
-
|
247
|
+
it 'includes an etag header (JSON)' do
|
246
248
|
|
247
|
-
|
248
|
-
last_response.status.should be(404)
|
249
|
-
end
|
249
|
+
get "/_ruote/workitems/#{@fei.sid}.json"
|
250
250
|
|
251
|
-
|
251
|
+
last_response.headers.should include('ETag')
|
252
|
+
last_response.headers['ETag'].should == "\"#{find_workitem(@wfid, @nada_exp_id).to_h['_rev'].to_s}\""
|
253
|
+
end
|
254
|
+
|
255
|
+
it 'includes a wf_name and a wf_revision (JSON)' do
|
252
256
|
|
253
|
-
|
257
|
+
get "/_ruote/workitems/#{@fei.sid}.json"
|
254
258
|
|
255
|
-
|
256
|
-
|
259
|
+
last_response.json_body['workitem']['wf_name'].should_not == nil
|
260
|
+
last_response.json_body['workitem']['wf_revision'].should_not == nil
|
261
|
+
end
|
257
262
|
end
|
258
|
-
end
|
259
|
-
end
|
260
263
|
|
261
|
-
|
264
|
+
context 'without a workitem' do
|
262
265
|
|
263
|
-
|
266
|
+
it 'returns a 404 (HTML)' do
|
264
267
|
|
265
|
-
|
268
|
+
get '/_ruote/workitems/foo/bar'
|
266
269
|
|
267
|
-
|
268
|
-
|
269
|
-
nada :activity => 'Work your magic'
|
270
|
-
echo '${f:foo}'
|
270
|
+
last_response.should_not be_ok
|
271
|
+
last_response.status.should be(404)
|
271
272
|
end
|
272
|
-
end)
|
273
273
|
|
274
|
-
|
274
|
+
it 'returns a 404 (JSON)' do
|
275
275
|
|
276
|
-
|
276
|
+
get '/_ruote/workitems/foo/bar.json'
|
277
277
|
|
278
|
-
|
279
|
-
|
280
|
-
|
281
|
-
|
282
|
-
|
283
|
-
after(:each) do
|
284
|
-
|
285
|
-
shutdown_and_purge_engine
|
278
|
+
last_response.should_not be_ok
|
279
|
+
last_response.status.should be(404)
|
280
|
+
end
|
281
|
+
end
|
286
282
|
end
|
287
283
|
|
288
|
-
|
284
|
+
describe 'PUT /_ruote/workitems/:fei' do
|
289
285
|
|
290
|
-
|
291
|
-
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}",
|
292
|
-
:fields => Rufus::Json.encode(@fields))
|
286
|
+
before(:each) do
|
293
287
|
|
294
|
-
|
288
|
+
register_participants
|
295
289
|
|
296
|
-
|
297
|
-
|
290
|
+
@wfid = RuoteKit.engine.launch(Ruote.process_definition do
|
291
|
+
sequence do
|
292
|
+
nada :activity => 'Work your magic'
|
293
|
+
echo '${f:foo}'
|
294
|
+
end
|
295
|
+
end)
|
298
296
|
|
299
|
-
|
297
|
+
RuoteKit.engine.wait_for(:nada)
|
300
298
|
|
301
|
-
|
299
|
+
@fei = engine.process(@wfid).expressions.last.fei
|
302
300
|
|
303
|
-
|
304
|
-
|
301
|
+
@fields = {
|
302
|
+
'params' => { 'activity' => 'Work your magic' }, 'foo' => 'bar'
|
303
|
+
}
|
304
|
+
end
|
305
305
|
|
306
|
-
|
306
|
+
it 'updates the workitem fields (HTML)' do
|
307
307
|
|
308
|
-
|
308
|
+
put(
|
309
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}",
|
310
|
+
:fields => Rufus::Json.encode(@fields))
|
309
311
|
|
310
|
-
|
311
|
-
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
312
|
-
Rufus::Json.encode(params),
|
313
|
-
{ 'CONTENT_TYPE' => 'application/json' })
|
312
|
+
last_response.should be_redirect
|
314
313
|
|
315
|
-
|
314
|
+
last_response['Location'].should ==
|
315
|
+
"http://example.org/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}"
|
316
316
|
|
317
|
-
|
317
|
+
find_workitem(@wfid, @nada_exp_id).fields.should == @fields
|
318
318
|
|
319
|
-
|
319
|
+
sleep 0.4
|
320
320
|
|
321
|
-
|
322
|
-
|
321
|
+
@tracer.to_s.should == ''
|
322
|
+
end
|
323
323
|
|
324
|
-
|
324
|
+
it 'updates the workitem fields (JSON)' do
|
325
325
|
|
326
|
-
|
326
|
+
params = { 'fields' => @fields }
|
327
327
|
|
328
|
-
|
329
|
-
|
330
|
-
|
331
|
-
|
328
|
+
put(
|
329
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
330
|
+
Rufus::Json.encode(params),
|
331
|
+
{ 'CONTENT_TYPE' => 'application/json' })
|
332
332
|
|
333
|
-
|
333
|
+
last_response.should be_ok
|
334
334
|
|
335
|
-
|
336
|
-
end
|
335
|
+
find_workitem(@wfid, @nada_exp_id).fields.should == @fields
|
337
336
|
|
338
|
-
|
337
|
+
sleep 0.4
|
339
338
|
|
340
|
-
|
339
|
+
@tracer.to_s.should == ''
|
340
|
+
end
|
341
341
|
|
342
|
-
|
343
|
-
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}",
|
344
|
-
:fields => fields,
|
345
|
-
:_proceed => '1')
|
342
|
+
it 'updates the fields when passed {"workitem":...} (JSON)' do
|
346
343
|
|
347
|
-
|
348
|
-
last_response['Location'].should == "/_ruote/workitems/#{@wfid}"
|
344
|
+
params = { 'workitem' => { 'fields' => @fields } }
|
349
345
|
|
350
|
-
|
351
|
-
|
352
|
-
|
353
|
-
|
354
|
-
sleep 0.5
|
346
|
+
put(
|
347
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
348
|
+
Rufus::Json.encode(params),
|
349
|
+
{ 'CONTENT_TYPE' => 'application/json' })
|
355
350
|
|
356
|
-
|
357
|
-
end
|
351
|
+
last_response.should be_ok
|
358
352
|
|
359
|
-
|
353
|
+
find_workitem(@wfid, @nada_exp_id).fields.should == @fields
|
354
|
+
end
|
360
355
|
|
361
|
-
|
356
|
+
it 'replies to the engine (HTML)' do
|
362
357
|
|
363
|
-
|
364
|
-
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
365
|
-
Rufus::Json.encode(params),
|
366
|
-
{ 'CONTENT_TYPE' => 'application/json' })
|
358
|
+
fields = Rufus::Json.encode(@fields)
|
367
359
|
|
368
|
-
|
360
|
+
put(
|
361
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}",
|
362
|
+
:fields => fields,
|
363
|
+
:_proceed => '1')
|
369
364
|
|
370
|
-
|
371
|
-
|
372
|
-
# [ :errors, nil, { :wfid => @wfid } ]
|
373
|
-
#])
|
374
|
-
sleep 0.5
|
365
|
+
last_response.should be_redirect
|
366
|
+
last_response['Location'].should == "http://example.org/_ruote/workitems/#{@wfid}"
|
375
367
|
|
376
|
-
|
377
|
-
|
368
|
+
#engine.context[:s_logger].wait_for([
|
369
|
+
# [ :processes, :terminated, { :wfid => @wfid } ],
|
370
|
+
# [ :errors, nil, { :wfid => @wfid } ]
|
371
|
+
#])
|
372
|
+
sleep 0.5
|
378
373
|
|
379
|
-
|
374
|
+
@tracer.to_s.should == 'bar'
|
375
|
+
end
|
380
376
|
|
381
|
-
|
382
|
-
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
383
|
-
:fields => '{"bogus"}')
|
377
|
+
it 'replies to the engine (JSON)' do
|
384
378
|
|
385
|
-
|
386
|
-
end
|
379
|
+
params = { 'fields' => @fields, '_proceed' => '1' }
|
387
380
|
|
388
|
-
|
381
|
+
put(
|
382
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
383
|
+
Rufus::Json.encode(params),
|
384
|
+
{ 'CONTENT_TYPE' => 'application/json' })
|
389
385
|
|
390
|
-
|
391
|
-
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
392
|
-
"{'bogus'}",
|
393
|
-
{ 'CONTENT_TYPE' => 'application/json' })
|
386
|
+
last_response.should be_ok
|
394
387
|
|
395
|
-
|
396
|
-
|
388
|
+
#engine.context[:s_logger].wait_for([
|
389
|
+
# [ :processes, :terminated, { :wfid => @wfid } ],
|
390
|
+
# [ :errors, nil, { :wfid => @wfid } ]
|
391
|
+
#])
|
392
|
+
sleep 0.5
|
397
393
|
|
398
|
-
|
394
|
+
@tracer.to_s.should == 'bar'
|
395
|
+
end
|
399
396
|
|
400
|
-
|
401
|
-
old_rev = workitem.to_h['_rev']
|
397
|
+
it 'goes 400 when passed bogus JSON fields (HTML)' do
|
402
398
|
|
403
|
-
|
404
|
-
|
399
|
+
put(
|
400
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
401
|
+
:fields => '{"bogus"}')
|
405
402
|
|
406
|
-
|
407
|
-
|
408
|
-
{ :fields => Rufus::Json.encode(@fields) },
|
409
|
-
{ 'HTTP_IF_MATCH' => ('"%s"' % old_rev) }
|
410
|
-
)
|
403
|
+
last_response.status.should be(400)
|
404
|
+
end
|
411
405
|
|
412
|
-
|
413
|
-
end
|
406
|
+
it 'goes 400 when passed bogus JSON fields (JSON)' do
|
414
407
|
|
415
|
-
|
408
|
+
put(
|
409
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
410
|
+
"{'bogus'}",
|
411
|
+
{ 'CONTENT_TYPE' => 'application/json' })
|
416
412
|
|
417
|
-
|
413
|
+
last_response.status.should be(400)
|
414
|
+
end
|
418
415
|
|
419
|
-
|
416
|
+
it 'goes 412 if the etags do not match (HTML)' do
|
420
417
|
|
421
|
-
|
422
|
-
|
418
|
+
workitem = find_workitem(@wfid, @nada_exp_id)
|
419
|
+
old_rev = workitem.to_h['_rev']
|
423
420
|
|
424
|
-
|
421
|
+
workitem.fields = {'baz' => 'bar'}.merge!(@fields)
|
422
|
+
RuoteKit.engine.storage_participant.update(workitem)
|
425
423
|
|
426
|
-
|
427
|
-
|
428
|
-
|
429
|
-
|
430
|
-
|
431
|
-
'HTTP_IF_MATCH' => ('"%s"' % old_rev)
|
432
|
-
}
|
433
|
-
)
|
424
|
+
put(
|
425
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}",
|
426
|
+
{ :fields => Rufus::Json.encode(@fields) },
|
427
|
+
{ 'HTTP_IF_MATCH' => ('"%s"' % old_rev) }
|
428
|
+
)
|
434
429
|
|
435
|
-
|
436
|
-
|
437
|
-
end
|
430
|
+
last_response.status.should be(412)
|
431
|
+
end
|
438
432
|
|
439
|
-
|
433
|
+
it 'goes 412 if the etags do not match (JSON)' do
|
440
434
|
|
441
|
-
|
435
|
+
workitem = find_workitem(@wfid, @nada_exp_id)
|
442
436
|
|
443
|
-
|
437
|
+
old_rev = workitem.to_h['_rev']
|
444
438
|
|
445
|
-
|
446
|
-
|
447
|
-
concurrence do
|
448
|
-
sequence do
|
449
|
-
set 'wands' => 101
|
450
|
-
set 'hinkypinky' => 'honkytonky'
|
451
|
-
jack :activity => 'Fetch a pale'
|
452
|
-
end
|
453
|
-
sequence do
|
454
|
-
set 'hinkypinky' => 'honkytonky'
|
455
|
-
jill :activity => 'Chase Jack'
|
456
|
-
end
|
457
|
-
well :activity => 'Ready water'
|
458
|
-
end
|
459
|
-
end)
|
439
|
+
workitem.fields = {'baz' => 'bar'}.merge!(@fields)
|
440
|
+
RuoteKit.engine.storage_participant.update(workitem)
|
460
441
|
|
461
|
-
|
462
|
-
RuoteKit.engine.wait_for(1)
|
463
|
-
end
|
442
|
+
params = { 'workitem' => { 'fields' => @fields } }
|
464
443
|
|
465
|
-
|
444
|
+
put(
|
445
|
+
"/_ruote/workitems/#{@fei.expid}!#{@fei.subid}!#{@wfid}.json",
|
446
|
+
Rufus::Json.encode(params),
|
447
|
+
{
|
448
|
+
'CONTENT_TYPE' => 'application/json',
|
449
|
+
'HTTP_IF_MATCH' => ('"%s"' % old_rev)
|
450
|
+
}
|
451
|
+
)
|
466
452
|
|
467
|
-
|
453
|
+
last_response.status.should be(412)
|
454
|
+
end
|
468
455
|
end
|
469
456
|
|
470
|
-
describe '
|
457
|
+
describe 'Filtering workitems' do
|
471
458
|
|
472
|
-
|
459
|
+
before(:each) do
|
473
460
|
|
474
|
-
|
461
|
+
register_participants
|
475
462
|
|
476
|
-
|
463
|
+
@wfid = RuoteKit.engine.launch(Ruote.process_definition do
|
464
|
+
set 'foo' => 'bar'
|
465
|
+
concurrence do
|
466
|
+
sequence do
|
467
|
+
set 'wands' => 101
|
468
|
+
set 'hinkypinky' => 'honkytonky'
|
469
|
+
jack :activity => 'Fetch a pale'
|
470
|
+
end
|
471
|
+
sequence do
|
472
|
+
set 'hinkypinky' => 'honkytonky'
|
473
|
+
jill :activity => 'Chase Jack'
|
474
|
+
end
|
475
|
+
well :activity => 'Ready water'
|
476
|
+
end
|
477
|
+
end)
|
477
478
|
|
478
|
-
|
479
|
+
RuoteKit.engine.wait_for(:jack)
|
480
|
+
RuoteKit.engine.wait_for(1)
|
479
481
|
end
|
480
482
|
|
481
|
-
|
483
|
+
context 'on participants' do
|
482
484
|
|
483
|
-
|
485
|
+
it 'narrows results down to a single participant (JSON)' do
|
484
486
|
|
485
|
-
|
487
|
+
get '/_ruote/workitems.json', :participant => 'jack'
|
486
488
|
|
487
|
-
|
488
|
-
|
489
|
+
last_response.should be_ok
|
490
|
+
last_response.json_body['workitems'].size.should == 1
|
491
|
+
end
|
489
492
|
|
490
|
-
|
493
|
+
it 'narrows results down to a single participant (HTML)' do
|
491
494
|
|
492
|
-
|
495
|
+
get '/_ruote/workitems', :participant => 'jack'
|
493
496
|
|
494
|
-
|
497
|
+
last_response.should be_ok
|
498
|
+
last_response.should match(workitem_count(1, 3, 3))
|
499
|
+
end
|
495
500
|
|
496
|
-
|
501
|
+
end
|
497
502
|
|
498
|
-
|
503
|
+
context 'on field values' do
|
499
504
|
|
500
|
-
|
501
|
-
end
|
505
|
+
it 'finds workitems with fields set to a given value (JSON)' do
|
502
506
|
|
503
|
-
|
507
|
+
get '/_ruote/workitems.json', :hinkypinky => 'honkytonky'
|
504
508
|
|
505
|
-
|
509
|
+
last_response.should be_ok
|
510
|
+
last_response.json_body['workitems'].size.should == 2
|
511
|
+
end
|
506
512
|
|
507
|
-
|
508
|
-
end
|
513
|
+
it 'finds workitems with fields set to a given value (HTML)' do
|
509
514
|
|
510
|
-
|
515
|
+
get '/_ruote/workitems', :hinkypinky => 'honkytonky'
|
511
516
|
|
512
|
-
|
517
|
+
last_response.should be_ok
|
518
|
+
end
|
513
519
|
|
514
|
-
|
520
|
+
it 'respects JSON encoded filter vars (JSON)' do
|
515
521
|
|
516
|
-
|
517
|
-
end
|
522
|
+
get '/_ruote/workitems.json', :wands => 101
|
518
523
|
|
519
|
-
|
524
|
+
last_response.should be_ok
|
525
|
+
last_response.json_body['workitems'].size.should == 1
|
526
|
+
end
|
520
527
|
|
521
|
-
|
528
|
+
it 'respects JSON encoded filter vars (HTML)' do
|
522
529
|
|
523
|
-
|
524
|
-
end
|
530
|
+
get '/_ruote/workitems', :wands => 101
|
525
531
|
|
526
|
-
|
532
|
+
last_response.should be_ok
|
533
|
+
end
|
527
534
|
|
528
|
-
|
535
|
+
it "should combine search criteria by 'and' (JSON)" do
|
529
536
|
|
530
|
-
|
537
|
+
get '/_ruote/workitems.json', :hinkypinky => 'honkytonky', :wands => 101
|
531
538
|
|
532
|
-
|
533
|
-
|
539
|
+
last_response.should be_ok
|
540
|
+
last_response.json_body['workitems'].size.should == 1
|
541
|
+
end
|
534
542
|
|
535
|
-
|
543
|
+
it "should combine search criteria by 'and' (HMTL)" do
|
536
544
|
|
537
|
-
|
545
|
+
get '/_ruote/workitems', :hinkypinky => 'honkytonky', :wands => 101
|
538
546
|
|
539
|
-
|
547
|
+
last_response.should be_ok
|
548
|
+
end
|
540
549
|
end
|
541
550
|
end
|
542
551
|
end
|