grpc_kit 0.1.4 → 0.1.5
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 +2 -1
- data/TODO.md +11 -4
- data/grpc_kit.gemspec +1 -1
- data/lib/grpc_kit/calls/client_client_streamer.rb +2 -2
- data/lib/grpc_kit/calls/client_request_response.rb +2 -2
- data/lib/grpc_kit/calls/client_server_streamer.rb +2 -2
- data/lib/grpc_kit/calls/server_client_streamer.rb +8 -1
- data/lib/grpc_kit/calls/server_request_response.rb +8 -1
- data/lib/grpc_kit/calls/server_server_streamer.rb +8 -1
- data/lib/grpc_kit/calls.rb +3 -0
- data/lib/grpc_kit/client.rb +17 -14
- data/lib/grpc_kit/grpc/dsl.rb +21 -8
- data/lib/grpc_kit/grpc_time.rb +2 -7
- data/lib/grpc_kit/interceptors/client_request_response.rb +2 -5
- data/lib/grpc_kit/interceptors.rb +2 -5
- data/lib/grpc_kit/rpc_desc.rb +4 -2
- data/lib/grpc_kit/rpcs/client_client_streamer.rb +4 -2
- data/lib/grpc_kit/rpcs/client_request_response.rb +16 -5
- data/lib/grpc_kit/rpcs/client_server_streamer.rb +8 -3
- data/lib/grpc_kit/server.rb +38 -8
- data/lib/grpc_kit/{sessions → session}/client_session.rb +49 -9
- data/lib/grpc_kit/session/drain_controller.rb +35 -0
- data/lib/grpc_kit/session/headers.rb +9 -3
- data/lib/grpc_kit/{sessions → session}/server_session.rb +42 -17
- data/lib/grpc_kit/{streams → stream}/client_stream.rb +27 -23
- data/lib/grpc_kit/{streams → stream}/server_stream.rb +29 -29
- data/lib/grpc_kit/{transports → transport}/client_transport.rb +3 -3
- data/lib/grpc_kit/{transports → transport}/server_transport.rb +4 -4
- data/lib/grpc_kit/version.rb +1 -1
- metadata +11 -10
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 5cd6355c75605e749f1590fa3f3f3346f5d77288753df21cd104c9af78d22f5f
|
4
|
+
data.tar.gz: 3e6d0c8606b0476edaca281b510b1c8d1f047df7accc479e2b1e569567869497
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: bde53f9753f23d273ed4b211c63f2e4727e88c8d67b9b330add41c9bec5b82ebbe884c551c496c5fcdca57252e36d58660ac5a70f31ecd8cb84f00258a6972f9
|
7
|
+
data.tar.gz: 75d4b9b74c7cc99111c348c754c79cda00295745485ee6d28a4e0aa492bc28bcc6303dd04bbd95320a483a3bc8559840c79be09621eabb04bfb853b7e7be9760
|
data/README.md
CHANGED
@@ -47,7 +47,8 @@ end
|
|
47
47
|
##### Client
|
48
48
|
|
49
49
|
```ruby
|
50
|
-
|
50
|
+
sock = TCPSocket.new('localhost', 50051)
|
51
|
+
stub = Helloworld::Greeter::Stub.new(sock)
|
51
52
|
message = stub.say_hello(Helloworld::HelloRequest.new(name: 'your name')).message
|
52
53
|
puts message
|
53
54
|
```
|
data/TODO.md
CHANGED
@@ -13,8 +13,8 @@
|
|
13
13
|
### server streamer
|
14
14
|
|
15
15
|
- [x] recv/send msg
|
16
|
-
- [
|
17
|
-
- [
|
16
|
+
- [x] metadata (client)
|
17
|
+
- [x] metadata (server)
|
18
18
|
- [x] interceptor (client)
|
19
19
|
- [x] interceptor (server)
|
20
20
|
- [ ] deadline (client)
|
@@ -23,8 +23,8 @@
|
|
23
23
|
### client streamer
|
24
24
|
|
25
25
|
- [x] recv/send msg
|
26
|
-
- [
|
27
|
-
- [
|
26
|
+
- [x] metadata (client)
|
27
|
+
- [x] metadata (server)
|
28
28
|
- [x] interceptor (client)
|
29
29
|
- [x] interceptor (server)
|
30
30
|
- [ ] deadline (client)
|
@@ -62,3 +62,10 @@
|
|
62
62
|
- [ ] add server request spec
|
63
63
|
- [ ] add client request spec
|
64
64
|
- [ ] handle RST FRAME
|
65
|
+
|
66
|
+
## bugs
|
67
|
+
|
68
|
+
- [x] status_check is invoked twice
|
69
|
+
- [x] undefined local variable or method `finish' for #<GrpcKit::Sessions::ClientSession:0x00007f9ae3abf970> (NameError)
|
70
|
+
- [x] clients don't use same object even if thier connections alive
|
71
|
+
|
data/grpc_kit.gemspec
CHANGED
@@ -22,7 +22,7 @@ Gem::Specification.new do |spec|
|
|
22
22
|
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
|
23
23
|
spec.require_paths = ['lib']
|
24
24
|
|
25
|
-
spec.add_dependency 'ds9', '~> 1.2.
|
25
|
+
spec.add_dependency 'ds9', '~> 1.2.1'
|
26
26
|
spec.add_dependency 'google-protobuf', '~> 3.6.1'
|
27
27
|
spec.add_dependency 'googleapis-common-protos-types', '~> 1.0.2'
|
28
28
|
|
@@ -9,10 +9,10 @@ module GrpcKit
|
|
9
9
|
attr_reader :metadata
|
10
10
|
alias outgoing_metadata metadata
|
11
11
|
|
12
|
-
def send_msg(data, timeout: nil,
|
12
|
+
def send_msg(data, timeout: nil, last: false)
|
13
13
|
raise 'No method error' if @restrict
|
14
14
|
|
15
|
-
@stream.send_msg(data, last: last, timeout: timeout, metadata:
|
15
|
+
@stream.send_msg(data, last: last, timeout: timeout, metadata: outgoing_metadata)
|
16
16
|
end
|
17
17
|
|
18
18
|
def recv(last: false)
|
@@ -9,10 +9,10 @@ module GrpcKit
|
|
9
9
|
attr_reader :metadata
|
10
10
|
alias outgoing_metadata metadata
|
11
11
|
|
12
|
-
def send_msg(data, timeout: nil,
|
12
|
+
def send_msg(data, timeout: nil, last: false)
|
13
13
|
raise 'No method error' if @restrict
|
14
14
|
|
15
|
-
@stream.send_msg(data, last: last, timeout: timeout, metadata:
|
15
|
+
@stream.send_msg(data, last: last, timeout: timeout, metadata: outgoing_metadata)
|
16
16
|
end
|
17
17
|
|
18
18
|
def recv(last: false)
|
@@ -9,10 +9,10 @@ module GrpcKit
|
|
9
9
|
attr_reader :metadata
|
10
10
|
alias outgoing_metadata metadata
|
11
11
|
|
12
|
-
def send_msg(data, timeout: nil,
|
12
|
+
def send_msg(data, timeout: nil, last: false)
|
13
13
|
raise 'No method error' if @restrict
|
14
14
|
|
15
|
-
@stream.send_msg(data, last: last, timeout: timeout, metadata:
|
15
|
+
@stream.send_msg(data, last: last, timeout: timeout, metadata: outgoing_metadata)
|
16
16
|
end
|
17
17
|
|
18
18
|
def recv(last: false)
|
@@ -19,7 +19,14 @@ module GrpcKit
|
|
19
19
|
def send_msg(data, last: false)
|
20
20
|
raise 'No method error' if @restrict
|
21
21
|
|
22
|
-
@stream.send_msg(
|
22
|
+
@stream.send_msg(
|
23
|
+
data,
|
24
|
+
@protobuf,
|
25
|
+
last: last,
|
26
|
+
initial_metadata: @outgoing_initial_metadata,
|
27
|
+
trailing_metadata: @outgoing_trailing_metadata,
|
28
|
+
limit_size: @config.max_send_message_size,
|
29
|
+
)
|
23
30
|
end
|
24
31
|
|
25
32
|
def recv(last: false)
|
@@ -19,7 +19,14 @@ module GrpcKit
|
|
19
19
|
def send_msg(data, last: false)
|
20
20
|
raise 'No method error' if @restrict
|
21
21
|
|
22
|
-
@stream.send_msg(
|
22
|
+
@stream.send_msg(
|
23
|
+
data,
|
24
|
+
@protobuf,
|
25
|
+
last: last,
|
26
|
+
initial_metadata: @outgoing_initial_metadata,
|
27
|
+
trailing_metadata: @outgoing_trailing_metadata,
|
28
|
+
limit_size: @config.max_send_message_size,
|
29
|
+
)
|
23
30
|
end
|
24
31
|
|
25
32
|
def recv(last: false)
|
@@ -19,7 +19,14 @@ module GrpcKit
|
|
19
19
|
def send_msg(data, last: false)
|
20
20
|
raise 'No method error' if @restrict
|
21
21
|
|
22
|
-
@stream.send_msg(
|
22
|
+
@stream.send_msg(
|
23
|
+
data,
|
24
|
+
@protobuf,
|
25
|
+
last: last,
|
26
|
+
initial_metadata: @outgoing_initial_metadata,
|
27
|
+
trailing_metadata: @outgoing_trailing_metadata,
|
28
|
+
limit_size: @config.max_send_message_size,
|
29
|
+
)
|
23
30
|
end
|
24
31
|
|
25
32
|
def recv(last: false)
|
data/lib/grpc_kit/calls.rb
CHANGED
@@ -8,6 +8,9 @@ module GrpcKit
|
|
8
8
|
Klass = Struct.new(:service_name)
|
9
9
|
attr_reader :method
|
10
10
|
|
11
|
+
# @params stream [GrpcKit::Stream::ServerStream|GrpcKit::Stream::ClientStream]
|
12
|
+
# @params config [GrpcKit::MethodConfig]
|
13
|
+
# @params metadata [Hash]
|
11
14
|
def initialize(stream:, config:, metadata:, timeout: nil)
|
12
15
|
@config = config
|
13
16
|
@metadata = metadata
|
data/lib/grpc_kit/client.rb
CHANGED
@@ -2,9 +2,9 @@
|
|
2
2
|
|
3
3
|
require 'grpc_kit/grpc_time'
|
4
4
|
require 'grpc_kit/session/io'
|
5
|
-
require 'grpc_kit/
|
6
|
-
require 'grpc_kit/
|
7
|
-
require 'grpc_kit/
|
5
|
+
require 'grpc_kit/session/client_session'
|
6
|
+
require 'grpc_kit/stream/client_stream'
|
7
|
+
require 'grpc_kit/transport/client_transport'
|
8
8
|
|
9
9
|
module GrpcKit
|
10
10
|
class Client
|
@@ -17,43 +17,46 @@ module GrpcKit
|
|
17
17
|
addr = sock.addr
|
18
18
|
"#{addr[3]}:#{addr[1]}"
|
19
19
|
end
|
20
|
-
|
20
|
+
|
21
21
|
@timeout = timeout && GrpcKit::GrpcTime.new(timeout)
|
22
|
+
|
23
|
+
build_rpcs(interceptors)
|
22
24
|
end
|
23
25
|
|
24
26
|
def request_response(rpc, request, opts = {})
|
25
27
|
GrpcKit.logger.debug('Calling request_respose')
|
26
|
-
|
27
|
-
rpc.config.interceptor.interceptors = @interceptors
|
28
28
|
do_request(rpc, request, opts)
|
29
29
|
end
|
30
30
|
|
31
31
|
def client_streamer(rpc, opts = {})
|
32
32
|
GrpcKit.logger.debug('Calling client_streamer')
|
33
|
-
rpc.config.interceptor.interceptors = @interceptors
|
34
33
|
do_request(rpc, nil, opts)
|
35
34
|
end
|
36
35
|
|
37
36
|
def server_streamer(rpc, request, opts = {})
|
38
37
|
GrpcKit.logger.debug('Calling server_streamer')
|
39
|
-
rpc.config.interceptor.interceptors = @interceptors
|
40
38
|
do_request(rpc, request, opts)
|
41
39
|
end
|
42
40
|
|
43
41
|
def bidi_streamer(rpc, requests, opts = {})
|
44
|
-
rpc.config.interceptor.interceptors = @interceptors
|
45
42
|
GrpcKit.logger.debug('Calling bidi_streamer')
|
46
43
|
end
|
47
44
|
|
48
45
|
private
|
49
46
|
|
50
47
|
def do_request(rpc, request, **opts)
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
t = GrpcKit::Transports::ClientTransport.new(session)
|
55
|
-
cs = GrpcKit::Streams::ClientStream.new(t, rpc.config, authority: @authority, timeout: @timeout)
|
48
|
+
t = GrpcKit::Transport::ClientTransport.new(session)
|
49
|
+
cs = GrpcKit::Stream::ClientStream.new(t, rpc.config, authority: @authority, timeout: @timeout)
|
56
50
|
rpc.invoke(cs, request, opts.merge(timeout: @timeout))
|
57
51
|
end
|
52
|
+
|
53
|
+
def session
|
54
|
+
@session ||=
|
55
|
+
begin
|
56
|
+
s = GrpcKit::Session::ClientSession.new(GrpcKit::Session::IO.new(@sock))
|
57
|
+
s.submit_settings([])
|
58
|
+
s
|
59
|
+
end
|
60
|
+
end
|
58
61
|
end
|
59
62
|
end
|
data/lib/grpc_kit/grpc/dsl.rb
CHANGED
@@ -48,27 +48,40 @@ module GrpcKit
|
|
48
48
|
end
|
49
49
|
|
50
50
|
def rpc_stub_class
|
51
|
-
rpc_descs_ =
|
51
|
+
rpc_descs_ = {}
|
52
|
+
rpc_descs.each_value do |rpc_desc|
|
53
|
+
rpc_descs_[rpc_desc.ruby_style_name] = rpc_desc
|
54
|
+
end
|
55
|
+
|
52
56
|
Class.new(GrpcKit::Client) do
|
53
|
-
|
54
|
-
|
55
|
-
|
57
|
+
def initialize(*)
|
58
|
+
@rpcs = {}
|
59
|
+
super
|
60
|
+
end
|
61
|
+
|
62
|
+
define_method(:build_rpcs) do |interceptors|
|
63
|
+
rpc_descs_.each do |method_name, rpc_desc|
|
64
|
+
@rpcs[method_name] = rpc_desc.build_client(interceptors: interceptors)
|
65
|
+
end
|
66
|
+
end
|
67
|
+
private :build_rpcs
|
56
68
|
|
69
|
+
rpc_descs_.each do |method_name, rpc_desc|
|
57
70
|
if rpc_desc.request_response?
|
58
71
|
define_method(method_name) do |request, opts = {}|
|
59
|
-
request_response(
|
72
|
+
request_response(@rpcs.fetch(method_name), request, opts)
|
60
73
|
end
|
61
74
|
elsif rpc_desc.client_streamer?
|
62
75
|
define_method(method_name) do |opts = {}|
|
63
|
-
client_streamer(
|
76
|
+
client_streamer(@rpcs.fetch(method_name), opts)
|
64
77
|
end
|
65
78
|
elsif rpc_desc.server_streamer?
|
66
79
|
define_method(method_name) do |request, opts = {}|
|
67
|
-
server_streamer(
|
80
|
+
server_streamer(@rpcs.fetch(method_name), request, opts)
|
68
81
|
end
|
69
82
|
elsif rpc_desc.bidi_streamer?
|
70
83
|
define_method(method_name) do |requests, opts = {}, &blk|
|
71
|
-
bidi_streamer(
|
84
|
+
bidi_streamer(@rpcs.fetch(method_name), requests, opts, &blk)
|
72
85
|
end
|
73
86
|
else
|
74
87
|
raise "unknown #{rpc_desc}"
|
data/lib/grpc_kit/grpc_time.rb
CHANGED
@@ -2,7 +2,7 @@
|
|
2
2
|
|
3
3
|
module GrpcKit
|
4
4
|
class GrpcTime
|
5
|
-
MAX = 10**9-1
|
5
|
+
MAX = 10**9 - 1
|
6
6
|
|
7
7
|
# @params value [String|Integer]
|
8
8
|
def initialize(value)
|
@@ -67,12 +67,7 @@ module GrpcKit
|
|
67
67
|
private
|
68
68
|
|
69
69
|
def from_integer(value)
|
70
|
-
|
71
|
-
@value = MAX
|
72
|
-
else
|
73
|
-
@value = value
|
74
|
-
end
|
75
|
-
|
70
|
+
@value = value < 0 ? MAX : value
|
76
71
|
@unit = 'S'
|
77
72
|
end
|
78
73
|
|
@@ -5,11 +5,8 @@ require 'grpc_kit/interceptors'
|
|
5
5
|
module GrpcKit
|
6
6
|
module Interceptors::Client
|
7
7
|
class RequestResponse
|
8
|
-
|
9
|
-
|
10
|
-
def initialize
|
11
|
-
# Cant' get interceptor at definition time...
|
12
|
-
@interceptors = nil
|
8
|
+
def initialize(interceptors)
|
9
|
+
@interceptors = interceptors
|
13
10
|
end
|
14
11
|
|
15
12
|
def intercept(request, call, metadata, &block)
|
@@ -4,11 +4,8 @@ module GrpcKit
|
|
4
4
|
module Interceptors
|
5
5
|
module Client
|
6
6
|
class Streaming
|
7
|
-
|
8
|
-
|
9
|
-
def initialize
|
10
|
-
# Cant' get interceptor at definition time...
|
11
|
-
@interceptors = nil
|
7
|
+
def initialize(interceptors)
|
8
|
+
@interceptors = interceptors
|
12
9
|
end
|
13
10
|
|
14
11
|
def intercept(call, metadata, &block)
|
data/lib/grpc_kit/rpc_desc.rb
CHANGED
@@ -46,14 +46,16 @@ module GrpcKit
|
|
46
46
|
server.new(handler, config)
|
47
47
|
end
|
48
48
|
|
49
|
-
def build_client
|
49
|
+
def build_client(interceptors: [])
|
50
|
+
inter = interceptors.empty? ? nil : client_interceptor.new(interceptors)
|
51
|
+
|
50
52
|
config = GrpcKit::MethodConfig.build_for_client(
|
51
53
|
path: path,
|
52
54
|
ruby_style_method_name: ruby_style_name,
|
53
55
|
protobuf: client_protobuf,
|
54
56
|
service_name: @server_name,
|
55
57
|
method_name: @name,
|
56
|
-
interceptor:
|
58
|
+
interceptor: inter,
|
57
59
|
)
|
58
60
|
client.new(config)
|
59
61
|
end
|
@@ -14,16 +14,27 @@ module GrpcKit
|
|
14
14
|
stream: stream,
|
15
15
|
)
|
16
16
|
|
17
|
-
|
18
|
-
|
17
|
+
# TODO: DRY
|
18
|
+
if @config.interceptor && timeout
|
19
|
+
@config.interceptor.intercept(request, call, call.metadata) do |r, c, _|
|
19
20
|
Timeout.timeout(timeout.to_f, GrpcKit::Errors::DeadlineExceeded) do
|
20
|
-
call.send_msg(
|
21
|
+
call.send_msg(request, timeout: timeout.to_s, last: true)
|
21
22
|
call.recv(last: true)
|
22
23
|
end
|
23
|
-
|
24
|
-
|
24
|
+
end
|
25
|
+
elsif @config.interceptor && !timeout
|
26
|
+
@config.interceptor.intercept(request, call, call.metadata) do |r, c, _|
|
27
|
+
call.send_msg(request, last: true)
|
28
|
+
call.recv(last: true)
|
29
|
+
end
|
30
|
+
elsif !@config.interceptor && timeout
|
31
|
+
Timeout.timeout(timeout.to_f, GrpcKit::Errors::DeadlineExceeded) do
|
32
|
+
call.send_msg(request, timeout: timeout.to_s, last: true)
|
25
33
|
call.recv(last: true)
|
26
34
|
end
|
35
|
+
else
|
36
|
+
call.send_msg(request, last: true)
|
37
|
+
call.recv(last: true)
|
27
38
|
end
|
28
39
|
end
|
29
40
|
end
|
@@ -9,9 +9,14 @@ module GrpcKit
|
|
9
9
|
def invoke(stream, request, metadata: {}, timeout: nil)
|
10
10
|
call = GrpcKit::Calls::Client::ServerStreamer.new(metadata: metadata, config: @config, timeout: timeout, stream: stream)
|
11
11
|
|
12
|
-
@config.interceptor
|
13
|
-
|
14
|
-
|
12
|
+
if @config.interceptor
|
13
|
+
@config.interceptor.intercept(call, metadata) do |c, m|
|
14
|
+
c.send_msg(request, last: true)
|
15
|
+
c
|
16
|
+
end
|
17
|
+
else
|
18
|
+
call.send_msg(request, last: true)
|
19
|
+
call
|
15
20
|
end
|
16
21
|
end
|
17
22
|
end
|
data/lib/grpc_kit/server.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
require 'grpc_kit/session/io'
|
4
|
-
require 'grpc_kit/
|
4
|
+
require 'grpc_kit/session/server_session'
|
5
5
|
|
6
6
|
module GrpcKit
|
7
7
|
class Server
|
@@ -10,6 +10,8 @@ module GrpcKit
|
|
10
10
|
@rpc_descs = {}
|
11
11
|
@interceptors = interceptors
|
12
12
|
@mutex = Mutex.new
|
13
|
+
@stopping = false
|
14
|
+
@max_graceful_wait = 60
|
13
15
|
|
14
16
|
GrpcKit.logger.debug("Launched grpc_kit(v#{GrpcKit::VERSION})")
|
15
17
|
end
|
@@ -26,23 +28,51 @@ module GrpcKit
|
|
26
28
|
end
|
27
29
|
|
28
30
|
def run(conn)
|
31
|
+
raise 'Stopping server' if @stopping
|
32
|
+
|
29
33
|
establish_session(conn) do |s|
|
30
34
|
s.submit_settings([])
|
31
35
|
s.start
|
32
36
|
end
|
33
37
|
end
|
34
38
|
|
35
|
-
def
|
36
|
-
|
39
|
+
def wait_shutdown
|
40
|
+
loop do
|
41
|
+
return if @stopping
|
42
|
+
|
43
|
+
sleep 1
|
44
|
+
end
|
45
|
+
end
|
37
46
|
|
38
|
-
|
39
|
-
|
47
|
+
def force_shutdown
|
48
|
+
# expected to be called in trap context
|
49
|
+
Thread.new do
|
50
|
+
@mutex.synchronize do
|
51
|
+
GrpcKit.logger.debug('force shutdown')
|
52
|
+
@stopping = true
|
53
|
+
@sessions.each(&:shutdown)
|
54
|
+
end
|
40
55
|
end
|
41
56
|
end
|
42
57
|
|
43
58
|
def graceful_shutdown
|
44
|
-
|
45
|
-
|
59
|
+
# expected to be called in trap context
|
60
|
+
Thread.new do
|
61
|
+
GrpcKit.logger.debug('graceful shutdown')
|
62
|
+
@mutex.synchronize { @sessions.each(&:drain) }
|
63
|
+
begin
|
64
|
+
Timeout.timeout(@max_graceful_wait) do
|
65
|
+
loop do
|
66
|
+
break if @mutex.synchronize { @sessions.empty? }
|
67
|
+
|
68
|
+
sleep 1
|
69
|
+
end
|
70
|
+
end
|
71
|
+
rescue Timeout::Error => _
|
72
|
+
GrpcKit.logger.debug('Max wait time expired')
|
73
|
+
end
|
74
|
+
|
75
|
+
@stopping = true
|
46
76
|
end
|
47
77
|
end
|
48
78
|
|
@@ -62,7 +92,7 @@ module GrpcKit
|
|
62
92
|
private
|
63
93
|
|
64
94
|
def establish_session(conn)
|
65
|
-
session = GrpcKit::
|
95
|
+
session = GrpcKit::Session::ServerSession.new(GrpcKit::Session::IO.new(conn), self)
|
66
96
|
begin
|
67
97
|
@mutex.synchronize { @sessions << session }
|
68
98
|
yield(session)
|
@@ -5,10 +5,14 @@ require 'forwardable'
|
|
5
5
|
require 'grpc_kit/session/stream'
|
6
6
|
|
7
7
|
module GrpcKit
|
8
|
-
module
|
8
|
+
module Session
|
9
9
|
class ClientSession < DS9::Client
|
10
|
+
class ConnectionClosing < StandardError; end
|
11
|
+
|
10
12
|
extend Forwardable
|
11
13
|
|
14
|
+
MAX_STREAM_ID = 2**31 - 1
|
15
|
+
|
12
16
|
delegate %i[send_event recv_event] => :@io
|
13
17
|
|
14
18
|
# @params io [GrpcKit::Session::IO]
|
@@ -18,16 +22,24 @@ module GrpcKit
|
|
18
22
|
@io = io
|
19
23
|
@streams = {}
|
20
24
|
@opts = opts
|
25
|
+
@draining = false
|
26
|
+
@stop = false
|
27
|
+
@last_stream_id = 0
|
21
28
|
end
|
22
29
|
|
23
30
|
def send_request(data, headers)
|
24
|
-
|
31
|
+
if @draining
|
32
|
+
raise ConnectionClosing, "You can't send new request. becuase this connection will shuting down"
|
33
|
+
end
|
34
|
+
|
35
|
+
stream_id = submit_request(headers, data).to_i
|
25
36
|
stream = GrpcKit::Session::Stream.new(stream_id: stream_id, send_data: data)
|
26
37
|
stream.stream_id = stream_id
|
27
38
|
@streams[stream_id] = stream
|
28
39
|
stream
|
29
40
|
end
|
30
41
|
|
42
|
+
# @params stream_id [Integer]
|
31
43
|
def start(stream_id)
|
32
44
|
stream = @streams.fetch(stream_id)
|
33
45
|
|
@@ -38,13 +50,18 @@ module GrpcKit
|
|
38
50
|
|
39
51
|
run_once
|
40
52
|
end
|
41
|
-
rescue Errno::ECONNRESET, IOError
|
42
|
-
|
53
|
+
rescue Errno::ECONNRESET, IOError => e
|
54
|
+
GrpcKit.logger.debug(e.message)
|
55
|
+
shutdown
|
43
56
|
end
|
44
57
|
|
45
58
|
def run_once
|
46
59
|
return if @stop
|
47
60
|
|
61
|
+
if @draining && @drain_time < Time.now
|
62
|
+
raise 'trasport is closing'
|
63
|
+
end
|
64
|
+
|
48
65
|
if want_read?
|
49
66
|
do_read
|
50
67
|
end
|
@@ -56,13 +73,18 @@ module GrpcKit
|
|
56
73
|
|
57
74
|
private
|
58
75
|
|
76
|
+
def shutdown
|
77
|
+
@stop = true
|
78
|
+
@io.close
|
79
|
+
end
|
80
|
+
|
59
81
|
def do_read
|
60
82
|
receive
|
61
83
|
rescue IOError => e
|
62
|
-
|
84
|
+
shutdown
|
63
85
|
raise e
|
64
86
|
rescue DS9::Exception => e
|
65
|
-
|
87
|
+
shutdown
|
66
88
|
if DS9::ERR_EOF == e.code
|
67
89
|
@peer_shutdowned = true
|
68
90
|
return
|
@@ -93,9 +115,8 @@ module GrpcKit
|
|
93
115
|
if frame.end_stream?
|
94
116
|
stream.close_remote
|
95
117
|
end
|
96
|
-
|
97
|
-
|
98
|
-
# when DS9::Frames::RstStream
|
118
|
+
when DS9::Frames::Goaway
|
119
|
+
handle_goaway(frame)
|
99
120
|
end
|
100
121
|
|
101
122
|
true
|
@@ -154,6 +175,25 @@ module GrpcKit
|
|
154
175
|
# # for nghttp2_session_callbacks_set_on_invalid_frame_recv_callback
|
155
176
|
# def on_invalid_frame_recv(frame, error_code)
|
156
177
|
# end
|
178
|
+
|
179
|
+
def handle_goaway(frame)
|
180
|
+
# shutdown notice
|
181
|
+
last_stream_id = frame.last_stream_id
|
182
|
+
if last_stream_id == MAX_STREAM_ID && frame.error_code == DS9::NO_ERROR
|
183
|
+
@draining = true
|
184
|
+
@drain_time = Time.now + 10 # XXX
|
185
|
+
@streams.each_value(&:drain)
|
186
|
+
end
|
187
|
+
|
188
|
+
@last_stream_id = last_stream_id
|
189
|
+
@streams.each do |id, stream|
|
190
|
+
if id > last_stream_id
|
191
|
+
stream.close
|
192
|
+
end
|
193
|
+
end
|
194
|
+
|
195
|
+
shutdown if @streams.empty?
|
196
|
+
end
|
157
197
|
end
|
158
198
|
end
|
159
199
|
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'ds9'
|
4
|
+
|
5
|
+
module GrpcKit
|
6
|
+
module Session
|
7
|
+
class DrainController
|
8
|
+
def initialize
|
9
|
+
@sent_shutdown_notice = false
|
10
|
+
@goaway_sent = false
|
11
|
+
@after_one_rtt = false
|
12
|
+
# @sent_ping = false
|
13
|
+
end
|
14
|
+
|
15
|
+
def recv_ping_ack
|
16
|
+
@after_one_rtt = true
|
17
|
+
end
|
18
|
+
|
19
|
+
def call(session)
|
20
|
+
if @goaway_sent
|
21
|
+
# session.shutdown
|
22
|
+
elsif @sent_shutdown_notice && @after_one_rtt
|
23
|
+
session.submit_goaway(DS9::NO_ERROR, session.last_proc_stream_id)
|
24
|
+
@goaway_sent = true
|
25
|
+
# elsif @sent_shutdown_notice && !@after_one_rtt && !@sent_ping
|
26
|
+
# @sent_ping = true
|
27
|
+
elsif !@sent_shutdown_notice
|
28
|
+
session.submit_shutdown
|
29
|
+
@sent_shutdown_notice = true
|
30
|
+
session.submit_ping # wait for 1 RTT
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -23,10 +23,13 @@ module GrpcKit
|
|
23
23
|
'grpc-message',
|
24
24
|
'grpc-status',
|
25
25
|
'grpc-status-details-bin',
|
26
|
+
'grpc-accept-encoding',
|
26
27
|
'te'
|
27
28
|
].freeze
|
28
29
|
|
29
|
-
|
30
|
+
IGNORE_HEADERS = [':method', ':scheme'].freeze
|
31
|
+
|
32
|
+
METADATA_ACCEPTABLE_HEADER = %w[:authority user-agent].freeze
|
30
33
|
def initialize
|
31
34
|
super({}) # set metadata empty hash
|
32
35
|
end
|
@@ -38,8 +41,7 @@ module GrpcKit
|
|
38
41
|
when ':status'
|
39
42
|
self.http_status = Integer(val)
|
40
43
|
when 'content-type'
|
41
|
-
#
|
42
|
-
metadata[key] = val
|
44
|
+
# self.grpc_encoding = val
|
43
45
|
when 'grpc-encoding'
|
44
46
|
self.grpc_encoding = val
|
45
47
|
when 'grpc-status'
|
@@ -52,6 +54,10 @@ module GrpcKit
|
|
52
54
|
# TODO
|
53
55
|
GrpcKit.logger.warn('grpc-status-details-bin is unsupported header now')
|
54
56
|
else
|
57
|
+
if IGNORE_HEADERS.include?(key)
|
58
|
+
return
|
59
|
+
end
|
60
|
+
|
55
61
|
if RESERVED_HEADERS.include?(key) && !METADATA_ACCEPTABLE_HEADER.include?(key)
|
56
62
|
return
|
57
63
|
end
|
@@ -3,11 +3,12 @@
|
|
3
3
|
require 'ds9'
|
4
4
|
require 'forwardable'
|
5
5
|
require 'grpc_kit/session/stream'
|
6
|
-
require 'grpc_kit/
|
7
|
-
require 'grpc_kit/
|
6
|
+
require 'grpc_kit/session/drain_controller'
|
7
|
+
require 'grpc_kit/stream/server_stream'
|
8
|
+
require 'grpc_kit/transport/server_transport'
|
8
9
|
|
9
10
|
module GrpcKit
|
10
|
-
module
|
11
|
+
module Session
|
11
12
|
class ServerSession < DS9::Server
|
12
13
|
extend Forwardable
|
13
14
|
|
@@ -24,11 +25,14 @@ module GrpcKit
|
|
24
25
|
@dispatcher = dispatcher
|
25
26
|
@peer_shutdowned = false
|
26
27
|
@inflights = []
|
28
|
+
@drain = nil
|
27
29
|
end
|
28
30
|
|
29
31
|
def start
|
30
32
|
@io.wait_readable
|
31
33
|
loop do
|
34
|
+
break if @stop
|
35
|
+
|
32
36
|
invoke
|
33
37
|
|
34
38
|
if !want_read? && !want_write?
|
@@ -41,12 +45,23 @@ module GrpcKit
|
|
41
45
|
end
|
42
46
|
rescue Errno::ECONNRESET, IOError => e
|
43
47
|
GrpcKit.logger.debug(e.message)
|
44
|
-
|
48
|
+
shutdown
|
49
|
+
ensure
|
50
|
+
GrpcKit.logger.debug('Finish server session')
|
45
51
|
end
|
46
52
|
|
47
53
|
def run_once
|
48
54
|
return if @stop
|
49
55
|
|
56
|
+
if @drain
|
57
|
+
if @streams.empty?
|
58
|
+
shutdown
|
59
|
+
return
|
60
|
+
end
|
61
|
+
|
62
|
+
@drain.call(self)
|
63
|
+
end
|
64
|
+
|
50
65
|
if want_read?
|
51
66
|
do_read
|
52
67
|
end
|
@@ -57,16 +72,14 @@ module GrpcKit
|
|
57
72
|
end
|
58
73
|
|
59
74
|
def drain
|
60
|
-
|
61
|
-
@streams.each do |s|
|
62
|
-
GrpcKit.logger.debug("#{s.stream_id} is draining")
|
63
|
-
s.drain
|
64
|
-
end
|
75
|
+
@drain ||= GrpcKit::Session::DrainController.new
|
65
76
|
end
|
66
77
|
|
67
|
-
def
|
78
|
+
def shutdown
|
68
79
|
stop
|
69
80
|
@io.close
|
81
|
+
rescue StandardError => e
|
82
|
+
GrpcKit.logger.debug(e)
|
70
83
|
end
|
71
84
|
|
72
85
|
private
|
@@ -77,8 +90,8 @@ module GrpcKit
|
|
77
90
|
|
78
91
|
def invoke
|
79
92
|
while (stream = @inflights.pop)
|
80
|
-
t = GrpcKit::
|
81
|
-
th = GrpcKit::
|
93
|
+
t = GrpcKit::Transport::ServerTransport.new(self, stream)
|
94
|
+
th = GrpcKit::Stream::ServerStream.new(t)
|
82
95
|
@dispatcher.dispatch(stream.headers.path, th)
|
83
96
|
end
|
84
97
|
end
|
@@ -86,10 +99,10 @@ module GrpcKit
|
|
86
99
|
def do_read
|
87
100
|
receive
|
88
101
|
rescue IOError => e
|
89
|
-
|
102
|
+
shutdown
|
90
103
|
raise e
|
91
104
|
rescue DS9::Exception => e
|
92
|
-
|
105
|
+
shutdown
|
93
106
|
if DS9::ERR_EOF == e.code
|
94
107
|
@peer_shutdowned = true
|
95
108
|
return
|
@@ -136,7 +149,15 @@ module GrpcKit
|
|
136
149
|
if frame.end_stream?
|
137
150
|
stream.close_remote
|
138
151
|
end
|
139
|
-
|
152
|
+
when DS9::Frames::Ping
|
153
|
+
if frame.ping_ack?
|
154
|
+
GrpcKit.logger.debug('ping ack is received')
|
155
|
+
# nghttp2 can't send any data once server sent actaul GoAway(not shutdown notice) frame.
|
156
|
+
# We want to send data in this case when ClientStreamer or BidiBstreamer which they are sending data in same stream
|
157
|
+
# So we have to wait to send actual GoAway frame untill timeout or something
|
158
|
+
|
159
|
+
# @drain.recv_ping_ack if @drain
|
160
|
+
end
|
140
161
|
# when DS9::Frames::Goaway
|
141
162
|
# when DS9::Frames::RstStream
|
142
163
|
end
|
@@ -192,9 +213,13 @@ module GrpcKit
|
|
192
213
|
def on_stream_close(stream_id, error_code)
|
193
214
|
GrpcKit.logger.debug("on_stream_close stream_id=#{stream_id}, error_code=#{error_code}")
|
194
215
|
stream = @streams.delete(stream_id)
|
195
|
-
|
216
|
+
stream.close if stream
|
196
217
|
|
197
|
-
|
218
|
+
if @drain
|
219
|
+
if @streams.empty?
|
220
|
+
shutdown
|
221
|
+
end
|
222
|
+
end
|
198
223
|
end
|
199
224
|
|
200
225
|
# nghttp2_session_callbacks_set_on_data_chunk_recv_callback
|
@@ -3,9 +3,9 @@
|
|
3
3
|
require 'grpc_kit/status_codes'
|
4
4
|
|
5
5
|
module GrpcKit
|
6
|
-
module
|
6
|
+
module Stream
|
7
7
|
class ClientStream
|
8
|
-
# @params transport [GrpcKit::
|
8
|
+
# @params transport [GrpcKit::Transport::ClientTransport]
|
9
9
|
# @params config [GrpcKit::MethodConfig]
|
10
10
|
# @params authority [String]
|
11
11
|
def initialize(transport, config, authority:, timeout: nil)
|
@@ -15,7 +15,7 @@ module GrpcKit
|
|
15
15
|
@authority = authority
|
16
16
|
@timeout = timeout
|
17
17
|
|
18
|
-
@
|
18
|
+
@started = false
|
19
19
|
end
|
20
20
|
|
21
21
|
def send_msg(data, metadata: {}, timeout: nil, last: false)
|
@@ -31,15 +31,10 @@ module GrpcKit
|
|
31
31
|
raise GrpcKit::Errors::ResourceExhausted, "Sending message is too large: send=#{req.bytesize}, max=#{limit_size}"
|
32
32
|
end
|
33
33
|
|
34
|
-
if @
|
35
|
-
# unless metadata.empty?
|
36
|
-
# raise 'You can attach metadata at first send_msg' # XXX
|
37
|
-
# end
|
34
|
+
if @started
|
38
35
|
@transport.write_data(buf, last: last)
|
39
36
|
else
|
40
|
-
|
41
|
-
@transport.send_request(buf, headers, last: last)
|
42
|
-
@sent_first_msg = true
|
37
|
+
start_request(buf, metadata: metadata, last: last)
|
43
38
|
end
|
44
39
|
end
|
45
40
|
|
@@ -59,7 +54,6 @@ module GrpcKit
|
|
59
54
|
validate_if_request_start!
|
60
55
|
|
61
56
|
@transport.close_and_flush
|
62
|
-
check_status!
|
63
57
|
|
64
58
|
data = []
|
65
59
|
loop { data.push(do_recv) }
|
@@ -69,7 +63,7 @@ module GrpcKit
|
|
69
63
|
private
|
70
64
|
|
71
65
|
def validate_if_request_start!
|
72
|
-
unless @
|
66
|
+
unless @started
|
73
67
|
raise 'You should call `send_msg` method to send data'
|
74
68
|
end
|
75
69
|
end
|
@@ -80,6 +74,8 @@ module GrpcKit
|
|
80
74
|
if data.nil?
|
81
75
|
check_status!
|
82
76
|
raise StopIteration
|
77
|
+
elsif last
|
78
|
+
check_status!
|
83
79
|
end
|
84
80
|
|
85
81
|
compressed, size, buf = *data
|
@@ -107,39 +103,47 @@ module GrpcKit
|
|
107
103
|
end
|
108
104
|
|
109
105
|
def check_status!
|
110
|
-
|
111
|
-
|
112
|
-
if headers.grpc_status != GrpcKit::StatusCodes::OK
|
113
|
-
raise GrpcKit::Errors.from_status_code(headers.grpc_status, headers.status_message)
|
106
|
+
if status.code != GrpcKit::StatusCodes::OK
|
107
|
+
raise GrpcKit::Errors.from_status_code(status.code, status.msg)
|
114
108
|
else
|
115
109
|
GrpcKit.logger.debug('request is success')
|
116
110
|
end
|
117
111
|
end
|
118
112
|
|
119
|
-
|
120
|
-
|
113
|
+
Status = Struct.new(:code, :msg, :metadata)
|
114
|
+
|
115
|
+
def status
|
116
|
+
@status ||=
|
117
|
+
begin
|
118
|
+
headers = @transport.recv_headers
|
119
|
+
Status.new(headers.grpc_status, headers.status_message, headers.metadata)
|
120
|
+
end
|
121
|
+
end
|
122
|
+
|
123
|
+
def start_request(buf = nil, last: nil, metadata: {}, timeout: @timeout, authority: @authority)
|
121
124
|
hdrs = {
|
122
125
|
':method' => 'POST',
|
123
126
|
':scheme' => 'http',
|
124
127
|
':path' => @config.path,
|
125
|
-
':authority' =>
|
126
|
-
'grpc-timeout' =>
|
128
|
+
':authority' => authority,
|
129
|
+
'grpc-timeout' => timeout,
|
127
130
|
'te' => 'trailers',
|
128
131
|
'content-type' => 'application/grpc',
|
129
132
|
'user-agent' => "grpc-ruby/#{GrpcKit::VERSION} (grpc_kit)",
|
130
133
|
'grpc-accept-encoding' => 'identity,deflate,gzip',
|
131
|
-
}
|
134
|
+
}
|
132
135
|
|
133
136
|
metadata.each do |k, v|
|
134
137
|
if k.start_with?('grpc-')
|
135
138
|
# https://github.com/grpc/grpc/blob/ffac9d90b18cb076b1c952faa55ce4e049cbc9a6/doc/PROTOCOL-HTTP2.md
|
136
|
-
GrpcKit.logger.info("metadata name wich starts with 'grpc-' is reserved for future GRPC")
|
139
|
+
GrpcKit.logger.info("metadata name wich starts with 'grpc-' is reserved for future GRPC metadata")
|
137
140
|
else
|
138
141
|
hdrs[k] = v
|
139
142
|
end
|
140
143
|
end
|
141
144
|
|
142
|
-
hdrs.compact
|
145
|
+
@transport.start_request(buf, hdrs.compact, last: last)
|
146
|
+
@started = true
|
143
147
|
end
|
144
148
|
end
|
145
149
|
end
|
@@ -3,12 +3,12 @@
|
|
3
3
|
require 'grpc_kit/status_codes'
|
4
4
|
|
5
5
|
module GrpcKit
|
6
|
-
module
|
6
|
+
module Stream
|
7
7
|
class ServerStream
|
8
8
|
# @params transport [GrpcKit::transports::ServerTransport]
|
9
9
|
def initialize(transport)
|
10
10
|
@transport = transport
|
11
|
-
@
|
11
|
+
@started = false
|
12
12
|
end
|
13
13
|
|
14
14
|
def invoke(rpc)
|
@@ -21,11 +21,7 @@ module GrpcKit
|
|
21
21
|
send_status(status: GrpcKit::StatusCodes::UNKNOWN, msg: e.message, metadata: {})
|
22
22
|
end
|
23
23
|
|
24
|
-
def send_msg(data, protobuf, last: false, limit_size: nil)
|
25
|
-
if last
|
26
|
-
send_trailer # TODO: pass trailer metadata
|
27
|
-
end
|
28
|
-
|
24
|
+
def send_msg(data, protobuf, last: false, limit_size: nil, initial_metadata: {}, trailing_metadata: {})
|
29
25
|
buf =
|
30
26
|
begin
|
31
27
|
protobuf.encode(data)
|
@@ -37,11 +33,13 @@ module GrpcKit
|
|
37
33
|
raise GrpcKit::Errors::ResourceExhausted, "Sending message is too large: send=#{req.bytesize}, max=#{limit_size}"
|
38
34
|
end
|
39
35
|
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
36
|
+
if last
|
37
|
+
send_status(data: buf, metadata: trailing_metadata)
|
38
|
+
elsif @started
|
39
|
+
@transport.write_data(buf)
|
40
|
+
else
|
41
|
+
start_response(buf, metadata: initial_metadata)
|
42
|
+
end
|
45
43
|
end
|
46
44
|
|
47
45
|
def recv_msg(protobuf, last: false, limit_size: nil)
|
@@ -68,7 +66,7 @@ module GrpcKit
|
|
68
66
|
begin
|
69
67
|
protobuf.decode(buf)
|
70
68
|
rescue ArgumentError => e
|
71
|
-
raise GrpcKit::Errors::Internal, "Error while decoding in
|
69
|
+
raise GrpcKit::Errors::Internal, "Error while decoding in server: #{e}"
|
72
70
|
end
|
73
71
|
end
|
74
72
|
|
@@ -76,29 +74,31 @@ module GrpcKit
|
|
76
74
|
loop { yield(recv) }
|
77
75
|
end
|
78
76
|
|
79
|
-
def send_status(status: GrpcKit::StatusCodes::
|
80
|
-
|
81
|
-
|
77
|
+
def send_status(data: nil, status: GrpcKit::StatusCodes::OK, msg: nil, metadata: {})
|
78
|
+
@transport.write_data(data, last: true) if data
|
79
|
+
write_trailers(status, msg, metadata)
|
82
80
|
|
83
|
-
|
84
|
-
@sent_first_msg = true
|
81
|
+
start_response unless @started
|
85
82
|
end
|
86
83
|
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
end
|
84
|
+
private
|
85
|
+
|
86
|
+
def start_response(data = nil, metadata: {})
|
87
|
+
h = { ':status' => '200', 'content-type' => 'application/grpc' }
|
88
|
+
h['accept-encoding'] = 'identity'
|
93
89
|
|
94
|
-
@transport.
|
90
|
+
@transport.write_data(data) if data
|
91
|
+
@transport.start_response(h.merge(metadata))
|
92
|
+
@started = true
|
95
93
|
end
|
96
94
|
|
97
|
-
def
|
98
|
-
|
99
|
-
|
95
|
+
def write_trailers(status, msg, metadata)
|
96
|
+
trailers = { 'grpc-status' => status.to_s }
|
97
|
+
if msg
|
98
|
+
trailers['grpc-message'] = msg
|
99
|
+
end
|
100
100
|
|
101
|
-
@transport.
|
101
|
+
@transport.write_trailers(trailers.merge(metadata))
|
102
102
|
end
|
103
103
|
end
|
104
104
|
end
|
@@ -4,18 +4,18 @@ require 'grpc_kit/transport/packable'
|
|
4
4
|
require 'grpc_kit/transport/send_buffer'
|
5
5
|
|
6
6
|
module GrpcKit
|
7
|
-
module
|
7
|
+
module Transport
|
8
8
|
class ClientTransport
|
9
9
|
include GrpcKit::Transport::Packable
|
10
10
|
|
11
|
-
# @params session [GrpcKit::Session::
|
11
|
+
# @params session [GrpcKit::Session::ClientSession]
|
12
12
|
def initialize(session)
|
13
13
|
@session = session
|
14
14
|
@stream = nil # set later
|
15
15
|
@deferred = false
|
16
16
|
end
|
17
17
|
|
18
|
-
def
|
18
|
+
def start_request(data, header, last: false)
|
19
19
|
@stream = @session.send_request(GrpcKit::Transport::SendBuffer.new, header)
|
20
20
|
write_data(data, last: last)
|
21
21
|
end
|
@@ -3,11 +3,11 @@
|
|
3
3
|
require 'grpc_kit/transport/packable'
|
4
4
|
|
5
5
|
module GrpcKit
|
6
|
-
module
|
6
|
+
module Transport
|
7
7
|
class ServerTransport
|
8
8
|
include GrpcKit::Transport::Packable
|
9
9
|
|
10
|
-
# @params session [GrpcKit::
|
10
|
+
# @params session [GrpcKit::Session::ServerSession]
|
11
11
|
# @params stream [GrpcKit::Session::Stream]
|
12
12
|
def initialize(session, stream)
|
13
13
|
@session = session
|
@@ -23,7 +23,7 @@ module GrpcKit
|
|
23
23
|
end
|
24
24
|
end
|
25
25
|
|
26
|
-
def
|
26
|
+
def start_response(headers)
|
27
27
|
@session.submit_response(@stream.stream_id, headers)
|
28
28
|
end
|
29
29
|
|
@@ -35,7 +35,7 @@ module GrpcKit
|
|
35
35
|
unpack(read(last: last))
|
36
36
|
end
|
37
37
|
|
38
|
-
def
|
38
|
+
def write_trailers(trailer)
|
39
39
|
@stream.write_trailers_data(trailer)
|
40
40
|
@stream.end_write
|
41
41
|
end
|
data/lib/grpc_kit/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: grpc_kit
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.5
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- ganmacs
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2018-
|
11
|
+
date: 2018-11-02 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: ds9
|
@@ -16,14 +16,14 @@ dependencies:
|
|
16
16
|
requirements:
|
17
17
|
- - "~>"
|
18
18
|
- !ruby/object:Gem::Version
|
19
|
-
version: 1.2.
|
19
|
+
version: 1.2.1
|
20
20
|
type: :runtime
|
21
21
|
prerelease: false
|
22
22
|
version_requirements: !ruby/object:Gem::Requirement
|
23
23
|
requirements:
|
24
24
|
- - "~>"
|
25
25
|
- !ruby/object:Gem::Version
|
26
|
-
version: 1.2.
|
26
|
+
version: 1.2.1
|
27
27
|
- !ruby/object:Gem::Dependency
|
28
28
|
name: google-protobuf
|
29
29
|
requirement: !ruby/object:Gem::Requirement
|
@@ -208,19 +208,20 @@ files:
|
|
208
208
|
- lib/grpc_kit/rpcs/server_server_streamer.rb
|
209
209
|
- lib/grpc_kit/server.rb
|
210
210
|
- lib/grpc_kit/session/buffer.rb
|
211
|
+
- lib/grpc_kit/session/client_session.rb
|
212
|
+
- lib/grpc_kit/session/drain_controller.rb
|
211
213
|
- lib/grpc_kit/session/headers.rb
|
212
214
|
- lib/grpc_kit/session/io.rb
|
215
|
+
- lib/grpc_kit/session/server_session.rb
|
213
216
|
- lib/grpc_kit/session/stream.rb
|
214
217
|
- lib/grpc_kit/session/stream_status.rb
|
215
|
-
- lib/grpc_kit/sessions/client_session.rb
|
216
|
-
- lib/grpc_kit/sessions/server_session.rb
|
217
218
|
- lib/grpc_kit/status_codes.rb
|
218
|
-
- lib/grpc_kit/
|
219
|
-
- lib/grpc_kit/
|
219
|
+
- lib/grpc_kit/stream/client_stream.rb
|
220
|
+
- lib/grpc_kit/stream/server_stream.rb
|
221
|
+
- lib/grpc_kit/transport/client_transport.rb
|
220
222
|
- lib/grpc_kit/transport/packable.rb
|
221
223
|
- lib/grpc_kit/transport/send_buffer.rb
|
222
|
-
- lib/grpc_kit/
|
223
|
-
- lib/grpc_kit/transports/server_transport.rb
|
224
|
+
- lib/grpc_kit/transport/server_transport.rb
|
224
225
|
- lib/grpc_kit/version.rb
|
225
226
|
homepage: https://github.com/ganmacs/grpc_kit
|
226
227
|
licenses:
|