openwferu 0.9.0

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.
Files changed (55) hide show
  1. data/README +47 -0
  2. data/lib/codec.rb +571 -0
  3. data/lib/controlclient.rb +115 -0
  4. data/lib/definitions.rb +112 -0
  5. data/lib/exception.rb +60 -0
  6. data/lib/flowexpressionid.rb +137 -0
  7. data/lib/openwferu.rb +43 -0
  8. data/lib/osocket.rb +138 -0
  9. data/lib/otime.rb +171 -0
  10. data/lib/restclient.rb +155 -0
  11. data/lib/ru/contextual.rb +63 -0
  12. data/lib/ru/dollar.rb +163 -0
  13. data/lib/ru/engine.rb +130 -0
  14. data/lib/ru/environment.rb +140 -0
  15. data/lib/ru/expressionmap.rb +120 -0
  16. data/lib/ru/expressionpool.rb +339 -0
  17. data/lib/ru/expressionstorage.rb +97 -0
  18. data/lib/ru/fe_base.rb +105 -0
  19. data/lib/ru/fe_concurrence.rb +122 -0
  20. data/lib/ru/fe_define.rb +101 -0
  21. data/lib/ru/fe_misc.rb +96 -0
  22. data/lib/ru/fe_participant.rb +75 -0
  23. data/lib/ru/fe_raw.rb +173 -0
  24. data/lib/ru/fe_subprocess.rb +84 -0
  25. data/lib/ru/fe_time.rb +135 -0
  26. data/lib/ru/fe_utils.rb +123 -0
  27. data/lib/ru/fe_value.rb +225 -0
  28. data/lib/ru/flowexpression.rb +250 -0
  29. data/lib/ru/logging.rb +85 -0
  30. data/lib/ru/participant.rb +67 -0
  31. data/lib/ru/participantmap.rb +93 -0
  32. data/lib/ru/participants.rb +74 -0
  33. data/lib/ru/rudefinitions.rb +70 -0
  34. data/lib/ru/ruutils.rb +68 -0
  35. data/lib/ru/scheduler.rb +478 -0
  36. data/lib/ru/schedulers.rb +63 -0
  37. data/lib/ru/service.rb +64 -0
  38. data/lib/test.rb +220 -0
  39. data/lib/utils.rb +94 -0
  40. data/lib/workitem.rb +250 -0
  41. data/lib/worklistclient.rb +276 -0
  42. data/test/dollartest.rb +79 -0
  43. data/test/feitest.rb +130 -0
  44. data/test/flowtestbase.rb +86 -0
  45. data/test/ft_0.rb +161 -0
  46. data/test/ft_1_unset.rb +152 -0
  47. data/test/ft_2_concurrence.rb +34 -0
  48. data/test/ft_3_equals.rb +84 -0
  49. data/test/ft_4_misc.rb +128 -0
  50. data/test/ft_5_time.rb +56 -0
  51. data/test/misctest.rb +46 -0
  52. data/test/runtest.rb +21 -0
  53. data/test/rutest_utils.rb +15 -0
  54. data/test/timetest.rb +111 -0
  55. metadata +100 -0
@@ -0,0 +1,276 @@
1
+ #
2
+ # Copyright (c) 2005-2006, John Mettraux, OpenWFE.org
3
+ # All rights reserved.
4
+ #
5
+ # Redistribution and use in source and binary forms, with or without
6
+ # modification, are permitted provided that the following conditions are met:
7
+ #
8
+ # . Redistributions of source code must retain the above copyright notice, this
9
+ # list of conditions and the following disclaimer.
10
+ #
11
+ # . Redistributions in binary form must reproduce the above copyright notice,
12
+ # this list of conditions and the following disclaimer in the documentation
13
+ # and/or other materials provided with the distribution.
14
+ #
15
+ # . Neither the name of the "OpenWFE" nor the names of its contributors may be
16
+ # used to endorse or promote products derived from this software without
17
+ # specific prior written permission.
18
+ #
19
+ # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20
+ # AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21
+ # IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22
+ # ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
23
+ # LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24
+ # CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25
+ # SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26
+ # INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27
+ # CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28
+ # ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
+ # POSSIBILITY OF SUCH DAMAGE.
30
+ #
31
+ # $Id: worklistclient.rb 3454 2006-10-08 16:51:00Z jmettraux $
32
+ #
33
+
34
+ #
35
+ # "hecho en Costa Rica"
36
+ #
37
+
38
+ require 'definitions'
39
+ require 'restclient'
40
+ require 'codec'
41
+
42
+
43
+ module OpenWFE
44
+
45
+ class WorklistClient < RestClient
46
+
47
+ def initialize (server, port, username, password)
48
+
49
+ super('http://'+server+':'+port.to_s(), username, password)
50
+ end
51
+
52
+ def initialize (url, username, password)
53
+
54
+ super(url, username, password)
55
+ end
56
+
57
+ #
58
+ # Returns the list of stores the worklist hosts
59
+ #
60
+ def listStores ()
61
+ r = self.get('listStores', nil, nil)
62
+ return decode(r)
63
+ end
64
+
65
+ #
66
+ # A synonym for listStores()
67
+ #
68
+ def getStoreNames ()
69
+ return listStores()
70
+ end
71
+
72
+ #
73
+ # Returns the headers of a given store.
74
+ #
75
+ def getHeaders (storeName, limit=1000)
76
+
77
+ params = {}
78
+ params["limit"] = limit
79
+
80
+ return decode(self.get('getHeaders', storeName, params))
81
+ end
82
+
83
+ def findFlowInstance (storeName, workflowInstanceId)
84
+
85
+ params = {}
86
+ params["id"] = workflowInstanceId
87
+
88
+ return decode(self.get('findFlowInstance', storeName, params))
89
+ end
90
+
91
+ #
92
+ # Launches a flow (on a given engine and with a given launchitem).
93
+ # The 'engineId' corresponds to an engine's participant name
94
+ # (see etc/engine/participant-map.xml)
95
+ #
96
+ def launchFlow (engineId, launchitem)
97
+
98
+ eli = OpenWFE.encode(launchitem)
99
+
100
+ params = {}
101
+ params[ENGINEID] = engineId
102
+
103
+ return decode(self.post('launchFlow', nil, params, eli))
104
+ end
105
+
106
+ #
107
+ # Returns a workitem (but doesn't put a lock on it, thus modifications
108
+ # to it cannot be communicated with saveWorkitem() or forwardWorkitem()
109
+ # to the worklist)
110
+ #
111
+ def getWorkitem (storeName, flowExpressionId)
112
+
113
+ return getItem('getWorkitem', storeName, flowExpressionId)
114
+ end
115
+
116
+ #
117
+ # Returns a workitem and makes sure it's locked in the worklist. Thus,
118
+ # the usage of the methods saveWorkitem() and forwardWorkitem() is
119
+ # possible.
120
+ #
121
+ def getAndLockWorkitem (storeName, flowExpressionId)
122
+
123
+ #puts "...getAndLockWorkitem() for #{flowExpressionId}"
124
+
125
+ return getItem('getAndLockWorkitem', storeName, flowExpressionId)
126
+ end
127
+
128
+ #
129
+ # Given a queryMap (a dict of keys and values), locks and returns
130
+ # the first workitem matching.
131
+ #
132
+ def queryAndLockWorkitem (storeName, queryMap)
133
+
134
+ hs = getHeaders(storeName)
135
+ hs.each do |h|
136
+
137
+ #puts "...h.id #{h.flowExpressionId}"
138
+ #h.attributes.each do |k, v|
139
+ # puts "......h '#{k}' => '#{v}'"
140
+ #end
141
+
142
+ ok = true
143
+ id = nil
144
+
145
+ queryMap.each do |key, value|
146
+
147
+ #puts "...'#{key}' => '#{h.attributes[key]}' ?= '#{value}'"
148
+ ok = (ok and h.attributes[key] == value)
149
+ #
150
+ # the parenthesis are very important
151
+
152
+ #puts " .ok is #{ok}"
153
+ #puts " .id is #{h.flowExpressionId}"
154
+ break if not ok
155
+ end
156
+
157
+ #puts " .id is #{h.flowExpressionId}"
158
+
159
+ return getAndLockWorkitem(storeName, h.flowExpressionId) if ok
160
+ end
161
+
162
+ return nil
163
+ end
164
+
165
+ #
166
+ # Notifies the worklist that the given workitem has to be unlocked
167
+ # any local (client-side) modification to it are ignored.
168
+ #
169
+ def releaseWorkitem (workitem)
170
+
171
+ return postItem('releaseWorkitem', workitem)
172
+ end
173
+
174
+ #
175
+ # Saves back the workitem in the worklist (and releases it)
176
+ #
177
+ def saveWorkitem (workitem)
178
+
179
+ return postItem('saveWorkitem', workitem)
180
+ end
181
+
182
+ #
183
+ # Returns the workitem to the worklist so that it can resume
184
+ # its flow (changes to the workitem are saved).
185
+ #
186
+ def proceedWorkitem (workitem)
187
+
188
+ return postItem('forwardWorkitem', workitem)
189
+ end
190
+
191
+ #
192
+ # A synonymous for proceedWorkitem (TODO : use ruby's alias trick)
193
+ #
194
+ def forwardWorkitem (workitem)
195
+
196
+ return proceedWorkitem(workitem)
197
+ end
198
+
199
+ #
200
+ # Returns the list of flow URLs the user owning this session may
201
+ # launch.
202
+ #
203
+ def listLaunchables ()
204
+
205
+ params = {}
206
+
207
+ #return decode(post('listLaunchables', nil, params, nil))
208
+ return decode(get('listLaunchables', nil, params))
209
+ end
210
+
211
+ #
212
+ # Delegate the workitem (transfer it to another store).
213
+ #
214
+ def delegate (workitem, targetStoreName)
215
+
216
+ ewi = OpenWFE.encode(workitem)
217
+
218
+ params = {}
219
+ params[TARGETSTORE] = targetStoreName
220
+
221
+ return decode(post('delegate', workitem.store, params, ewi))
222
+ end
223
+
224
+ #
225
+ # Delegate the workitem (ask the worklist to deliver it to
226
+ # another participant).
227
+ #
228
+ def delegateToParticipant (workitem, targetParticipantName)
229
+
230
+ ewi = OpenWFE.encode(workitem)
231
+
232
+ params = {}
233
+ params[TARGETPARTICIPANT] = targetParticipantName
234
+
235
+ return decode(post('delegate', workitem.store, params, ewi))
236
+ end
237
+
238
+ #def queryStore (storeName, query)
239
+ #end
240
+
241
+
242
+ protected
243
+
244
+ def decode (reply)
245
+
246
+ xml = REXML::Document.new(reply.body)
247
+ return OpenWFE.decode(xml.root)
248
+ end
249
+
250
+ def getItem (restMethodName, storeName, flowExpressionId)
251
+
252
+ fei = OpenWFE.encode(flowExpressionId)
253
+ fei = OpenWFE.docToString(fei, false)
254
+
255
+ params = {}
256
+
257
+ wi = decode(self.post(restMethodName, storeName, params, fei))
258
+
259
+ wi.store = storeName if wi
260
+
261
+ return wi
262
+ end
263
+
264
+ def postItem (restMethodName, workitem)
265
+
266
+ ewi = OpenWFE.encode(workitem)
267
+
268
+ params = {}
269
+
270
+ return decode(post(restMethodName, workitem.store, params, ewi))
271
+ end
272
+
273
+ end
274
+
275
+ end
276
+
@@ -0,0 +1,79 @@
1
+
2
+ #
3
+ # Testing OpenWFEru
4
+ #
5
+ # John Mettraux at openwfe.org
6
+ #
7
+ # Mon Oct 9 22:19:44 JST 2006
8
+ #
9
+
10
+ require 'test/unit'
11
+ require 'ru/dollar'
12
+
13
+ #
14
+ # testing the 'dollar notation'
15
+ #
16
+
17
+ class DollarTest < Test::Unit::TestCase
18
+
19
+ #def setup
20
+ #end
21
+
22
+ #def teardown
23
+ #end
24
+
25
+ def test_one
26
+ dict = {}
27
+ dict['renard'] = 'goupil'
28
+ dict['cane'] = 'oie'
29
+ dict['oie blanche'] = 'poule'
30
+
31
+ dotest("le petit renard", dict, "le petit renard")
32
+ dotest("le petit {renard}", dict, "le petit {renard}")
33
+ dotest("le petit ${renard}", dict, "le petit goupil")
34
+ dotest("le petit ${renard} noir", dict, "le petit goupil noir")
35
+
36
+ dotest("la grande ${${cane} blanche}", dict, "la grande poule")
37
+
38
+ dotest("le ${renard} et la ${cane}", dict, "le goupil et la oie")
39
+ #
40
+ # excuse my french...
41
+
42
+ dotest("le \\${renard} encore", dict, "le \\${renard} encore")
43
+
44
+ dotest("", dict, "")
45
+
46
+ dotest("""
47
+ """, dict, """
48
+ """)
49
+ dotest("""
50
+ """, dict, """
51
+ """)
52
+ end
53
+
54
+ def test_two
55
+ dict = {}
56
+ dict['x'] = 'y'
57
+ dotest("${x}", dict, "y")
58
+ dotest("\\${x}", dict, "\\${x}")
59
+ end
60
+
61
+ def test_three
62
+ dict = {}
63
+ dict['A'] = 'a'
64
+ dict['B'] = 'b'
65
+ dict['ab'] = 'ok'
66
+ dotest("${${A}${B}}", dict, "ok")
67
+ end
68
+
69
+ def dotest (text, dict, target)
70
+ result = OpenWFEru::dsub(text, dict)
71
+ #puts "..>#{text}<"
72
+ #puts "...->"
73
+ #puts "..>#{result}<"
74
+ #puts
75
+ assert \
76
+ result == target,
77
+ ">#{result}< != >#{target}<"
78
+ end
79
+ end
data/test/feitest.rb ADDED
@@ -0,0 +1,130 @@
1
+
2
+ #
3
+ # Testing OpenWFEru
4
+ #
5
+ # John Mettraux at openwfe.org
6
+ #
7
+ # Mon Oct 9 22:19:44 JST 2006
8
+ #
9
+
10
+ require 'test/unit'
11
+ require 'workitem'
12
+ require 'ru/rudefinitions'
13
+
14
+
15
+ class FeiTest < Test::Unit::TestCase
16
+
17
+ #def setup
18
+ #end
19
+
20
+ #def teardown
21
+ #end
22
+
23
+ def test_equality
24
+
25
+ fei1 = new_fei()
26
+ fei2 = new_fei()
27
+
28
+ assert \
29
+ fei1.object_id != fei2.object_id, \
30
+ "feis are not two distinct feis"
31
+ assert \
32
+ fei1.hash == fei2.hash, \
33
+ "feis do not have the same hash"
34
+ assert \
35
+ fei1 == fei2, \
36
+ "feis are not equals (==)"
37
+ assert \
38
+ fei1.eql?(fei2), \
39
+ "feis are not equals (eql?)"
40
+ end
41
+
42
+ def test_inequality
43
+
44
+ fei1 = new_fei()
45
+
46
+ fei2 = new_fei()
47
+ fei2.expressionName = OpenWFEru::EN_ENVIRONMENT
48
+
49
+ assert \
50
+ fei1.object_id != fei2.object_id, \
51
+ "feis are not two distinct feis"
52
+ assert \
53
+ fei1.hash != fei2.hash, \
54
+ "feis do have the same hash"
55
+ assert \
56
+ fei1 != fei2, \
57
+ "feis are equals (==)"
58
+ assert \
59
+ (not fei1.eql?(fei2)), \
60
+ "feis are equals (eql?)"
61
+ end
62
+
63
+ def test_in_hash
64
+ h = Hash.new()
65
+
66
+ fei1 = new_fei()
67
+ fei2 = new_fei()
68
+
69
+ h[fei1] = 'one'
70
+ h[fei2] = 'two'
71
+
72
+ #puts_hash(h)
73
+ #puts "fei1 : #{fei1.to_debug_s}"
74
+ #puts "fei2 : #{fei2.to_debug_s}"
75
+
76
+ assert \
77
+ h.size() == 1,
78
+ "h should have one entry"
79
+ assert \
80
+ h[fei1] == h[fei2],
81
+ "both keys should point to the same thing"
82
+ assert \
83
+ h[fei1] == 'two',
84
+ "value should be 'two' (fei1)"
85
+ assert \
86
+ h[fei2] == 'two',
87
+ "value should be 'two' (fei2)"
88
+ end
89
+
90
+ def test_dup
91
+ fei0 = new_fei()
92
+ fei1 = fei0.dup()
93
+
94
+ assert \
95
+ fei0 == fei1,
96
+ "feis should be equal"
97
+
98
+ fei1.expressionName = OpenWFEru::EN_ENVIRONMENT
99
+
100
+ assert \
101
+ fei0 != fei1,
102
+ "feis should not be equal"
103
+ end
104
+
105
+ protected
106
+
107
+ def new_fei ()
108
+ fei = OpenWFE::FlowExpressionId.new()
109
+ fei.owfeVersion = OpenWFEru::OPENWFE_VERSION
110
+ fei.engineId = 'this'
111
+ fei.initialEngineId = 'that'
112
+ fei.workflowDefinitionUrl = 'http://test/test.xml'
113
+ fei.workflowDefinitionName = 'test'
114
+ fei.workflowDefinitionRevision = '1.0'
115
+ fei.workflowInstanceId = '123456'
116
+ fei.expressionName = 'do-test'
117
+ fei.expressionId = '0.0'
118
+ return fei
119
+ end
120
+
121
+ def puts_hash (h)
122
+ puts
123
+ h.each do |k, v|
124
+ puts " * '#{k.to_debug_s}' --> '#{v}'"
125
+ end
126
+ puts
127
+ end
128
+
129
+ end
130
+
@@ -0,0 +1,86 @@
1
+
2
+ #
3
+ # Testing OpenWFEru
4
+ #
5
+ # John Mettraux at openwfe.org
6
+ #
7
+ # Sun Oct 29 15:41:44 JST 2006
8
+ #
9
+ # somewhere between Philippina and the Japan
10
+ #
11
+
12
+ require 'test/unit'
13
+ require 'workitem'
14
+ require 'ru/engine'
15
+ require 'ru/rudefinitions'
16
+ require 'ru/participants'
17
+ require 'rutest_utils'
18
+
19
+
20
+ class FlowTestBase < Test::Unit::TestCase
21
+
22
+ #def setup
23
+ #end
24
+
25
+ #def teardown
26
+ #end
27
+
28
+ def default_test ()
29
+ assert true
30
+ end
31
+
32
+ protected
33
+
34
+ def dotest (flowDef, expectedTrace, sleepTime=0)
35
+
36
+ engine = OpenWFEru::Engine.new()
37
+
38
+ engine.application_context["__tracer"] = Tracer.new
39
+
40
+ engine.register_participant('test-.*', OpenWFEru::PrintParticipant.new())
41
+
42
+ # register unique tracing participant
43
+
44
+ li = OpenWFE::LaunchItem.new()
45
+
46
+ li.workflowDefinitionUrl = "field:__definition"
47
+
48
+ li.attributes['__definition'] = flowDef
49
+ engine.launch(li)
50
+
51
+ sleep(sleepTime)
52
+
53
+ trace = engine.application_context["__tracer"].to_s
54
+
55
+ #puts "...'#{trace}' ?= '#{expectedTrace}'"
56
+
57
+ if expectedTrace.kind_of?([].class)
58
+ result = true
59
+ expectedTrace.each do |etrace|
60
+ result = result and trace == etrace
61
+ end
62
+ assert \
63
+ result,
64
+ "flow failed : trace doesn't correspond to any expected traces"
65
+ else
66
+ assert \
67
+ trace == expectedTrace, \
68
+ "flow failed : '#{trace}' != '#{expectedTrace}'"
69
+ end
70
+
71
+ exp_storage = \
72
+ engine.application_context[OpenWFEru::S_EXPRESSION_STORAGE]
73
+
74
+ if exp_storage.length != 1
75
+ puts
76
+ puts exp_storage.to_s
77
+ puts
78
+ end
79
+
80
+ assert \
81
+ exp_storage.length == 1,
82
+ "there are expressions remaining in the expression pool"
83
+ end
84
+
85
+ end
86
+