thrift 0.23.0 → 0.25.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.
- checksums.yaml +4 -4
- data/README.md +203 -40
- data/ext/binary_protocol_accelerated.c +130 -40
- data/ext/bytes.c +14 -0
- data/ext/compact_protocol.c +184 -91
- data/ext/constants.h +3 -0
- data/ext/extconf.rb +12 -4
- data/ext/macros.h +11 -0
- data/ext/memory_buffer.c +67 -12
- data/ext/struct.c +192 -71
- data/ext/thrift_native.c +7 -0
- data/lib/thrift/bytes.rb +6 -3
- data/lib/thrift/client.rb +31 -33
- data/lib/thrift/exceptions.rb +11 -8
- data/lib/thrift/multiplexed_processor.rb +17 -8
- data/lib/thrift/processor.rb +25 -3
- data/lib/thrift/protocol/base_protocol.rb +66 -31
- data/lib/thrift/protocol/binary_protocol.rb +80 -37
- data/lib/thrift/protocol/binary_protocol_accelerated.rb +7 -2
- data/lib/thrift/protocol/compact_protocol.rb +204 -88
- data/lib/thrift/protocol/header_protocol.rb +15 -3
- data/lib/thrift/protocol/json_protocol.rb +158 -109
- data/lib/thrift/protocol/multiplexed_protocol.rb +3 -3
- data/lib/thrift/protocol/protocol_decorator.rb +6 -2
- data/lib/thrift/serializer/deserializer.rb +1 -0
- data/lib/thrift/serializer/serializer.rb +7 -0
- data/lib/thrift/server/base_server.rb +11 -2
- data/lib/thrift/server/nonblocking_server.rb +69 -20
- data/lib/thrift/server/rack_application.rb +69 -0
- data/lib/thrift/server/simple_server.rb +27 -15
- data/lib/thrift/server/thin_http_server.rb +21 -44
- data/lib/thrift/server/thread_pool_server.rb +21 -17
- data/lib/thrift/server/threaded_server.rb +22 -18
- data/lib/thrift/struct.rb +34 -18
- data/lib/thrift/struct_union.rb +37 -36
- data/lib/thrift/thrift_native.rb +2 -1
- data/lib/thrift/transport/base_server_transport.rb +3 -0
- data/lib/thrift/transport/base_transport.rb +26 -4
- data/lib/thrift/transport/buffered_transport.rb +5 -4
- data/lib/thrift/transport/framed_transport.rb +33 -7
- data/lib/thrift/transport/header_transport.rb +159 -33
- data/lib/thrift/transport/http_client_transport.rb +28 -14
- data/lib/thrift/transport/io_stream_transport.rb +3 -1
- data/lib/thrift/transport/memory_buffer_transport.rb +14 -9
- data/lib/thrift/transport/server_socket.rb +10 -8
- data/lib/thrift/transport/socket.rb +85 -48
- data/lib/thrift/transport/ssl_server_socket.rb +67 -6
- data/lib/thrift/transport/ssl_socket.rb +73 -14
- data/lib/thrift/transport/unix_server_socket.rb +6 -2
- data/lib/thrift/transport/unix_socket.rb +5 -6
- data/lib/thrift/types.rb +23 -22
- data/lib/thrift/union.rb +21 -11
- data/lib/thrift/uuid.rb +9 -8
- data/lib/thrift.rb +40 -39
- metadata +7 -266
- data/benchmark/Benchmark.thrift +0 -24
- data/benchmark/benchmark.rb +0 -285
- data/benchmark/client.rb +0 -117
- data/benchmark/server.rb +0 -120
- data/benchmark/thin_server.rb +0 -45
- data/lib/thrift/server/mongrel_http_server.rb +0 -60
- data/spec/BaseService.thrift +0 -27
- data/spec/ExtendedService.thrift +0 -25
- data/spec/Referenced.thrift +0 -44
- data/spec/ThriftNamespacedSpec.thrift +0 -53
- data/spec/ThriftSpec.thrift +0 -187
- data/spec/base_protocol_spec.rb +0 -224
- data/spec/base_transport_spec.rb +0 -387
- data/spec/binary_protocol_accelerated_spec.rb +0 -46
- data/spec/binary_protocol_spec.rb +0 -72
- data/spec/binary_protocol_spec_shared.rb +0 -445
- data/spec/bytes_spec.rb +0 -99
- data/spec/client_spec.rb +0 -166
- data/spec/compact_protocol_spec.rb +0 -196
- data/spec/constants_demo_spec.rb +0 -101
- data/spec/exception_spec.rb +0 -140
- data/spec/flat_spec.rb +0 -62
- data/spec/header_protocol_spec.rb +0 -475
- data/spec/header_transport_spec.rb +0 -386
- data/spec/http_client_spec.rb +0 -159
- data/spec/json_protocol_spec.rb +0 -552
- data/spec/namespaced_spec.rb +0 -66
- data/spec/nonblocking_server_spec.rb +0 -361
- data/spec/processor_spec.rb +0 -79
- data/spec/serializer_spec.rb +0 -66
- data/spec/server_socket_spec.rb +0 -84
- data/spec/server_spec.rb +0 -186
- data/spec/socket_spec.rb +0 -67
- data/spec/socket_spec_shared.rb +0 -167
- data/spec/spec_helper.rb +0 -69
- data/spec/ssl_server_socket_spec.rb +0 -45
- data/spec/ssl_socket_spec.rb +0 -87
- data/spec/struct_nested_containers_spec.rb +0 -190
- data/spec/struct_spec.rb +0 -397
- data/spec/support/header_protocol_helper.rb +0 -54
- data/spec/thin_http_server_spec.rb +0 -126
- data/spec/types_spec.rb +0 -117
- data/spec/union_spec.rb +0 -272
- data/spec/unix_socket_spec.rb +0 -115
- data/spec/uuid_validation_spec.rb +0 -238
- data/test/fuzz/Makefile.am +0 -173
- data/test/fuzz/README.md +0 -149
- data/test/fuzz/fuzz_common.rb +0 -95
- data/test/fuzz/fuzz_parse_binary_protocol.rb +0 -22
- data/test/fuzz/fuzz_parse_binary_protocol_accelerated.rb +0 -22
- data/test/fuzz/fuzz_parse_binary_protocol_accelerated_harness.rb +0 -22
- data/test/fuzz/fuzz_parse_binary_protocol_harness.rb +0 -22
- data/test/fuzz/fuzz_parse_compact_protocol.rb +0 -22
- data/test/fuzz/fuzz_parse_compact_protocol_harness.rb +0 -22
- data/test/fuzz/fuzz_parse_json_protocol.rb +0 -22
- data/test/fuzz/fuzz_parse_json_protocol_harness.rb +0 -22
- data/test/fuzz/fuzz_roundtrip_binary_protocol.rb +0 -22
- data/test/fuzz/fuzz_roundtrip_binary_protocol_accelerated.rb +0 -22
- data/test/fuzz/fuzz_roundtrip_binary_protocol_accelerated_harness.rb +0 -22
- data/test/fuzz/fuzz_roundtrip_binary_protocol_harness.rb +0 -22
- data/test/fuzz/fuzz_roundtrip_compact_protocol.rb +0 -22
- data/test/fuzz/fuzz_roundtrip_compact_protocol_harness.rb +0 -22
- data/test/fuzz/fuzz_roundtrip_json_protocol.rb +0 -22
- data/test/fuzz/fuzz_roundtrip_json_protocol_harness.rb +0 -22
- data/test/fuzz/fuzz_tracer.rb +0 -28
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
1
2
|
#
|
|
2
3
|
# Licensed to the Apache Software Foundation (ASF) under one
|
|
3
4
|
# or more contributor license agreements. See the NOTICE file
|
|
@@ -17,13 +18,21 @@
|
|
|
17
18
|
# under the License.
|
|
18
19
|
#
|
|
19
20
|
|
|
21
|
+
require "logger"
|
|
22
|
+
|
|
20
23
|
module Thrift
|
|
21
24
|
class BaseServer
|
|
22
|
-
def initialize(processor, server_transport, transport_factory = nil, protocol_factory = nil)
|
|
25
|
+
def initialize(processor, server_transport, transport_factory = nil, protocol_factory = nil, logger: nil)
|
|
23
26
|
@processor = processor
|
|
24
27
|
@server_transport = server_transport
|
|
25
28
|
@transport_factory = transport_factory ? transport_factory : Thrift::BaseTransportFactory.new
|
|
26
29
|
@protocol_factory = protocol_factory ? protocol_factory : Thrift::BinaryProtocolFactory.new
|
|
30
|
+
if logger.nil?
|
|
31
|
+
@logger = Logger.new(STDERR)
|
|
32
|
+
@logger.level = Logger::WARN
|
|
33
|
+
else
|
|
34
|
+
@logger = logger
|
|
35
|
+
end
|
|
27
36
|
end
|
|
28
37
|
|
|
29
38
|
def serve
|
|
@@ -31,7 +40,7 @@ module Thrift
|
|
|
31
40
|
end
|
|
32
41
|
|
|
33
42
|
def to_s
|
|
34
|
-
"server(#{@protocol_factory
|
|
43
|
+
"server(#{@protocol_factory}(#{@transport_factory}(#{@server_transport})))"
|
|
35
44
|
end
|
|
36
45
|
end
|
|
37
46
|
end
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
1
2
|
#
|
|
2
3
|
# Licensed to the Apache Software Foundation (ASF) under one
|
|
3
4
|
# or more contributor license agreements. See the NOTICE file
|
|
@@ -17,15 +18,20 @@
|
|
|
17
18
|
# under the License.
|
|
18
19
|
#
|
|
19
20
|
|
|
20
|
-
require
|
|
21
|
-
require
|
|
21
|
+
require "logger"
|
|
22
|
+
require "thread"
|
|
22
23
|
|
|
23
24
|
module Thrift
|
|
24
25
|
# this class expects to always use a FramedTransport for reading messages
|
|
25
26
|
class NonblockingServer < BaseServer
|
|
26
|
-
def initialize(processor, server_transport, transport_factory = nil, protocol_factory = nil, num = 20, logger = nil
|
|
27
|
+
def initialize(processor, server_transport, transport_factory = nil, protocol_factory = nil, num = 20, logger = nil,
|
|
28
|
+
max_frame_size: FramedTransport::DEFAULT_MAX_FRAME_SIZE)
|
|
27
29
|
super(processor, server_transport, transport_factory, protocol_factory)
|
|
30
|
+
unless max_frame_size > 0 && max_frame_size <= FramedTransport::HARD_MAX_FRAME_SIZE
|
|
31
|
+
raise ArgumentError, "max_frame_size must be > 0 and <= #{FramedTransport::HARD_MAX_FRAME_SIZE}"
|
|
32
|
+
end
|
|
28
33
|
@num_threads = num
|
|
34
|
+
@max_frame_size = max_frame_size
|
|
29
35
|
if logger.nil?
|
|
30
36
|
@logger = Logger.new(STDERR)
|
|
31
37
|
@logger.level = Logger::WARN
|
|
@@ -52,11 +58,16 @@ module Thrift
|
|
|
52
58
|
break
|
|
53
59
|
end
|
|
54
60
|
next if rd.nil?
|
|
55
|
-
|
|
61
|
+
begin
|
|
62
|
+
socket = @server_transport.accept
|
|
63
|
+
rescue => e
|
|
64
|
+
next if defined?(OpenSSL::SSL::SSLError) && e.is_a?(OpenSSL::SSL::SSLError)
|
|
65
|
+
raise
|
|
66
|
+
end
|
|
56
67
|
@logger.debug "Accepted socket: #{socket.inspect}"
|
|
57
68
|
@io_manager.add_connection socket
|
|
58
69
|
end
|
|
59
|
-
rescue IOError
|
|
70
|
+
rescue IOError
|
|
60
71
|
end
|
|
61
72
|
# we must be shutting down
|
|
62
73
|
@logger.info "#{self} is shutting down, goodbye"
|
|
@@ -83,14 +94,17 @@ module Thrift
|
|
|
83
94
|
if block
|
|
84
95
|
shutdown_proc.call
|
|
85
96
|
else
|
|
86
|
-
Thread.new
|
|
97
|
+
Thread.new(&shutdown_proc)
|
|
87
98
|
end
|
|
88
99
|
end
|
|
89
100
|
|
|
90
101
|
private
|
|
91
102
|
|
|
92
103
|
def start_io_manager
|
|
93
|
-
iom = IOManager.new(
|
|
104
|
+
iom = IOManager.new(
|
|
105
|
+
@processor, @server_transport, @transport_factory, @protocol_factory, @num_threads, @logger,
|
|
106
|
+
max_frame_size: @max_frame_size,
|
|
107
|
+
)
|
|
94
108
|
iom.spawn
|
|
95
109
|
iom
|
|
96
110
|
end
|
|
@@ -98,15 +112,17 @@ module Thrift
|
|
|
98
112
|
class IOManager # :nodoc:
|
|
99
113
|
DEFAULT_BUFFER = 2**20
|
|
100
114
|
|
|
101
|
-
def initialize(processor, server_transport, transport_factory, protocol_factory, num, logger
|
|
115
|
+
def initialize(processor, server_transport, transport_factory, protocol_factory, num, logger,
|
|
116
|
+
max_frame_size: FramedTransport::DEFAULT_MAX_FRAME_SIZE)
|
|
102
117
|
@processor = processor
|
|
103
118
|
@server_transport = server_transport
|
|
104
119
|
@transport_factory = transport_factory
|
|
105
120
|
@protocol_factory = protocol_factory
|
|
106
121
|
@num_threads = num
|
|
107
122
|
@logger = logger
|
|
123
|
+
@max_frame_size = max_frame_size
|
|
108
124
|
@connections = []
|
|
109
|
-
@buffers = Hash.new { |h, k| h[k] =
|
|
125
|
+
@buffers = Hash.new { |h, k| h[k] = Bytes.empty_byte_buffer }
|
|
110
126
|
@signal_queue = Queue.new
|
|
111
127
|
@signal_pipes = IO.pipe
|
|
112
128
|
@signal_pipes[1].sync = true
|
|
@@ -138,7 +154,12 @@ module Thrift
|
|
|
138
154
|
|
|
139
155
|
def ensure_closed
|
|
140
156
|
kill_worker_threads if @worker_threads
|
|
141
|
-
@iom_thread
|
|
157
|
+
if @iom_thread&.alive?
|
|
158
|
+
@iom_thread.kill
|
|
159
|
+
@iom_thread.join
|
|
160
|
+
end
|
|
161
|
+
close_connections
|
|
162
|
+
close_signal_pipes
|
|
142
163
|
end
|
|
143
164
|
|
|
144
165
|
private
|
|
@@ -152,15 +173,13 @@ module Thrift
|
|
|
152
173
|
break if read_signals == :shutdown
|
|
153
174
|
end
|
|
154
175
|
rd.each do |fd|
|
|
155
|
-
|
|
156
|
-
if fd.handle.eof?
|
|
157
|
-
remove_connection fd
|
|
158
|
-
else
|
|
159
|
-
read_connection fd
|
|
160
|
-
end
|
|
161
|
-
rescue Errno::ECONNRESET
|
|
176
|
+
if fd.handle.eof?
|
|
162
177
|
remove_connection fd
|
|
178
|
+
else
|
|
179
|
+
read_connection fd
|
|
163
180
|
end
|
|
181
|
+
rescue Errno::ECONNRESET
|
|
182
|
+
remove_connection fd
|
|
164
183
|
end
|
|
165
184
|
end
|
|
166
185
|
join_worker_threads(@shutdown_timeout)
|
|
@@ -169,8 +188,22 @@ module Thrift
|
|
|
169
188
|
end
|
|
170
189
|
|
|
171
190
|
def read_connection(fd)
|
|
172
|
-
@buffers[fd]
|
|
173
|
-
|
|
191
|
+
buf = @buffers[fd]
|
|
192
|
+
buf << fd.read(DEFAULT_BUFFER)
|
|
193
|
+
while buf.length >= 4
|
|
194
|
+
# Refuse the size before collecting the frame: the four-byte length
|
|
195
|
+
# is read here and the bytes are then buffered as they arrive, for as
|
|
196
|
+
# long as the declared length allows. FramedTransport applies the
|
|
197
|
+
# same maximum to the frame the worker later reads back.
|
|
198
|
+
size = buf.unpack1("N")
|
|
199
|
+
if size > @max_frame_size
|
|
200
|
+
@logger.error "Frame size #{size} exceeds maximum #{@max_frame_size}, closing connection"
|
|
201
|
+
fd.close
|
|
202
|
+
remove_connection fd
|
|
203
|
+
break
|
|
204
|
+
end
|
|
205
|
+
frame = slice_frame!(buf)
|
|
206
|
+
break if frame.nil?
|
|
174
207
|
@logger.debug "#{self} is processing a frame"
|
|
175
208
|
@worker_queue.push [:frame, fd, frame]
|
|
176
209
|
end
|
|
@@ -246,9 +279,25 @@ module Thrift
|
|
|
246
279
|
@worker_threads.clear
|
|
247
280
|
end
|
|
248
281
|
|
|
282
|
+
def close_connections
|
|
283
|
+
@connections.each do |fd|
|
|
284
|
+
fd.close
|
|
285
|
+
rescue IOError, SystemCallError, TransportException
|
|
286
|
+
end
|
|
287
|
+
@connections.clear
|
|
288
|
+
@buffers.clear
|
|
289
|
+
end
|
|
290
|
+
|
|
291
|
+
def close_signal_pipes
|
|
292
|
+
@signal_pipes.each do |pipe|
|
|
293
|
+
pipe.close unless pipe.closed?
|
|
294
|
+
rescue IOError
|
|
295
|
+
end
|
|
296
|
+
end
|
|
297
|
+
|
|
249
298
|
def slice_frame!(buf)
|
|
250
299
|
if buf.length >= 4
|
|
251
|
-
size = buf.
|
|
300
|
+
size = buf.unpack1("N")
|
|
252
301
|
if buf.length >= size + 4
|
|
253
302
|
buf.slice!(0, size + 4)
|
|
254
303
|
else
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
#
|
|
3
|
+
# Licensed to the Apache Software Foundation (ASF) under one
|
|
4
|
+
# or more contributor license agreements. See the NOTICE file
|
|
5
|
+
# distributed with this work for additional information
|
|
6
|
+
# regarding copyright ownership. The ASF licenses this file
|
|
7
|
+
# to you under the Apache License, Version 2.0 (the
|
|
8
|
+
# "License"); you may not use this file except in compliance
|
|
9
|
+
# with the License. You may obtain a copy of the License at
|
|
10
|
+
#
|
|
11
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
|
12
|
+
#
|
|
13
|
+
# Unless required by applicable law or agreed to in writing,
|
|
14
|
+
# software distributed under the License is distributed on an
|
|
15
|
+
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
|
16
|
+
# KIND, either express or implied. See the License for the
|
|
17
|
+
# specific language governing permissions and limitations
|
|
18
|
+
# under the License.
|
|
19
|
+
#
|
|
20
|
+
|
|
21
|
+
require "rack"
|
|
22
|
+
require "thrift/transport/io_stream_transport"
|
|
23
|
+
|
|
24
|
+
module Thrift
|
|
25
|
+
class RackApplication
|
|
26
|
+
THRIFT_HEADER = "application/x-thrift"
|
|
27
|
+
|
|
28
|
+
def initialize(processor, protocol_factory = BinaryProtocolFactory.new)
|
|
29
|
+
@processor = processor
|
|
30
|
+
@protocol_factory = protocol_factory
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def call(env)
|
|
34
|
+
request = Rack::Request.new(env)
|
|
35
|
+
|
|
36
|
+
if self.class.valid_thrift_request?(request)
|
|
37
|
+
self.class.successful_request(request, @processor, @protocol_factory).finish
|
|
38
|
+
else
|
|
39
|
+
self.class.failed_request.finish
|
|
40
|
+
end
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
def self.mapped(path, processor, protocol_factory = BinaryProtocolFactory.new)
|
|
44
|
+
Rack::Builder.new do
|
|
45
|
+
use Rack::ContentLength
|
|
46
|
+
map path do
|
|
47
|
+
run RackApplication.new(processor, protocol_factory)
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def self.successful_request(rack_request, processor, protocol_factory)
|
|
53
|
+
response = Rack::Response.new([], 200, {Rack::CONTENT_TYPE => THRIFT_HEADER})
|
|
54
|
+
transport = IOStreamTransport.new(rack_request.body, response)
|
|
55
|
+
protocol = protocol_factory.get_protocol(transport)
|
|
56
|
+
processor.process protocol, protocol
|
|
57
|
+
|
|
58
|
+
response
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def self.failed_request
|
|
62
|
+
Rack::Response.new(["Not Found"], 404, {Rack::CONTENT_TYPE => THRIFT_HEADER})
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
def self.valid_thrift_request?(rack_request)
|
|
66
|
+
rack_request.post? && rack_request.media_type == THRIFT_HEADER
|
|
67
|
+
end
|
|
68
|
+
end
|
|
69
|
+
end
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
1
2
|
#
|
|
2
3
|
# Licensed to the Apache Software Foundation (ASF) under one
|
|
3
4
|
# or more contributor license agreements. See the NOTICE file
|
|
@@ -20,28 +21,39 @@
|
|
|
20
21
|
module Thrift
|
|
21
22
|
class SimpleServer < BaseServer
|
|
22
23
|
def serve
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
24
|
+
@server_transport.listen
|
|
25
|
+
loop do
|
|
26
|
+
begin
|
|
26
27
|
client = @server_transport.accept
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
28
|
+
rescue Errno::ECONNRESET, Errno::EPIPE
|
|
29
|
+
next
|
|
30
|
+
rescue => e
|
|
31
|
+
next if defined?(OpenSSL::SSL::SSLError) && e.is_a?(OpenSSL::SSL::SSLError)
|
|
32
|
+
raise
|
|
33
|
+
end
|
|
34
|
+
trans = @transport_factory.get_transport(client)
|
|
35
|
+
prot = @protocol_factory.get_protocol(trans)
|
|
36
|
+
begin
|
|
37
|
+
loop do
|
|
38
|
+
@processor.process(prot, prot)
|
|
36
39
|
end
|
|
40
|
+
rescue Thrift::TransportException, Thrift::ProtocolException
|
|
41
|
+
# The client hung up or sent a message this connection could not
|
|
42
|
+
# read. Close it below and keep accepting other clients.
|
|
43
|
+
rescue => e
|
|
44
|
+
# Any other error raised while serving this one client must not end
|
|
45
|
+
# the accept loop. Log it, close the connection, and keep serving.
|
|
46
|
+
@logger.error("Error while serving a client connection: #{e.inspect}")
|
|
47
|
+
ensure
|
|
48
|
+
trans.close
|
|
37
49
|
end
|
|
38
|
-
ensure
|
|
39
|
-
@server_transport.close
|
|
40
50
|
end
|
|
51
|
+
ensure
|
|
52
|
+
@server_transport.close
|
|
41
53
|
end
|
|
42
54
|
|
|
43
55
|
def to_s
|
|
44
|
-
"simple(#{super
|
|
56
|
+
"simple(#{super})"
|
|
45
57
|
end
|
|
46
58
|
end
|
|
47
59
|
end
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
1
2
|
#
|
|
2
3
|
# Licensed to the Apache Software Foundation (ASF) under one
|
|
3
4
|
# or more contributor license agreements. See the NOTICE file
|
|
@@ -17,14 +18,16 @@
|
|
|
17
18
|
# under the License.
|
|
18
19
|
#
|
|
19
20
|
|
|
20
|
-
require
|
|
21
|
-
require
|
|
21
|
+
require "rack"
|
|
22
|
+
require "thin"
|
|
23
|
+
require "thrift/server/rack_application"
|
|
22
24
|
|
|
23
25
|
##
|
|
24
26
|
# Wraps the Thin web server to provide a Thrift server over HTTP.
|
|
27
|
+
# <b>DEPRECATED:</b> Use <tt>Thrift::RackApplication</tt> with a maintained Rack
|
|
28
|
+
# server instead.
|
|
25
29
|
module Thrift
|
|
26
30
|
class ThinHTTPServer < BaseServer
|
|
27
|
-
|
|
28
31
|
##
|
|
29
32
|
# Accepts a Thrift::Processor
|
|
30
33
|
# Options include:
|
|
@@ -32,13 +35,26 @@ module Thrift
|
|
|
32
35
|
# * :ip
|
|
33
36
|
# * :path
|
|
34
37
|
# * :protocol_factory
|
|
38
|
+
# * :ssl
|
|
39
|
+
# * :ssl_options
|
|
35
40
|
def initialize(processor, options = {})
|
|
41
|
+
Kernel.warn "[DEPRECATION WARNING] `Thrift::ThinHTTPServer` is deprecated because Thin is no longer maintained. Please use `Thrift::RackApplication` with a maintained Rack server instead."
|
|
36
42
|
port = options[:port] || 80
|
|
37
43
|
ip = options[:ip] || "0.0.0.0"
|
|
38
44
|
path = options[:path] || "/"
|
|
39
45
|
protocol_factory = options[:protocol_factory] || BinaryProtocolFactory.new
|
|
40
|
-
|
|
46
|
+
endpoint = RackApplication.mapped(path, processor, protocol_factory)
|
|
47
|
+
app = Rack::Builder.new do
|
|
48
|
+
use Rack::CommonLogger
|
|
49
|
+
use Rack::ShowExceptions
|
|
50
|
+
use Rack::Lint
|
|
51
|
+
run endpoint
|
|
52
|
+
end
|
|
41
53
|
@server = Thin::Server.new(ip, port, app)
|
|
54
|
+
if options[:ssl]
|
|
55
|
+
@server.ssl = true
|
|
56
|
+
@server.ssl_options = options[:ssl_options] || {}
|
|
57
|
+
end
|
|
42
58
|
end
|
|
43
59
|
|
|
44
60
|
##
|
|
@@ -47,45 +63,6 @@ module Thrift
|
|
|
47
63
|
@server.start
|
|
48
64
|
end
|
|
49
65
|
|
|
50
|
-
|
|
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).finish
|
|
64
|
-
else
|
|
65
|
-
RackApplication.failed_request.finish
|
|
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
|
-
|
|
66
|
+
RackApplication = Thrift::RackApplication
|
|
90
67
|
end
|
|
91
68
|
end
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
1
2
|
#
|
|
2
3
|
# Licensed to the Apache Software Foundation (ASF) under one
|
|
3
4
|
# or more contributor license agreements. See the NOTICE file
|
|
@@ -17,7 +18,7 @@
|
|
|
17
18
|
# under the License.
|
|
18
19
|
#
|
|
19
20
|
|
|
20
|
-
require
|
|
21
|
+
require "thread"
|
|
21
22
|
|
|
22
23
|
module Thrift
|
|
23
24
|
class ThreadPoolServer < BaseServer
|
|
@@ -46,25 +47,28 @@ module Thrift
|
|
|
46
47
|
loop do
|
|
47
48
|
@thread_q.push(:token)
|
|
48
49
|
Thread.new do
|
|
49
|
-
|
|
50
|
-
|
|
50
|
+
loop do
|
|
51
|
+
begin
|
|
51
52
|
client = @server_transport.accept
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
53
|
+
rescue => e
|
|
54
|
+
next if defined?(OpenSSL::SSL::SSLError) && e.is_a?(OpenSSL::SSL::SSLError)
|
|
55
|
+
raise
|
|
56
|
+
end
|
|
57
|
+
trans = @transport_factory.get_transport(client)
|
|
58
|
+
prot = @protocol_factory.get_protocol(trans)
|
|
59
|
+
begin
|
|
60
|
+
loop do
|
|
61
|
+
@processor.process(prot, prot)
|
|
61
62
|
end
|
|
63
|
+
rescue Thrift::TransportException, Thrift::ProtocolException
|
|
64
|
+
ensure
|
|
65
|
+
trans.close
|
|
62
66
|
end
|
|
63
|
-
rescue => e
|
|
64
|
-
@exception_q.push(e)
|
|
65
|
-
ensure
|
|
66
|
-
@thread_q.pop # thread died!
|
|
67
67
|
end
|
|
68
|
+
rescue => e
|
|
69
|
+
@exception_q.push(e)
|
|
70
|
+
ensure
|
|
71
|
+
@thread_q.pop # thread died!
|
|
68
72
|
end
|
|
69
73
|
end
|
|
70
74
|
ensure
|
|
@@ -73,7 +77,7 @@ module Thrift
|
|
|
73
77
|
end
|
|
74
78
|
|
|
75
79
|
def to_s
|
|
76
|
-
"threadpool(#{super
|
|
80
|
+
"threadpool(#{super})"
|
|
77
81
|
end
|
|
78
82
|
end
|
|
79
83
|
end
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
1
2
|
#
|
|
2
3
|
# Licensed to the Apache Software Foundation (ASF) under one
|
|
3
4
|
# or more contributor license agreements. See the NOTICE file
|
|
@@ -17,35 +18,38 @@
|
|
|
17
18
|
# under the License.
|
|
18
19
|
#
|
|
19
20
|
|
|
20
|
-
require
|
|
21
|
+
require "thread"
|
|
21
22
|
|
|
22
23
|
module Thrift
|
|
23
24
|
class ThreadedServer < BaseServer
|
|
24
25
|
def serve
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
26
|
+
@server_transport.listen
|
|
27
|
+
loop do
|
|
28
|
+
begin
|
|
28
29
|
client = @server_transport.accept
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
30
|
+
rescue Errno::ECONNRESET, Errno::EPIPE
|
|
31
|
+
next
|
|
32
|
+
rescue => e
|
|
33
|
+
next if defined?(OpenSSL::SSL::SSLError) && e.is_a?(OpenSSL::SSL::SSLError)
|
|
34
|
+
raise
|
|
35
|
+
end
|
|
36
|
+
trans = @transport_factory.get_transport(client)
|
|
37
|
+
prot = @protocol_factory.get_protocol(trans)
|
|
38
|
+
Thread.new(prot, trans) do |p, t|
|
|
39
|
+
loop do
|
|
40
|
+
@processor.process(p, p)
|
|
40
41
|
end
|
|
42
|
+
rescue Thrift::TransportException, Thrift::ProtocolException
|
|
43
|
+
ensure
|
|
44
|
+
t.close
|
|
41
45
|
end
|
|
42
|
-
ensure
|
|
43
|
-
@server_transport.close
|
|
44
46
|
end
|
|
47
|
+
ensure
|
|
48
|
+
@server_transport.close
|
|
45
49
|
end
|
|
46
50
|
|
|
47
51
|
def to_s
|
|
48
|
-
"threaded(#{super
|
|
52
|
+
"threaded(#{super})"
|
|
49
53
|
end
|
|
50
54
|
end
|
|
51
55
|
end
|