qrpc 0.4.0 → 0.9.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (44) hide show
  1. data/CHANGES.txt +9 -6
  2. data/Gemfile +10 -4
  3. data/Gemfile.lock +34 -12
  4. data/LICENSE.txt +1 -1
  5. data/README.md +92 -25
  6. data/Rakefile +2 -1
  7. data/TODO.md +1 -3
  8. data/VERSION +1 -1
  9. data/lib/qrpc/client.rb +13 -5
  10. data/lib/qrpc/client/dispatcher.rb +66 -50
  11. data/lib/qrpc/client/exception.rb +8 -37
  12. data/lib/qrpc/client/job.rb +49 -16
  13. data/lib/qrpc/general.rb +61 -1
  14. data/lib/qrpc/generator/object-id.rb +43 -0
  15. data/lib/qrpc/generator/uuid.rb +43 -0
  16. data/lib/qrpc/locator.rb +11 -85
  17. data/lib/qrpc/locator/em-jack.rb +160 -0
  18. data/lib/qrpc/locator/evented-queue.rb +101 -0
  19. data/lib/qrpc/protocol/abstract.rb +119 -0
  20. data/lib/qrpc/protocol/abstract/error.rb +54 -0
  21. data/lib/qrpc/protocol/abstract/object.rb +81 -0
  22. data/lib/qrpc/protocol/abstract/request.rb +126 -0
  23. data/lib/qrpc/protocol/abstract/response.rb +103 -0
  24. data/lib/qrpc/protocol/json-rpc.rb +32 -0
  25. data/lib/qrpc/protocol/json-rpc/error.rb +71 -0
  26. data/lib/qrpc/protocol/json-rpc/native/exception-data.rb +247 -0
  27. data/lib/qrpc/protocol/json-rpc/native/qrpc-object.rb +137 -0
  28. data/lib/qrpc/protocol/json-rpc/request.rb +140 -0
  29. data/lib/qrpc/protocol/json-rpc/response.rb +146 -0
  30. data/lib/qrpc/protocol/object.rb +32 -0
  31. data/lib/qrpc/protocol/object/error.rb +46 -0
  32. data/lib/qrpc/protocol/object/request.rb +111 -0
  33. data/lib/qrpc/protocol/object/response.rb +93 -0
  34. data/lib/qrpc/server.rb +63 -48
  35. data/lib/qrpc/server/dispatcher.rb +5 -107
  36. data/lib/qrpc/server/job.rb +69 -19
  37. data/qrpc.gemspec +55 -19
  38. data/test-both.rb +85 -0
  39. data/test-client.rb +36 -8
  40. data/test-server.rb +17 -12
  41. metadata +181 -31
  42. data/lib/qrpc/protocol/exception-data.rb +0 -227
  43. data/lib/qrpc/protocol/qrpc-object.rb +0 -103
  44. data/lib/qrpc/protocol/request.rb +0 -46
@@ -0,0 +1,126 @@
1
+ # encoding: utf-8
2
+ # (c) 2011 Martin Kozák (martinkozak@martinkozak.net)
3
+
4
+ require "abstract"
5
+ require "qrpc/general"
6
+ require "qrpc/protocol/abstract/object"
7
+
8
+ ##
9
+ # General QRPC module.
10
+ #
11
+
12
+ module QRPC
13
+
14
+ ##
15
+ # Protocols helper module.
16
+ # @since 0.9.0
17
+ #
18
+
19
+ module Protocol
20
+
21
+ ##
22
+ # Abstract protocol implementation.
23
+ # @since 0.9.0
24
+ #
25
+
26
+ class Abstract
27
+
28
+ ##
29
+ # Abstract request implementation.
30
+ #
31
+ # @since 0.9.0
32
+ # @abstract
33
+ #
34
+
35
+ class Request < Object
36
+
37
+ ##
38
+ # Constructor.
39
+ #
40
+ # @param [Hash] init initial options
41
+ # @abstract
42
+ #
43
+
44
+ def initialize(init = { })
45
+ super(init)
46
+ if self.instance_of? Request
47
+ not_implemented
48
+ end
49
+ end
50
+
51
+ ##
52
+ # Parses the data for new object.
53
+ #
54
+ # @param [String] raw raw data
55
+ # @return [Request] new request according to data
56
+ # @abstract
57
+ #
58
+
59
+ def self.parse(raw)
60
+ not_implemented
61
+ end
62
+
63
+ ##
64
+ # Returns ID of the request.
65
+ #
66
+ # @return [Object] request ID
67
+ # @abstract
68
+ #
69
+
70
+ def id
71
+ not_implemented
72
+ end
73
+
74
+ ##
75
+ # Returns method identifier of the request.
76
+ #
77
+ # @return Symbol
78
+ # @abstract
79
+ #
80
+
81
+ def method
82
+ not_implemented
83
+ end
84
+
85
+ ##
86
+ # Returns method params of the request.
87
+ #
88
+ # @return Array
89
+ # @abstract
90
+ #
91
+
92
+ def params
93
+ not_implemented
94
+ end
95
+
96
+ ##
97
+ # Returns the QRPC request priority.
98
+ # @return Integer
99
+ #
100
+
101
+ def priority
102
+ not_implemented
103
+ end
104
+
105
+ ##
106
+ # Returns the QRPC request client identifier.
107
+ # @return Object
108
+ #
109
+
110
+ def client
111
+ not_implemented
112
+ end
113
+
114
+ ##
115
+ # Indicates, job is notification.
116
+ # @return Boolean
117
+ #
118
+
119
+ def notification?
120
+ not_implemented
121
+ end
122
+
123
+ end
124
+ end
125
+ end
126
+ end
@@ -0,0 +1,103 @@
1
+ # encoding: utf-8
2
+ # (c) 2011 Martin Kozák (martinkozak@martinkozak.net)
3
+
4
+ require "abstract"
5
+ require "qrpc/general"
6
+ require "qrpc/protocol/abstract/object"
7
+
8
+ ##
9
+ # General QRPC module.
10
+ #
11
+
12
+ module QRPC
13
+
14
+ ##
15
+ # Protocols helper module.
16
+ # @since 0.9.0
17
+ #
18
+
19
+ module Protocol
20
+
21
+ ##
22
+ # Abstract protocol implementation.
23
+ # @since 0.9.0
24
+ #
25
+
26
+ class Abstract
27
+
28
+ ##
29
+ # Abstract response implementation.
30
+ #
31
+ # @since 0.9.0
32
+ # @abstract
33
+ #
34
+
35
+ class Response < Object
36
+
37
+ ##
38
+ # Constructor.
39
+ #
40
+ # @param [Hash] init initial options
41
+ # @abstract
42
+ #
43
+
44
+ def initialize(init = { })
45
+ super(init)
46
+ if self.instance_of? Response
47
+ not_implemented
48
+ end
49
+ end
50
+
51
+ ##
52
+ # Parses the data for new object.
53
+ #
54
+ # @param [String] raw raw data
55
+ # @return [Response] new response according to data
56
+ # @abstract
57
+ #
58
+
59
+ def self.parse(raw)
60
+ not_implemented
61
+ end
62
+
63
+ ##
64
+ # Returns ID of the request.
65
+ # @return [Object] request ID
66
+ #
67
+
68
+ def id
69
+ not_implemented
70
+ end
71
+
72
+
73
+ ##
74
+ # Returns response error.
75
+ # @return [Exception] error object
76
+ #
77
+
78
+ def error
79
+ not_implemented
80
+ end
81
+
82
+ ##
83
+ # Indicates, error state of the response.
84
+ # @return [Boolean] error indication
85
+ #
86
+
87
+ def error?
88
+ not_implemented
89
+ end
90
+
91
+ ##
92
+ # Returns response result.
93
+ # @return [Object] response result
94
+ #
95
+
96
+ def result
97
+ not_implemented
98
+ end
99
+
100
+ end
101
+ end
102
+ end
103
+ end
@@ -0,0 +1,32 @@
1
+ # encoding: utf-8
2
+ # (c) 2011 Martin Kozák (martinkozak@martinkozak.net)
3
+
4
+ require "qrpc/protocol/abstract"
5
+
6
+ ##
7
+ # General QRPC module.
8
+ #
9
+
10
+ module QRPC
11
+
12
+ ##
13
+ # Protocols helper module.
14
+ # @since 0.9.0
15
+ #
16
+
17
+ module Protocol
18
+
19
+ ##
20
+ # JSON-RPC protocol implementation.
21
+ # @since 0.9.0
22
+ #
23
+
24
+ class JsonRpc < Abstract
25
+ end
26
+
27
+ end
28
+ end
29
+
30
+ require "qrpc/protocol/json-rpc/error"
31
+ require "qrpc/protocol/json-rpc/request"
32
+ require "qrpc/protocol/json-rpc/response"
@@ -0,0 +1,71 @@
1
+ # encoding: utf-8
2
+ # (c) 2011 Martin Kozák (martinkozak@martinkozak.net)
3
+
4
+ require "qrpc/general"
5
+ require "qrpc/protocol/abstract/error"
6
+ require "qrpc/protocol/json-rpc/native/exception-data"
7
+
8
+ ##
9
+ # General QRPC module.
10
+ #
11
+
12
+ module QRPC
13
+
14
+ ##
15
+ # Protocols helper module.
16
+ # @since 0.9.0
17
+ #
18
+
19
+ module Protocol
20
+
21
+ ##
22
+ # JSON-RPC protocol implementation.
23
+ # @since 0.9.0
24
+ #
25
+
26
+ class JsonRpc
27
+
28
+ ##
29
+ # JSON-RPC error implementation.
30
+ # @since 0.9.0
31
+ #
32
+
33
+ class Error < QRPC::Protocol::Abstract::Error
34
+
35
+ ##
36
+ # Holds native object.
37
+ #
38
+
39
+ @native
40
+
41
+ ##
42
+ # Returns the native object.
43
+ # @return [JsonRpcObjects::Generic::Error] native response object
44
+ #
45
+
46
+ def native
47
+ if @native.nil?
48
+ exception = @options.exception
49
+ request = @options.request
50
+ data = QRPC::Protocol::JsonRpc::Native::ExceptionData::create(exception)
51
+
52
+ @native = request.native.class::version.error::create(100, "exception raised during processing the request", :error => data.output)
53
+ @native.serializer = @options.serializer
54
+ end
55
+
56
+ @native
57
+ end
58
+
59
+ ##
60
+ # Serializes object to the resultant form.
61
+ # @return [String] serialized form
62
+ #
63
+
64
+ def serialize
65
+ self.native.serialize
66
+ end
67
+
68
+ end
69
+ end
70
+ end
71
+ end
@@ -0,0 +1,247 @@
1
+ # encoding: utf-8
2
+ # (c) 2011 Martin Kozák (martinkozak@martinkozak.net)
3
+
4
+ require "qrpc/protocol/json-rpc/native/qrpc-object"
5
+ require "json-rpc-objects/generic/object"
6
+ require "qrpc/protocol/json-rpc"
7
+ require "qrpc/general"
8
+ require "base64"
9
+
10
+ ##
11
+ # General QRPC module.
12
+ #
13
+
14
+ module QRPC
15
+
16
+ ##
17
+ # JSON RPC helper module.
18
+ # @since 0.2.0
19
+ #
20
+
21
+ module Protocol
22
+
23
+ ##
24
+ # JSON-RPC protocol implementation.
25
+ # @since 0.9.0
26
+ #
27
+
28
+ class JsonRpc
29
+
30
+ ##
31
+ # Native JSON-RPC classes.
32
+ # @since 0.9.0
33
+ #
34
+
35
+ module Native
36
+
37
+ ##
38
+ # Exception data QRPC JSON-RPC object.
39
+ # @since 0.2.0
40
+ #
41
+
42
+ class ExceptionData < JsonRpcObjects::Generic::Object
43
+
44
+ ##
45
+ # Holds JSON-RPC version indication.
46
+ #
47
+
48
+ VERSION = QRPC::Protocol::JsonRpc::Native::QrpcObject::VERSION
49
+
50
+ ##
51
+ # Holds exception name.
52
+ # @return [Symbol]
53
+ #
54
+
55
+ attr_accessor :name
56
+ @name
57
+
58
+ ##
59
+ # Holds exception message.
60
+ # @return [String]
61
+ #
62
+
63
+ attr_accessor :message
64
+ @message
65
+
66
+ ##
67
+ # Holds backtrace. See readme for structure details.
68
+ # @return [Array]
69
+ #
70
+
71
+ attr_accessor :backtrace
72
+ @backtrace
73
+
74
+ ##
75
+ # Holds native dump. See readme for structure details.
76
+ # @return [Class]
77
+ #
78
+
79
+ attr_accessor :dump
80
+ @dump
81
+
82
+ ##
83
+ # Indicates, data are encoded and should be decoded.
84
+ #
85
+
86
+ @__encoded
87
+
88
+ ##
89
+ # Creates new QRPC JSON-RPC object.
90
+ #
91
+ # @overload create(exception, nil, opts = { })
92
+ # Creates from exception.
93
+ # @param [Exception] exception exception object
94
+ # @param [NilClass] nil (not applicable)
95
+ # @param [Hash] opts optional members of object
96
+ # @overload create(name, message, opts = { })
97
+ # Creates from exception description.
98
+ # @param [Symbol, String] name exception name
99
+ # @param [Object] exception message
100
+ # @param [Hash] opts optional members of object
101
+ # @return [QRPC::Protocol::ExceptionData] new instance
102
+ #
103
+
104
+ def self.create(arg1, message = nil, opts = { })
105
+ if arg1.kind_of? ::Exception
106
+ mode = :decoded
107
+ data = {
108
+ :name => arg1.class.name,
109
+ :message => arg1.message,
110
+ :backtrace => arg1.backtrace,
111
+ :dump => {
112
+ "format" => "ruby",
113
+ "object" => arg1
114
+ }
115
+ }
116
+ else
117
+ mode = :encoded
118
+ data = {
119
+ :name => arg1,
120
+ :message => message
121
+ }
122
+ end
123
+
124
+ data.merge! opts
125
+ return self::new(data, mode)
126
+ end
127
+
128
+ ##
129
+ # Constructor.
130
+ # @param [Hash] data for initializing the object
131
+ #
132
+
133
+ def initialize(data, mode = :encoded)
134
+ @__encoded = (mode == :encoded)
135
+ super(data)
136
+ end
137
+
138
+ ##
139
+ # Checks correctness of the object data.
140
+ #
141
+
142
+ def check!
143
+ self.normalize!
144
+
145
+ if not @name.kind_of? Symbol
146
+ raise Exception::new("Exception name is expected to be Symbol or convertable to symbol.")
147
+ end
148
+
149
+ if not @backtrace.nil? and not @backtrace.kind_of? Array
150
+ raise Exception::new("Backtrace is expected to be an Array.")
151
+ end
152
+
153
+ if not @dump.nil?
154
+ if @dump.object.nil? and @dump.raw.nil?
155
+ raise Exception::new("Either object or RAW form of the dump must be set if dump is set.")
156
+ elsif @dump.format.nil? or not @dump.format.kind_of? Symbol
157
+ raise Exception::new("Dump format must be set and must be Symbol.")
158
+ end
159
+ end
160
+ end
161
+
162
+ ##
163
+ # Renders data to output form.
164
+ # @return [Hash] with data of object
165
+ #
166
+
167
+ def output
168
+ result = {
169
+ "name" => @name.to_s,
170
+ "message" => @message,
171
+ }
172
+
173
+ # Backtrace
174
+ if @backtrace.kind_of? Array
175
+ result["backtrace"] = @backtrace.map { |i| Base64.encode64(i) }
176
+ end
177
+
178
+ # Dump
179
+ if not @dump.nil?
180
+ result["dump"] = {
181
+ "format" => @dump.format,
182
+ }
183
+
184
+ if not dump.object.nil?
185
+ raw = Base64.encode64(Marshal.dump(dump.object))
186
+ else
187
+ raw = dump.raw
188
+ end
189
+
190
+ result["dump"]["raw"] = raw
191
+ end
192
+
193
+ return result
194
+ end
195
+
196
+
197
+ protected
198
+
199
+ ##
200
+ # Assigns data.
201
+ #
202
+
203
+ def data=(value, mode = nil)
204
+ data = __convert_data(value, mode)
205
+
206
+ # Required
207
+ @name = data[:name]
208
+ @message = data[:message]
209
+
210
+ # Backtrace
211
+ backtrace = data[:backtrace]
212
+
213
+ if @__encoded and (backtrace.kind_of? Array)
214
+ @backtrace = backtrace.map { |i| Base64.decode64(i) }
215
+ end
216
+
217
+ # Dump
218
+ dump = data[:dump]
219
+
220
+ if dump.kind_of? Hash
221
+ @dump = Struct::new(:format, :raw, :object)::new(dump["format"].downcase.to_sym, dump["raw"], dump["object"])
222
+
223
+ if not @dump.raw.nil? and @dump.object.nil? and (@dump.format == :ruby)
224
+ @dump.object = Marshal.load(Base64.decode64(@dump.raw))
225
+ end
226
+ end
227
+
228
+ end
229
+
230
+ ##
231
+ # Converts data to standard (defined) format.
232
+ #
233
+
234
+ def normalize!
235
+ @name = @name.to_sym
236
+
237
+ if not @dump.nil?
238
+ @dump.format = @dump.format.to_sym
239
+ end
240
+ end
241
+
242
+ end
243
+
244
+ end
245
+ end
246
+ end
247
+ end