ruote-activeresource 2.0.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.
- data/.gitignore +1 -0
- data/CREDITS.txt +15 -0
- data/LICENSE.txt +21 -0
- data/README.rdoc +34 -0
- data/Rakefile +16 -0
- data/VERSION +1 -0
- data/lib/ruote/active_resource/part/active_resource_participant.rb +223 -0
- data/lib/work/wfidgen.last +1 -0
- data/test/path_helper.rb +9 -0
- data/test/test.rb +6 -0
- data/test/test_helper.rb +7 -0
- data/test/ut_1_participant.rb +75 -0
- metadata +89 -0
data/.gitignore
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
nbproject
|
data/CREDITS.txt
ADDED
data/LICENSE.txt
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
|
2
|
+
Copyright (c) 2001-2009, John Mettraux, jmettraux@gmail.com
|
3
|
+
|
4
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
5
|
+
of this software and associated documentation files (the "Software"), to deal
|
6
|
+
in the Software without restriction, including without limitation the rights
|
7
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
8
|
+
copies of the Software, and to permit persons to whom the Software is
|
9
|
+
furnished to do so, subject to the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be included in
|
12
|
+
all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
15
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
16
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
17
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
18
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
19
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
20
|
+
THE SOFTWARE.
|
21
|
+
|
data/README.rdoc
ADDED
@@ -0,0 +1,34 @@
|
|
1
|
+
|
2
|
+
= ruote-activeresource
|
3
|
+
|
4
|
+
ruote 2.0 extension for a participant using ActiveResource to send messages around
|
5
|
+
|
6
|
+
|
7
|
+
== usage
|
8
|
+
|
9
|
+
well...
|
10
|
+
|
11
|
+
|
12
|
+
== running tests
|
13
|
+
|
14
|
+
to run unit tests
|
15
|
+
|
16
|
+
ruby test/test.rb
|
17
|
+
|
18
|
+
|
19
|
+
== license
|
20
|
+
|
21
|
+
MIT
|
22
|
+
|
23
|
+
|
24
|
+
== links
|
25
|
+
|
26
|
+
http://api.rubyonrails.org/files/vendor/rails/activeresource/README.html
|
27
|
+
http://ruote.rubyforge.org/
|
28
|
+
|
29
|
+
|
30
|
+
== feedback
|
31
|
+
|
32
|
+
mailing list : http://groups.google.com/group/openwferu-users
|
33
|
+
irc : irc.freenode.net #ruote
|
34
|
+
|
data/Rakefile
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
begin
|
2
|
+
require 'jeweler'
|
3
|
+
Jeweler::Tasks.new do |gemspec|
|
4
|
+
gemspec.name = "ruote-activeresource"
|
5
|
+
gemspec.summary = "Ruote participant using ActiveResource"
|
6
|
+
gemspec.description = "A ruote participant implementation using ActiveResource to notify RESTful interfaces about workitems."
|
7
|
+
gemspec.email = "torsten.schoenebaum@planquadrat-software.de"
|
8
|
+
gemspec.homepage = "http://github.com/tosch/ruote-activeresource"
|
9
|
+
gemspec.authors = ["Torsten Schönebaum"]
|
10
|
+
gemspec.add_dependency('ruote', '>= 2.0.0')
|
11
|
+
gemspec.add_dependency('activeresource', '>= 2.0.0')
|
12
|
+
end
|
13
|
+
Jeweler::GemcutterTasks.new
|
14
|
+
rescue LoadError
|
15
|
+
puts "Jeweler not available. Install it with: sudo gem install jeweler"
|
16
|
+
end
|
data/VERSION
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
2.0.0
|
@@ -0,0 +1,223 @@
|
|
1
|
+
#--
|
2
|
+
# Copyright (c) 2008-2009, Torsten Schönebaum, John Mettraux (OpenWFE.org)
|
3
|
+
#
|
4
|
+
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
5
|
+
# of this software and associated documentation files (the "Software"), to deal
|
6
|
+
# in the Software without restriction, including without limitation the rights
|
7
|
+
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
8
|
+
# copies of the Software, and to permit persons to whom the Software is
|
9
|
+
# furnished to do so, subject to the following conditions:
|
10
|
+
#
|
11
|
+
# The above copyright notice and this permission notice shall be included in
|
12
|
+
# all copies or substantial portions of the Software.
|
13
|
+
#
|
14
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
15
|
+
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
16
|
+
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
17
|
+
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
18
|
+
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
19
|
+
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
20
|
+
# THE SOFTWARE.
|
21
|
+
#
|
22
|
+
# Made in Europe and Japan.
|
23
|
+
#++
|
24
|
+
|
25
|
+
|
26
|
+
require 'activeresource' # gem activeresource
|
27
|
+
|
28
|
+
require 'ruote/engine/context'
|
29
|
+
require 'ruote/part/local_participant'
|
30
|
+
|
31
|
+
|
32
|
+
module Ruote
|
33
|
+
module ActiveResource
|
34
|
+
|
35
|
+
#
|
36
|
+
# Ruote participant which does a REST call. It's using ActiveResource to do
|
37
|
+
# the actual magic. You can call every class and instance method
|
38
|
+
# ActiveResource::Base and its mixins provide. You can also process the
|
39
|
+
# response of the REST request and save some of its data into the workitem
|
40
|
+
# for example.
|
41
|
+
#
|
42
|
+
# Before using this participant you *really* should make yourself familiar
|
43
|
+
# with ActiveResource and its usage.
|
44
|
+
#
|
45
|
+
# ==Using it
|
46
|
+
#
|
47
|
+
# The participant should be registered in the engine in a way like this:
|
48
|
+
#
|
49
|
+
# engine.register_participant(
|
50
|
+
# 'reminder',
|
51
|
+
# ActiveResourceParticipant.new(
|
52
|
+
# {
|
53
|
+
# :site => 'http://localhost:7000',
|
54
|
+
# :resource_name => 'story',
|
55
|
+
# :method => 'put', # we will use ActiveResource::CustomMethods::InstanceMethods#put
|
56
|
+
# :argument => 'send_reminder', # put is happy with just one
|
57
|
+
# # parameter: The action to be
|
58
|
+
# # called. So we won't have to use a
|
59
|
+
# # block to set the arguments of the
|
60
|
+
# # ActiveResource method to call.
|
61
|
+
# }
|
62
|
+
# )
|
63
|
+
# )
|
64
|
+
#
|
65
|
+
# Let's try a more complex example:
|
66
|
+
#
|
67
|
+
# engine.register_participant(
|
68
|
+
# 'complex_ares',
|
69
|
+
# ActiveResourceParticipant.new(
|
70
|
+
# {
|
71
|
+
# :site => 'http://localhost:7000',
|
72
|
+
# :resource_name => 'story',
|
73
|
+
# :method => 'find', # yes, even ActiveResource::Base#find method
|
74
|
+
# # may be used...
|
75
|
+
# :response_handling => proc do |response, workitem| # define response
|
76
|
+
# # handling block
|
77
|
+
# workitem.set_attribute('title', response.attributes['title'])
|
78
|
+
# # The type of the response object depends on
|
79
|
+
# # the method you use!
|
80
|
+
# end
|
81
|
+
# }
|
82
|
+
# ) do |workitem| # define arguments to use with the find method
|
83
|
+
# # each argument is an entry in an array the block has to return
|
84
|
+
# [
|
85
|
+
# workitem.attributes['story_id'], # the first argument
|
86
|
+
# {:prefix => 'foo'} # the second one is an hash
|
87
|
+
# ]
|
88
|
+
# end
|
89
|
+
# )
|
90
|
+
#
|
91
|
+
# You can now use the participant in your workflow definitions. An example
|
92
|
+
# using XML:
|
93
|
+
#
|
94
|
+
# <concurrence count="1">
|
95
|
+
# <participant ref="qa" />
|
96
|
+
# <cron every="1m">
|
97
|
+
# <participant
|
98
|
+
# ref="reminder"
|
99
|
+
# site="http://localhost:7000"
|
100
|
+
# resource_name="story"
|
101
|
+
# method="put"
|
102
|
+
# action="send_reminder"
|
103
|
+
# resource_id="${field:story_id}" />
|
104
|
+
# </cron>
|
105
|
+
# </concurrence>
|
106
|
+
#
|
107
|
+
# Here, the ActiveResourceParticipant is used to send a reminder.
|
108
|
+
#
|
109
|
+
# *Note:* prefer configuration of the participant at registration time,
|
110
|
+
# information like 'method', 'site' and 'resource_name' may clutter the
|
111
|
+
# process definition.
|
112
|
+
#
|
113
|
+
class ActiveResourceParticipant
|
114
|
+
include Ruote::EngineContext
|
115
|
+
include Ruote::LocalParticipant
|
116
|
+
|
117
|
+
#
|
118
|
+
# == options hash
|
119
|
+
#
|
120
|
+
# You have to set some default options by passing an options hash to the
|
121
|
+
# new method. It should contain the following keys:
|
122
|
+
#
|
123
|
+
# <tt>:site</tt>:: The URI (as string) of the site where your REST
|
124
|
+
# interface sits. See <tt>site</tt> parameter in ActiveResource::Base.
|
125
|
+
# <tt>:resource_name</tt>:: The name of the resource you like to access.
|
126
|
+
# See <tt>element_name</tt> parameter in ActiveResource::Base.
|
127
|
+
# <tt>:method</tt>:: The ActiveResource method to call. In most cases
|
128
|
+
# should be "get", "put", "post" or "delete".
|
129
|
+
# <tt>:argument</tt>:: The first parameter which should be used as
|
130
|
+
# argument to the ActiveResource method which will be called. This value
|
131
|
+
# is ignored if a block is given (see below)
|
132
|
+
# <tt>:resource_id</tt>:: The ID of the resource on which the action
|
133
|
+
# should be called on default. If negative, nil or false, the action
|
134
|
+
# will be called on the complete set of resources instead of on a single
|
135
|
+
# resource determined by its ID.
|
136
|
+
# <tt>:response_handling</tt>:: A proc object / block which gets called
|
137
|
+
# after the request is done. It gets called with to arguments: The
|
138
|
+
# response of the ActiveResource method called and the workitem.
|
139
|
+
#
|
140
|
+
# The new method also takes a block. It may be used to set the arguments
|
141
|
+
# of the ActiveResource method to call. The block must return an array of
|
142
|
+
# arguments. The array will be splitted and each entry will be used as
|
143
|
+
# argument to the ActiveResource method called. The block itself takes one
|
144
|
+
# or two arguments: Either only the current workitem or the workitem and
|
145
|
+
# expstorage[workitem.fei].
|
146
|
+
#
|
147
|
+
# All parameters except response_handling and the block set default values
|
148
|
+
# -- you can always override them in the process definition. Just use the
|
149
|
+
# corresponding symbol name (without ":") as attribute.
|
150
|
+
#
|
151
|
+
def initialize (options, &block)
|
152
|
+
|
153
|
+
@options = options
|
154
|
+
|
155
|
+
# some defaults
|
156
|
+
@options[:site] ||= 'http://127.0.0.1:3000'
|
157
|
+
@options[:method] ||= :get
|
158
|
+
|
159
|
+
@block = block
|
160
|
+
end
|
161
|
+
|
162
|
+
#
|
163
|
+
# This method is called each time the participant receives a workitem. It
|
164
|
+
# calls the requested ActiveResource method, calls the response handling
|
165
|
+
# code if present and then immediatly replies to the engine.
|
166
|
+
#
|
167
|
+
def consume (workitem)
|
168
|
+
|
169
|
+
# use block to determine the method's arguments if given
|
170
|
+
args = if @block
|
171
|
+
if @block.arity == 1
|
172
|
+
@block.call(workitem)
|
173
|
+
else
|
174
|
+
@block.call(workitem, expstorage[workitem.fei])
|
175
|
+
end
|
176
|
+
elsif a = param(workitem, :arg) || param(workitem, :argument)
|
177
|
+
Array(a)
|
178
|
+
else
|
179
|
+
[] # no arguments
|
180
|
+
end
|
181
|
+
|
182
|
+
# create new subclass of ActiveResource::Base
|
183
|
+
active_resource_class = Class.new(::ActiveResource::Base)
|
184
|
+
active_resource_class.site = param(workitem, :site) # set site parameter
|
185
|
+
active_resource_class.element_name = param(workitem, :resource_name) # set element name
|
186
|
+
|
187
|
+
# Do we work on a single or on a set of resources? If resource_id is nil
|
188
|
+
# or negative, it's a set of resources.
|
189
|
+
|
190
|
+
resource_id = param(workitem, :resource_id)
|
191
|
+
|
192
|
+
active_resource = if (!resource_id) || (resource_id.to_i < 0)
|
193
|
+
# set of resources
|
194
|
+
active_resource_class
|
195
|
+
else
|
196
|
+
# specific resource
|
197
|
+
active_resource_class.new(:id => resource_id)
|
198
|
+
end
|
199
|
+
|
200
|
+
response = active_resource.send(param(workitem, :method), args)
|
201
|
+
|
202
|
+
# we got our response, but what to do with it?
|
203
|
+
if (h = param(workitem, :response_handling)).is_a?(Proc)
|
204
|
+
h.call(response, workitem)
|
205
|
+
end
|
206
|
+
|
207
|
+
# reply to the engine
|
208
|
+
reply_to_engine(workitem)
|
209
|
+
end
|
210
|
+
|
211
|
+
# Does nothing.
|
212
|
+
def cancel (fei, flavour)
|
213
|
+
end
|
214
|
+
|
215
|
+
protected
|
216
|
+
|
217
|
+
def param (workitem, key)
|
218
|
+
workitem.fields['params'][key.to_s] || @options[key]
|
219
|
+
end
|
220
|
+
end
|
221
|
+
|
222
|
+
end
|
223
|
+
end
|
@@ -0,0 +1 @@
|
|
1
|
+
2009/11/11 13:11:53.44553
|
data/test/path_helper.rb
ADDED
@@ -0,0 +1,9 @@
|
|
1
|
+
ruote_lib = File.expand_path(File.dirname(__FILE__) + '/../../ruota/lib')
|
2
|
+
ruote_lib = File.expand_path(File.dirname(__FILE__) + '/../../ruote/lib') \
|
3
|
+
unless File.exist?(ruote_lib)
|
4
|
+
|
5
|
+
ruote_dm_lib = File.expand_path(File.dirname(__FILE__) + '/../lib')
|
6
|
+
|
7
|
+
$:.unshift(ruote_lib) unless $:.include?(ruote_lib)
|
8
|
+
$:.unshift(ruote_dm_lib) unless $:.include?(ruote_dm_lib)
|
9
|
+
|
data/test/test.rb
ADDED
data/test/test_helper.rb
ADDED
@@ -0,0 +1,75 @@
|
|
1
|
+
#
|
2
|
+
# testing the ActiveResourceParticipant by Torsten Schoenebaum
|
3
|
+
#
|
4
|
+
# Tue Dec 16 09:01:28 JST 2008
|
5
|
+
#
|
6
|
+
|
7
|
+
require File.join(File.dirname(__FILE__), 'test_helper.rb')
|
8
|
+
|
9
|
+
require 'ruote/active_resource/part/active_resource_participant'
|
10
|
+
|
11
|
+
require 'active_resource/http_mock'
|
12
|
+
|
13
|
+
class AresParticipantTest < Test::Unit::TestCase
|
14
|
+
|
15
|
+
def setup
|
16
|
+
@engine = Engine.new()
|
17
|
+
|
18
|
+
@fruit1 = { 'id' => 1, 'name' => 'apple' }
|
19
|
+
@fruits = [ @fruit1 ]
|
20
|
+
|
21
|
+
ActiveResource::HttpMock.respond_to do |mck|
|
22
|
+
mck.get '/fruits/.xml', {}, @fruits.to_xml(:root => 'fruits')
|
23
|
+
mck.get '/fruits/1/.xml', {}, @fruit1.to_xml(:root => 'fruit')
|
24
|
+
#
|
25
|
+
# why /.xml ??, well... it's just some mocking after all...
|
26
|
+
# no time to dig deeper
|
27
|
+
end
|
28
|
+
end
|
29
|
+
|
30
|
+
def test_basic
|
31
|
+
|
32
|
+
response = nil
|
33
|
+
|
34
|
+
par = new_ares_participant({
|
35
|
+
:resource_name => 'fruit',
|
36
|
+
:response_handling => lambda { |r, wi| response = r }
|
37
|
+
})
|
38
|
+
|
39
|
+
workitem = new_workitem(:resource_id => 1)
|
40
|
+
|
41
|
+
par.consume(workitem)
|
42
|
+
|
43
|
+
assert_equal(@fruit1, response)
|
44
|
+
assert_equal({'params'=>{:resource_id=>1}}, @engine.workitem)
|
45
|
+
end
|
46
|
+
|
47
|
+
protected
|
48
|
+
|
49
|
+
class Engine
|
50
|
+
attr_accessor :workitem
|
51
|
+
def reply (wi)
|
52
|
+
@workitem = wi
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
def new_workitem (opts={})
|
57
|
+
wi = { 'params' => opts }
|
58
|
+
def wi.params
|
59
|
+
self['params'] ||= {}
|
60
|
+
end
|
61
|
+
wi
|
62
|
+
end
|
63
|
+
|
64
|
+
def new_ares_participant(opts={})
|
65
|
+
|
66
|
+
par = Ruote::ActiveResource::ActiveResourceParticipant.new(opts)
|
67
|
+
|
68
|
+
par.instance_variable_set(:@engine, @engine)
|
69
|
+
def par.engine
|
70
|
+
@engine
|
71
|
+
end
|
72
|
+
|
73
|
+
par
|
74
|
+
end
|
75
|
+
end
|
metadata
ADDED
@@ -0,0 +1,89 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: ruote-activeresource
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 2.0.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- "Torsten Sch\xC3\xB6nebaum"
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
|
12
|
+
date: 2009-11-11 00:00:00 +01:00
|
13
|
+
default_executable:
|
14
|
+
dependencies:
|
15
|
+
- !ruby/object:Gem::Dependency
|
16
|
+
name: ruote
|
17
|
+
type: :runtime
|
18
|
+
version_requirement:
|
19
|
+
version_requirements: !ruby/object:Gem::Requirement
|
20
|
+
requirements:
|
21
|
+
- - ">="
|
22
|
+
- !ruby/object:Gem::Version
|
23
|
+
version: 2.0.0
|
24
|
+
version:
|
25
|
+
- !ruby/object:Gem::Dependency
|
26
|
+
name: activeresource
|
27
|
+
type: :runtime
|
28
|
+
version_requirement:
|
29
|
+
version_requirements: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - ">="
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: 2.0.0
|
34
|
+
version:
|
35
|
+
description: A ruote participant implementation using ActiveResource to notify RESTful interfaces about workitems.
|
36
|
+
email: torsten.schoenebaum@planquadrat-software.de
|
37
|
+
executables: []
|
38
|
+
|
39
|
+
extensions: []
|
40
|
+
|
41
|
+
extra_rdoc_files:
|
42
|
+
- LICENSE.txt
|
43
|
+
- README.rdoc
|
44
|
+
files:
|
45
|
+
- .gitignore
|
46
|
+
- CREDITS.txt
|
47
|
+
- LICENSE.txt
|
48
|
+
- README.rdoc
|
49
|
+
- Rakefile
|
50
|
+
- VERSION
|
51
|
+
- lib/ruote/active_resource/part/active_resource_participant.rb
|
52
|
+
- lib/work/wfidgen.last
|
53
|
+
- test/path_helper.rb
|
54
|
+
- test/test.rb
|
55
|
+
- test/test_helper.rb
|
56
|
+
- test/ut_1_participant.rb
|
57
|
+
has_rdoc: true
|
58
|
+
homepage: http://github.com/tosch/ruote-activeresource
|
59
|
+
licenses: []
|
60
|
+
|
61
|
+
post_install_message:
|
62
|
+
rdoc_options:
|
63
|
+
- --charset=UTF-8
|
64
|
+
require_paths:
|
65
|
+
- lib
|
66
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
67
|
+
requirements:
|
68
|
+
- - ">="
|
69
|
+
- !ruby/object:Gem::Version
|
70
|
+
version: "0"
|
71
|
+
version:
|
72
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
73
|
+
requirements:
|
74
|
+
- - ">="
|
75
|
+
- !ruby/object:Gem::Version
|
76
|
+
version: "0"
|
77
|
+
version:
|
78
|
+
requirements: []
|
79
|
+
|
80
|
+
rubyforge_project:
|
81
|
+
rubygems_version: 1.3.5
|
82
|
+
signing_key:
|
83
|
+
specification_version: 3
|
84
|
+
summary: Ruote participant using ActiveResource
|
85
|
+
test_files:
|
86
|
+
- test/test_helper.rb
|
87
|
+
- test/test.rb
|
88
|
+
- test/path_helper.rb
|
89
|
+
- test/ut_1_participant.rb
|