thrift 0.9.0 → 0.9.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +15 -0
- data/ext/binary_protocol_accelerated.c +19 -3
- data/ext/compact_protocol.c +21 -7
- data/ext/constants.h +1 -5
- data/ext/extconf.rb +1 -1
- data/ext/protocol.c +0 -185
- data/ext/protocol.h +0 -20
- data/ext/struct.c +0 -3
- data/ext/thrift_native.c +1 -11
- data/lib/thrift.rb +1 -0
- data/lib/thrift/exceptions.rb +3 -0
- data/lib/thrift/protocol/base_protocol.rb +87 -10
- data/lib/thrift/protocol/binary_protocol.rb +13 -5
- data/lib/thrift/protocol/compact_protocol.rb +14 -7
- data/lib/thrift/protocol/json_protocol.rb +19 -15
- data/lib/thrift/server/mongrel_http_server.rb +2 -0
- data/lib/thrift/server/thin_http_server.rb +91 -0
- data/lib/thrift/struct.rb +1 -1
- data/lib/thrift/struct_union.rb +2 -2
- data/lib/thrift/transport/http_client_transport.rb +4 -1
- data/spec/base_protocol_spec.rb +65 -7
- data/spec/binary_protocol_spec_shared.rb +30 -0
- data/spec/compact_protocol_spec.rb +1 -3
- data/spec/http_client_spec.rb +49 -0
- data/spec/json_protocol_spec.rb +2 -2
- data/spec/thin_http_server_spec.rb +140 -0
- data/spec/union_spec.rb +13 -1
- metadata +113 -93
- data/benchmark/gen-rb/benchmark_constants.rb +0 -11
- data/benchmark/gen-rb/benchmark_service.rb +0 -80
- data/benchmark/gen-rb/benchmark_types.rb +0 -10
- data/spec/gen-rb/nonblocking_service.rb +0 -272
- data/spec/gen-rb/thrift_spec_constants.rb +0 -11
- data/spec/gen-rb/thrift_spec_types.rb +0 -538
- data/spec/mongrel_http_server_spec.rb +0 -114
- data/test/debug_proto/gen-rb/debug_proto_test_constants.rb +0 -274
- data/test/debug_proto/gen-rb/debug_proto_test_types.rb +0 -761
- data/test/debug_proto/gen-rb/empty_service.rb +0 -24
- data/test/debug_proto/gen-rb/inherited.rb +0 -79
- data/test/debug_proto/gen-rb/reverse_order_service.rb +0 -82
- data/test/debug_proto/gen-rb/service_for_exception_with_a_map.rb +0 -81
- data/test/debug_proto/gen-rb/srv.rb +0 -330
data/lib/thrift.rb
CHANGED
data/lib/thrift/exceptions.rb
CHANGED
@@ -125,6 +125,16 @@ module Thrift
|
|
125
125
|
raise NotImplementedError
|
126
126
|
end
|
127
127
|
|
128
|
+
# Writes a Thrift Binary (Thrift String with no encoding). In Ruby 1.9+, the String passed
|
129
|
+
# will forced into BINARY encoding.
|
130
|
+
#
|
131
|
+
# buf - The String to write.
|
132
|
+
#
|
133
|
+
# Returns nothing.
|
134
|
+
def write_binary(buf)
|
135
|
+
raise NotImplementedError
|
136
|
+
end
|
137
|
+
|
128
138
|
def read_message_begin
|
129
139
|
raise NotImplementedError
|
130
140
|
end
|
@@ -185,21 +195,67 @@ module Thrift
|
|
185
195
|
raise NotImplementedError
|
186
196
|
end
|
187
197
|
|
188
|
-
# Reads a Thrift String. In Ruby 1.9+, all
|
198
|
+
# Reads a Thrift String. In Ruby 1.9+, all Strings will be returned with an Encoding of UTF-8.
|
189
199
|
#
|
190
200
|
# Returns a String.
|
191
201
|
def read_string
|
192
202
|
raise NotImplementedError
|
193
203
|
end
|
194
204
|
|
195
|
-
|
196
|
-
|
197
|
-
|
205
|
+
# Reads a Thrift Binary (Thrift String without encoding). In Ruby 1.9+, all Strings will be returned
|
206
|
+
# with an Encoding of BINARY.
|
207
|
+
#
|
208
|
+
# Returns a String.
|
209
|
+
def read_binary
|
210
|
+
raise NotImplementedError
|
211
|
+
end
|
212
|
+
|
213
|
+
# Writes a field based on the field information, field ID and value.
|
214
|
+
#
|
215
|
+
# field_info - A Hash containing the definition of the field:
|
216
|
+
# :name - The name of the field.
|
217
|
+
# :type - The type of the field, which must be a Thrift::Types constant.
|
218
|
+
# :binary - A Boolean flag that indicates if Thrift::Types::STRING is a binary string (string without encoding).
|
219
|
+
# fid - The ID of the field.
|
220
|
+
# value - The field's value to write; object type varies based on :type.
|
221
|
+
#
|
222
|
+
# Returns nothing.
|
223
|
+
def write_field(*args)
|
224
|
+
if args.size == 3
|
225
|
+
# handles the documented method signature - write_field(field_info, fid, value)
|
226
|
+
field_info = args[0]
|
227
|
+
fid = args[1]
|
228
|
+
value = args[2]
|
229
|
+
elsif args.size == 4
|
230
|
+
# handles the deprecated method signature - write_field(name, type, fid, value)
|
231
|
+
field_info = {:name => args[0], :type => args[1]}
|
232
|
+
fid = args[2]
|
233
|
+
value = args[3]
|
234
|
+
else
|
235
|
+
raise ArgumentError, "wrong number of arguments (#{args.size} for 3)"
|
236
|
+
end
|
237
|
+
|
238
|
+
write_field_begin(field_info[:name], field_info[:type], fid)
|
239
|
+
write_type(field_info, value)
|
198
240
|
write_field_end
|
199
241
|
end
|
200
242
|
|
201
|
-
|
202
|
-
|
243
|
+
# Writes a field value based on the field information.
|
244
|
+
#
|
245
|
+
# field_info - A Hash containing the definition of the field:
|
246
|
+
# :type - The Thrift::Types constant that determines how the value is written.
|
247
|
+
# :binary - A Boolean flag that indicates if Thrift::Types::STRING is a binary string (string without encoding).
|
248
|
+
# value - The field's value to write; object type varies based on field_info[:type].
|
249
|
+
#
|
250
|
+
# Returns nothing.
|
251
|
+
def write_type(field_info, value)
|
252
|
+
# if field_info is a Fixnum, assume it is a Thrift::Types constant
|
253
|
+
# convert it into a field_info Hash for backwards compatibility
|
254
|
+
if field_info.is_a? Fixnum
|
255
|
+
field_info = {:type => field_info}
|
256
|
+
end
|
257
|
+
|
258
|
+
case field_info[:type]
|
203
259
|
when Types::BOOL
|
204
260
|
write_bool(value)
|
205
261
|
when Types::BYTE
|
@@ -213,7 +269,11 @@ module Thrift
|
|
213
269
|
when Types::I64
|
214
270
|
write_i64(value)
|
215
271
|
when Types::STRING
|
216
|
-
|
272
|
+
if field_info[:binary]
|
273
|
+
write_binary(value)
|
274
|
+
else
|
275
|
+
write_string(value)
|
276
|
+
end
|
217
277
|
when Types::STRUCT
|
218
278
|
value.write(self)
|
219
279
|
else
|
@@ -221,8 +281,21 @@ module Thrift
|
|
221
281
|
end
|
222
282
|
end
|
223
283
|
|
224
|
-
|
225
|
-
|
284
|
+
# Reads a field value based on the field information.
|
285
|
+
#
|
286
|
+
# field_info - A Hash containing the pertinent data to write:
|
287
|
+
# :type - The Thrift::Types constant that determines how the value is written.
|
288
|
+
# :binary - A flag that indicates if Thrift::Types::STRING is a binary string (string without encoding).
|
289
|
+
#
|
290
|
+
# Returns the value read; object type varies based on field_info[:type].
|
291
|
+
def read_type(field_info)
|
292
|
+
# if field_info is a Fixnum, assume it is a Thrift::Types constant
|
293
|
+
# convert it into a field_info Hash for backwards compatibility
|
294
|
+
if field_info.is_a? Fixnum
|
295
|
+
field_info = {:type => field_info}
|
296
|
+
end
|
297
|
+
|
298
|
+
case field_info[:type]
|
226
299
|
when Types::BOOL
|
227
300
|
read_bool
|
228
301
|
when Types::BYTE
|
@@ -236,7 +309,11 @@ module Thrift
|
|
236
309
|
when Types::I64
|
237
310
|
read_i64
|
238
311
|
when Types::STRING
|
239
|
-
|
312
|
+
if field_info[:binary]
|
313
|
+
read_binary
|
314
|
+
else
|
315
|
+
read_string
|
316
|
+
end
|
240
317
|
else
|
241
318
|
raise NotImplementedError
|
242
319
|
end
|
@@ -107,9 +107,13 @@ module Thrift
|
|
107
107
|
end
|
108
108
|
|
109
109
|
def write_string(str)
|
110
|
-
|
111
|
-
|
112
|
-
|
110
|
+
buf = Bytes.convert_to_utf8_byte_buffer(str)
|
111
|
+
write_binary(buf)
|
112
|
+
end
|
113
|
+
|
114
|
+
def write_binary(buf)
|
115
|
+
write_i32(buf.bytesize)
|
116
|
+
trans.write(buf)
|
113
117
|
end
|
114
118
|
|
115
119
|
def read_message_begin
|
@@ -214,11 +218,15 @@ module Thrift
|
|
214
218
|
end
|
215
219
|
|
216
220
|
def read_string
|
217
|
-
|
218
|
-
buffer = trans.read_all(size)
|
221
|
+
buffer = read_binary
|
219
222
|
Bytes.convert_to_string(buffer)
|
220
223
|
end
|
221
224
|
|
225
|
+
def read_binary
|
226
|
+
size = read_i32
|
227
|
+
trans.read_all(size)
|
228
|
+
end
|
229
|
+
|
222
230
|
end
|
223
231
|
|
224
232
|
class BinaryProtocolFactory < BaseProtocolFactory
|
@@ -210,9 +210,13 @@ module Thrift
|
|
210
210
|
end
|
211
211
|
|
212
212
|
def write_string(str)
|
213
|
-
|
214
|
-
|
215
|
-
|
213
|
+
buf = Bytes.convert_to_utf8_byte_buffer(str)
|
214
|
+
write_binary(buf)
|
215
|
+
end
|
216
|
+
|
217
|
+
def write_binary(buf)
|
218
|
+
write_varint32(buf.bytesize)
|
219
|
+
@trans.write(buf)
|
216
220
|
end
|
217
221
|
|
218
222
|
def read_message_begin
|
@@ -332,12 +336,15 @@ module Thrift
|
|
332
336
|
end
|
333
337
|
|
334
338
|
def read_string
|
335
|
-
|
336
|
-
buffer = trans.read_all(size)
|
339
|
+
buffer = read_binary
|
337
340
|
Bytes.convert_to_string(buffer)
|
338
341
|
end
|
339
|
-
|
340
|
-
|
342
|
+
|
343
|
+
def read_binary
|
344
|
+
size = read_varint32()
|
345
|
+
trans.read_all(size)
|
346
|
+
end
|
347
|
+
|
341
348
|
private
|
342
349
|
|
343
350
|
#
|
@@ -18,21 +18,6 @@
|
|
18
18
|
# under the License.
|
19
19
|
#
|
20
20
|
|
21
|
-
@@kJSONObjectStart = '{'
|
22
|
-
@@kJSONObjectEnd = '}'
|
23
|
-
@@kJSONArrayStart = '['
|
24
|
-
@@kJSONArrayEnd = ']'
|
25
|
-
@@kJSONNewline = '\n'
|
26
|
-
@@kJSONElemSeparator = ','
|
27
|
-
@@kJSONPairSeparator = ':'
|
28
|
-
@@kJSONBackslash = '\\'
|
29
|
-
@@kJSONStringDelimiter = '"'
|
30
|
-
|
31
|
-
@@kThriftVersion1 = 1
|
32
|
-
|
33
|
-
@@kThriftNan = "NaN"
|
34
|
-
@@kThriftInfinity = "Infinity"
|
35
|
-
@@kThriftNegativeInfinity = "-Infinity"
|
36
21
|
|
37
22
|
module Thrift
|
38
23
|
class LookaheadReader
|
@@ -66,6 +51,7 @@ module Thrift
|
|
66
51
|
# implementations
|
67
52
|
#
|
68
53
|
class JSONContext
|
54
|
+
@@kJSONElemSeparator = ','
|
69
55
|
#
|
70
56
|
# Write context data to the trans. Default is to do nothing.
|
71
57
|
#
|
@@ -89,6 +75,8 @@ module Thrift
|
|
89
75
|
|
90
76
|
# Context class for object member key-value pairs
|
91
77
|
class JSONPairContext < JSONContext
|
78
|
+
@@kJSONPairSeparator = ':'
|
79
|
+
|
92
80
|
def initialize
|
93
81
|
@first = true
|
94
82
|
@colon = true
|
@@ -146,6 +134,21 @@ module Thrift
|
|
146
134
|
end
|
147
135
|
|
148
136
|
class JsonProtocol < BaseProtocol
|
137
|
+
|
138
|
+
@@kJSONObjectStart = '{'
|
139
|
+
@@kJSONObjectEnd = '}'
|
140
|
+
@@kJSONArrayStart = '['
|
141
|
+
@@kJSONArrayEnd = ']'
|
142
|
+
@@kJSONNewline = '\n'
|
143
|
+
@@kJSONBackslash = '\\'
|
144
|
+
@@kJSONStringDelimiter = '"'
|
145
|
+
|
146
|
+
@@kThriftVersion1 = 1
|
147
|
+
|
148
|
+
@@kThriftNan = "NaN"
|
149
|
+
@@kThriftInfinity = "Infinity"
|
150
|
+
@@kThriftNegativeInfinity = "-Infinity"
|
151
|
+
|
149
152
|
def initialize(trans)
|
150
153
|
super(trans)
|
151
154
|
@context = JSONContext.new
|
@@ -717,6 +720,7 @@ module Thrift
|
|
717
720
|
|
718
721
|
def read_set_begin
|
719
722
|
read_json_array_start
|
723
|
+
[get_type_id_for_type_name(read_json_string), read_json_integer]
|
720
724
|
end
|
721
725
|
|
722
726
|
def read_set_end
|
@@ -20,6 +20,7 @@
|
|
20
20
|
require 'mongrel'
|
21
21
|
|
22
22
|
## Sticks a service on a URL, using mongrel to do the HTTP work
|
23
|
+
# <b>DEPRECATED:</b> Please use <tt>Thrift::ThinHTTPServer</tt> instead.
|
23
24
|
module Thrift
|
24
25
|
class MongrelHTTPServer < BaseServer
|
25
26
|
class Handler < Mongrel::HttpHandler
|
@@ -43,6 +44,7 @@ module Thrift
|
|
43
44
|
end
|
44
45
|
|
45
46
|
def initialize(processor, opts={})
|
47
|
+
Kernel.warn "[DEPRECATION WARNING] `Thrift::MongrelHTTPServer` is deprecated. Please use `Thrift::ThinHTTPServer` instead."
|
46
48
|
port = opts[:port] || 80
|
47
49
|
ip = opts[:ip] || "0.0.0.0"
|
48
50
|
path = opts[:path] || ""
|
@@ -0,0 +1,91 @@
|
|
1
|
+
#
|
2
|
+
# Licensed to the Apache Software Foundation (ASF) under one
|
3
|
+
# or more contributor license agreements. See the NOTICE file
|
4
|
+
# distributed with this work for additional information
|
5
|
+
# regarding copyright ownership. The ASF licenses this file
|
6
|
+
# to you under the Apache License, Version 2.0 (the
|
7
|
+
# "License"); you may not use this file except in compliance
|
8
|
+
# with the License. You may obtain a copy of the License at
|
9
|
+
#
|
10
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
11
|
+
#
|
12
|
+
# Unless required by applicable law or agreed to in writing,
|
13
|
+
# software distributed under the License is distributed on an
|
14
|
+
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
15
|
+
# KIND, either express or implied. See the License for the
|
16
|
+
# specific language governing permissions and limitations
|
17
|
+
# under the License.
|
18
|
+
#
|
19
|
+
|
20
|
+
require 'rack'
|
21
|
+
require 'thin'
|
22
|
+
|
23
|
+
##
|
24
|
+
# Wraps the Thin web server to provide a Thrift server over HTTP.
|
25
|
+
module Thrift
|
26
|
+
class ThinHTTPServer < BaseServer
|
27
|
+
|
28
|
+
##
|
29
|
+
# Accepts a Thrift::Processor
|
30
|
+
# Options include:
|
31
|
+
# * :port
|
32
|
+
# * :ip
|
33
|
+
# * :path
|
34
|
+
# * :protocol_factory
|
35
|
+
def initialize(processor, options={})
|
36
|
+
port = options[:port] || 80
|
37
|
+
ip = options[:ip] || "0.0.0.0"
|
38
|
+
path = options[:path] || "/"
|
39
|
+
protocol_factory = options[:protocol_factory] || BinaryProtocolFactory.new
|
40
|
+
app = RackApplication.for(path, processor, protocol_factory)
|
41
|
+
@server = Thin::Server.new(ip, port, app)
|
42
|
+
end
|
43
|
+
|
44
|
+
##
|
45
|
+
# Starts the server
|
46
|
+
def serve
|
47
|
+
@server.start
|
48
|
+
end
|
49
|
+
|
50
|
+
class RackApplication
|
51
|
+
|
52
|
+
THRIFT_HEADER = "application/x-thrift"
|
53
|
+
|
54
|
+
def self.for(path, processor, protocol_factory)
|
55
|
+
Rack::Builder.new do
|
56
|
+
use Rack::CommonLogger
|
57
|
+
use Rack::ShowExceptions
|
58
|
+
use Rack::Lint
|
59
|
+
map path do
|
60
|
+
run lambda { |env|
|
61
|
+
request = Rack::Request.new(env)
|
62
|
+
if RackApplication.valid_thrift_request?(request)
|
63
|
+
RackApplication.successful_request(request, processor, protocol_factory)
|
64
|
+
else
|
65
|
+
RackApplication.failed_request
|
66
|
+
end
|
67
|
+
}
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
def self.successful_request(rack_request, processor, protocol_factory)
|
73
|
+
response = Rack::Response.new([], 200, {'Content-Type' => THRIFT_HEADER})
|
74
|
+
transport = IOStreamTransport.new rack_request.body, response
|
75
|
+
protocol = protocol_factory.get_protocol transport
|
76
|
+
processor.process protocol, protocol
|
77
|
+
response
|
78
|
+
end
|
79
|
+
|
80
|
+
def self.failed_request
|
81
|
+
Rack::Response.new(['Not Found'], 404, {'Content-Type' => THRIFT_HEADER})
|
82
|
+
end
|
83
|
+
|
84
|
+
def self.valid_thrift_request?(rack_request)
|
85
|
+
rack_request.post? && rack_request.env["CONTENT_TYPE"] == THRIFT_HEADER
|
86
|
+
end
|
87
|
+
|
88
|
+
end
|
89
|
+
|
90
|
+
end
|
91
|
+
end
|
data/lib/thrift/struct.rb
CHANGED
data/lib/thrift/struct_union.rb
CHANGED
@@ -101,7 +101,7 @@ module Thrift
|
|
101
101
|
end
|
102
102
|
iprot.read_set_end
|
103
103
|
else
|
104
|
-
value = iprot.read_type(field
|
104
|
+
value = iprot.read_type(field)
|
105
105
|
end
|
106
106
|
value
|
107
107
|
end
|
@@ -110,7 +110,7 @@ module Thrift
|
|
110
110
|
if is_container? field[:type]
|
111
111
|
write_container(oprot, value, field)
|
112
112
|
else
|
113
|
-
oprot.write_type(field
|
113
|
+
oprot.write_type(field, value)
|
114
114
|
end
|
115
115
|
end
|
116
116
|
|
@@ -20,16 +20,18 @@
|
|
20
20
|
|
21
21
|
require 'net/http'
|
22
22
|
require 'net/https'
|
23
|
+
require 'openssl'
|
23
24
|
require 'uri'
|
24
25
|
require 'stringio'
|
25
26
|
|
26
27
|
module Thrift
|
27
28
|
class HTTPClientTransport < BaseTransport
|
28
29
|
|
29
|
-
def initialize(url)
|
30
|
+
def initialize(url, opts = {})
|
30
31
|
@url = URI url
|
31
32
|
@headers = {'Content-Type' => 'application/x-thrift'}
|
32
33
|
@outbuf = Bytes.empty_byte_buffer
|
34
|
+
@ssl_verify_mode = opts.fetch(:ssl_verify_mode, OpenSSL::SSL::VERIFY_PEER)
|
33
35
|
end
|
34
36
|
|
35
37
|
def open?; true end
|
@@ -43,6 +45,7 @@ module Thrift
|
|
43
45
|
def flush
|
44
46
|
http = Net::HTTP.new @url.host, @url.port
|
45
47
|
http.use_ssl = @url.scheme == 'https'
|
48
|
+
http.verify_mode = @ssl_verify_mode if @url.scheme == 'https'
|
46
49
|
resp = http.post(@url.request_uri, @outbuf, @headers)
|
47
50
|
data = resp.body
|
48
51
|
data = Bytes.force_binary_encoding(data)
|