rhebok 0.2.3 → 0.8.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/Changes +4 -0
- data/README.md +1 -1
- data/ext/rhebok/rhebok.c +58 -6
- data/lib/rack/handler/rhebok.rb +59 -15
- data/lib/rhebok/buffered.rb +46 -0
- data/lib/rhebok/version.rb +1 -1
- data/test/spec_06_curl.rb +46 -0
- data/test/testrequest.rb +34 -1
- metadata +5 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 454acd81875129e8a6b70d0322faeded5a9b12ab
|
4
|
+
data.tar.gz: c2e879260c7505697b312f7ce07b4b91e137ccbb
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 0233481756e663f30ca815c7320e2bfc0bc88636a2577451dc8717c2e938c76fd68a71eec61c36da06e95d8f7ad985c8cb36fd566f6d92e6fc98191c0ff21066
|
7
|
+
data.tar.gz: a3297edf4bd16b7e331e7c068bb2bb0c1be641d145b9fca70c52b06a68599ce48488ea6d19b997eea69ece63aa46bb18be6ad1c5f625fd8b0a0bad4de993a78e
|
data/Changes
CHANGED
data/README.md
CHANGED
@@ -9,7 +9,7 @@ Rhebok supports following features.
|
|
9
9
|
- uses writev(2) for output responses
|
10
10
|
- prefork and graceful shutdown using [prefork_engine](https://rubygems.org/gems/prefork_engine)
|
11
11
|
- hot deploy using [start_server](https://metacpan.org/release/Server-Starter) ([here](https://github.com/lestrrat/go-server-starter) is golang version by lestrrat-san)
|
12
|
-
-
|
12
|
+
- supports HTTP/1.1. But does not have Keepalive
|
13
13
|
- supports OobGC
|
14
14
|
|
15
15
|
This server is suitable for running HTTP application servers behind a reverse proxy like nginx.
|
data/ext/rhebok/rhebok.c
CHANGED
@@ -18,6 +18,7 @@
|
|
18
18
|
#define MAX_HEADER_NAME_LEN 1024
|
19
19
|
#define MAX_HEADERS 128
|
20
20
|
#define BAD_REQUEST "HTTP/1.0 400 Bad Request\r\nConnection: close\r\n\r\n400 Bad Request\r\n"
|
21
|
+
#define READ_BUF 16384
|
21
22
|
#define TOU(ch) (('a' <= ch && ch <= 'z') ? ch - ('a' - 'A') : ch)
|
22
23
|
|
23
24
|
static const char *DoW[] = {
|
@@ -26,6 +27,8 @@ static const char *DoW[] = {
|
|
26
27
|
static const char *MoY[] = {
|
27
28
|
"Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"
|
28
29
|
};
|
30
|
+
static const char xdigit[16] = {'0','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f'};
|
31
|
+
|
29
32
|
|
30
33
|
/* stolen from HTTP::Status and Feersum */
|
31
34
|
/* Unmarked codes are from RFC 2616 */
|
@@ -377,6 +380,24 @@ void str_i(char * dst, int * dst_len, int src, int fig) {
|
|
377
380
|
*dst_len += fig;
|
378
381
|
}
|
379
382
|
|
383
|
+
static
|
384
|
+
int _chunked_header(char *buf, ssize_t len) {
|
385
|
+
int dlen = 0, i;
|
386
|
+
ssize_t l = len;
|
387
|
+
while ( l > 0 ) {
|
388
|
+
dlen++;
|
389
|
+
l /= 16;
|
390
|
+
}
|
391
|
+
i = dlen;
|
392
|
+
buf[i++] = 13;
|
393
|
+
buf[i++] = 10;
|
394
|
+
while ( len > 0 ) {
|
395
|
+
buf[--dlen] = xdigit[len % 16];
|
396
|
+
len /= 16;
|
397
|
+
}
|
398
|
+
return i;
|
399
|
+
}
|
400
|
+
|
380
401
|
static
|
381
402
|
int _date_line(char * date_line) {
|
382
403
|
struct tm gtm;
|
@@ -436,7 +457,7 @@ int _parse_http_request(char *buf, ssize_t buf_len, VALUE env) {
|
|
436
457
|
rb_hash_aset(env, request_method_key, rb_str_new(method,method_len));
|
437
458
|
rb_hash_aset(env, request_uri_key, rb_str_new(path, path_len));
|
438
459
|
rb_hash_aset(env, script_name_key, vacant_string_val);
|
439
|
-
rb_hash_aset(env, server_protocol_key, (minor_version
|
460
|
+
rb_hash_aset(env, server_protocol_key, (minor_version == 1) ? http11_val : http10_val);
|
440
461
|
|
441
462
|
/* PATH_INFO QUERY_STRING */
|
442
463
|
path_len = find_ch(path, path_len, '#'); /* strip off all text after # after storing request_uri */
|
@@ -582,6 +603,8 @@ VALUE rhe_read_timeout(VALUE self, VALUE filenov, VALUE rbuf, VALUE lenv, VALUE
|
|
582
603
|
timeout = NUM2DBL(timeoutv);
|
583
604
|
offset = NUM2LONG(offsetv);
|
584
605
|
len = NUM2LONG(lenv);
|
606
|
+
if ( len > READ_BUF )
|
607
|
+
len = READ_BUF;
|
585
608
|
d = ALLOC_N(char, len);
|
586
609
|
rv = _read_timeout(fileno, timeout, &d[offset], len);
|
587
610
|
if ( rv > 0 ) {
|
@@ -665,7 +688,7 @@ VALUE rhe_close(VALUE self, VALUE fileno) {
|
|
665
688
|
}
|
666
689
|
|
667
690
|
static
|
668
|
-
VALUE rhe_write_response(VALUE self, VALUE filenov, VALUE timeoutv, VALUE status_codev, VALUE headers, VALUE body) {
|
691
|
+
VALUE rhe_write_response(VALUE self, VALUE filenov, VALUE timeoutv, VALUE status_codev, VALUE headers, VALUE body, VALUE use_chunkedv) {
|
669
692
|
ssize_t hlen = 0;
|
670
693
|
ssize_t blen = 0;
|
671
694
|
|
@@ -687,12 +710,15 @@ VALUE rhe_write_response(VALUE self, VALUE filenov, VALUE timeoutv, VALUE status
|
|
687
710
|
const char * message;
|
688
711
|
|
689
712
|
const char * s;
|
690
|
-
char* d;
|
713
|
+
char * d;
|
691
714
|
ssize_t n;
|
692
715
|
|
716
|
+
char * chunked_header_buf;
|
717
|
+
|
693
718
|
int fileno = NUM2INT(filenov);
|
694
719
|
double timeout = NUM2DBL(timeoutv);
|
695
720
|
int status_code = NUM2INT(status_codev);
|
721
|
+
int use_chunked = NUM2INT(use_chunkedv);
|
696
722
|
|
697
723
|
harr = rb_ary_new();
|
698
724
|
RB_GC_GUARD(harr);
|
@@ -700,6 +726,9 @@ VALUE rhe_write_response(VALUE self, VALUE filenov, VALUE timeoutv, VALUE status
|
|
700
726
|
hlen = RARRAY_LEN(harr);
|
701
727
|
blen = RARRAY_LEN(body);
|
702
728
|
iovcnt = 10 + (hlen * 2) + blen;
|
729
|
+
if ( use_chunked )
|
730
|
+
iovcnt += blen*2;
|
731
|
+
chunked_header_buf = ALLOC_N(char, 32 * blen);
|
703
732
|
|
704
733
|
{
|
705
734
|
struct iovec v[iovcnt]; // Needs C99 compiler
|
@@ -713,7 +742,7 @@ VALUE rhe_write_response(VALUE self, VALUE filenov, VALUE timeoutv, VALUE status
|
|
713
742
|
status_line[i++] = '/';
|
714
743
|
status_line[i++] = '1';
|
715
744
|
status_line[i++] = '.';
|
716
|
-
status_line[i++] = '
|
745
|
+
status_line[i++] = '1';
|
717
746
|
status_line[i++] = ' ';
|
718
747
|
str_i(status_line,&i,status_code,3);
|
719
748
|
status_line[i++] = ' ';
|
@@ -790,15 +819,38 @@ VALUE rhe_write_response(VALUE self, VALUE filenov, VALUE timeoutv, VALUE status
|
|
790
819
|
v[1].iov_base = date_line;
|
791
820
|
}
|
792
821
|
|
822
|
+
if ( use_chunked ) {
|
823
|
+
v[iovcnt].iov_base = "Transfer-Encoding: chunked\r\n";
|
824
|
+
v[iovcnt].iov_len = sizeof("Transfer-Encoding: chunked\r\n") - 1;
|
825
|
+
iovcnt++;
|
826
|
+
}
|
827
|
+
|
793
828
|
v[iovcnt].iov_base = "Connection: close\r\n\r\n";
|
794
829
|
v[iovcnt].iov_len = sizeof("Connection: close\r\n\r\n") - 1;
|
795
830
|
iovcnt++;
|
796
831
|
|
832
|
+
ssize_t chb_offset = 0;
|
797
833
|
for ( i=0; i<blen; i++) {
|
798
834
|
val_obj = rb_ary_entry(body, i);
|
835
|
+
if ( use_chunked ) {
|
836
|
+
v[iovcnt].iov_len = _chunked_header(&chunked_header_buf[chb_offset],RSTRING_LEN(val_obj));
|
837
|
+
v[iovcnt].iov_base = &chunked_header_buf[chb_offset];
|
838
|
+
chb_offset += v[iovcnt].iov_len;
|
839
|
+
iovcnt++;
|
840
|
+
}
|
799
841
|
v[iovcnt].iov_base = RSTRING_PTR(val_obj);
|
800
842
|
v[iovcnt].iov_len = RSTRING_LEN(val_obj);
|
801
843
|
iovcnt++;
|
844
|
+
if ( use_chunked ) {
|
845
|
+
v[iovcnt].iov_base = "\r\n";
|
846
|
+
v[iovcnt].iov_len = sizeof("\r\n") -1;
|
847
|
+
iovcnt++;
|
848
|
+
}
|
849
|
+
}
|
850
|
+
if ( use_chunked ) {
|
851
|
+
v[iovcnt].iov_base = "0\r\n\r\n";
|
852
|
+
v[iovcnt].iov_len = sizeof("0\r\n\r\n") - 1;
|
853
|
+
iovcnt++;
|
802
854
|
}
|
803
855
|
|
804
856
|
vec_offset = 0;
|
@@ -824,7 +876,7 @@ VALUE rhe_write_response(VALUE self, VALUE filenov, VALUE timeoutv, VALUE status
|
|
824
876
|
}
|
825
877
|
}
|
826
878
|
}
|
827
|
-
|
879
|
+
xfree(chunked_header_buf);
|
828
880
|
if ( rv < 0 ) {
|
829
881
|
return Qnil;
|
830
882
|
}
|
@@ -880,5 +932,5 @@ void Init_rhebok()
|
|
880
932
|
rb_define_module_function(cRhebok, "write_timeout", rhe_write_timeout, 5);
|
881
933
|
rb_define_module_function(cRhebok, "write_all", rhe_write_all, 4);
|
882
934
|
rb_define_module_function(cRhebok, "close_rack", rhe_close, 1);
|
883
|
-
rb_define_module_function(cRhebok, "write_response", rhe_write_response,
|
935
|
+
rb_define_module_function(cRhebok, "write_response", rhe_write_response, 6);
|
884
936
|
}
|
data/lib/rack/handler/rhebok.rb
CHANGED
@@ -11,6 +11,7 @@ require 'io/nonblock'
|
|
11
11
|
require 'prefork_engine'
|
12
12
|
require 'rhebok'
|
13
13
|
require 'rhebok/config'
|
14
|
+
require 'rhebok/buffered'
|
14
15
|
|
15
16
|
$RACK_HANDLER_RHEBOK_GCTOOL = true
|
16
17
|
begin
|
@@ -238,16 +239,15 @@ module Rack
|
|
238
239
|
begin
|
239
240
|
proc_req_count += 1
|
240
241
|
@can_exit = false
|
242
|
+
# expect
|
243
|
+
if env.key?("HTTP_EXPECT") && env.delete("HTTP_EXPECT") == "100-continue"
|
244
|
+
::Rhebok.write_all(connection, "HTTP/1.1 100 Continue\015\012\015\012", 0, @options[:Timeout])
|
245
|
+
end
|
241
246
|
# handle request
|
247
|
+
is_chunked = env.key?("HTTP_TRANSFER_ENCODING") && env.delete("HTTP_TRANSFER_ENCODING") == 'chunked'
|
242
248
|
if env.key?("CONTENT_LENGTH") && env["CONTENT_LENGTH"].to_i > 0
|
243
249
|
cl = env["CONTENT_LENGTH"].to_i
|
244
|
-
|
245
|
-
buffer = Tempfile.open('r')
|
246
|
-
buffer.binmode
|
247
|
-
buffer.set_encoding('BINARY')
|
248
|
-
else
|
249
|
-
buffer = StringIO.new("").set_encoding('BINARY')
|
250
|
-
end
|
250
|
+
buffer = ::Rhebok::Buffered.new(cl,MAX_MEMORY_BUFFER_SIZE)
|
251
251
|
while cl > 0
|
252
252
|
chunk = ""
|
253
253
|
if buf.bytesize > 0
|
@@ -259,30 +259,74 @@ module Rack
|
|
259
259
|
return
|
260
260
|
end
|
261
261
|
end
|
262
|
-
buffer
|
262
|
+
buffer.print(chunk)
|
263
263
|
cl -= chunk.bytesize
|
264
264
|
end
|
265
|
-
buffer.rewind
|
266
|
-
|
265
|
+
env["rack.input"] = buffer.rewind
|
266
|
+
elsif is_chunked
|
267
|
+
buffer = ::Rhebok::Buffered.new(0,MAX_MEMORY_BUFFER_SIZE)
|
268
|
+
chunked_buffer = '';
|
269
|
+
complete = false
|
270
|
+
while !complete
|
271
|
+
chunk = ""
|
272
|
+
if buf.bytesize > 0
|
273
|
+
chunk = buf
|
274
|
+
buf = ""
|
275
|
+
else
|
276
|
+
readed = ::Rhebok.read_timeout(connection, chunk, 16384, 0, @options[:Timeout])
|
277
|
+
if readed == nil
|
278
|
+
return
|
279
|
+
end
|
280
|
+
end
|
281
|
+
chunked_buffer << chunk
|
282
|
+
while chunked_buffer.sub!(/^(([0-9a-fA-F]+).*\015\012)/,"") != nil
|
283
|
+
trailer = $1
|
284
|
+
chunked_len = $2.hex
|
285
|
+
if chunked_len == 0
|
286
|
+
complete = true
|
287
|
+
break
|
288
|
+
elsif chunked_buffer.bytesize < chunked_len + 2
|
289
|
+
chunked_buffer = trailer + chunked_buffer
|
290
|
+
break
|
291
|
+
end
|
292
|
+
buffer.print(chunked_buffer.byteslice(0,chunked_len))
|
293
|
+
chunked_buffer = chunked_buffer.byteslice(chunked_len,chunked_buffer.bytesize-chunked_len)
|
294
|
+
chunked_buffer.sub!(/^\015\012/,"")
|
295
|
+
end
|
296
|
+
break if complete
|
297
|
+
end
|
298
|
+
env["CONTENT_LENGTH"] = buffer.size.to_s
|
299
|
+
env["rack.input"] = buffer.rewind
|
267
300
|
end
|
268
301
|
|
269
302
|
status_code, headers, body = app.call(env)
|
303
|
+
|
304
|
+
use_chunked = env["SERVER_PROTOCOL"] != "HTTP/1.1" ||
|
305
|
+
headers.key?("Transfer-Encoding") ||
|
306
|
+
headers.key?("Content-Length") ? false : true
|
307
|
+
|
270
308
|
if body.instance_of?(Array)
|
271
|
-
::Rhebok.write_response(connection, @options[:Timeout], status_code.to_i, headers, body)
|
309
|
+
::Rhebok.write_response(connection, @options[:Timeout], status_code.to_i, headers, body, use_chunked ? 1 : 0)
|
272
310
|
else
|
273
|
-
::Rhebok.write_response(connection, @options[:Timeout], status_code.to_i, headers, [])
|
311
|
+
::Rhebok.write_response(connection, @options[:Timeout], status_code.to_i, headers, [], use_chunked ? 1 : 0)
|
274
312
|
body.each do |part|
|
275
|
-
ret =
|
313
|
+
ret = nil
|
314
|
+
if use_chunked
|
315
|
+
ret = ::Rhebok.write_all(connection, part.bytesize.to_s(16) + "\015\012" + part + "\015\012", 0, @options[:Timeout])
|
316
|
+
else
|
317
|
+
ret = ::Rhebok.write_all(connection, part, 0, @options[:Timeout])
|
318
|
+
end
|
276
319
|
if ret == nil
|
277
320
|
break
|
278
321
|
end
|
279
322
|
end #body.each
|
323
|
+
::Rhebok.write_all(connection, "0\015\012\015\012", 0, @options[:Timeout]) if use_chunked
|
280
324
|
body.respond_to?(:close) and body.close
|
281
325
|
end
|
282
326
|
#p [env,status_code,headers,body]
|
283
327
|
ensure
|
284
|
-
if buffer
|
285
|
-
buffer.close
|
328
|
+
if buffer != nil
|
329
|
+
buffer.close
|
286
330
|
end
|
287
331
|
::Rhebok.close_rack(connection)
|
288
332
|
# out of band gc
|
@@ -0,0 +1,46 @@
|
|
1
|
+
require 'stringio'
|
2
|
+
require 'tempfile'
|
3
|
+
|
4
|
+
class Rhebok
|
5
|
+
class Buffered
|
6
|
+
def initialize(length=0,memory_max=1048576)
|
7
|
+
@length = length
|
8
|
+
@memory_max = memory_max
|
9
|
+
@size = 0
|
10
|
+
if length > memory_max
|
11
|
+
@buffer = Tempfile.open('r')
|
12
|
+
@buffer.binmode
|
13
|
+
@buffer.set_encoding('BINARY')
|
14
|
+
else
|
15
|
+
@buffer = StringIO.new("").set_encoding('BINARY')
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
def print(buf)
|
20
|
+
if @size + buf.bytesize > @memory_max && @buffer.instance_of?(StringIO)
|
21
|
+
new_buffer = Tempfile.open('r')
|
22
|
+
new_buffer.binmode
|
23
|
+
new_buffer.set_encoding('BINARY')
|
24
|
+
new_buffer << @buffer.string
|
25
|
+
@buffer = new_buffer
|
26
|
+
end
|
27
|
+
@buffer << buf
|
28
|
+
@size += buf.bytesize
|
29
|
+
end
|
30
|
+
|
31
|
+
def size
|
32
|
+
@size
|
33
|
+
end
|
34
|
+
|
35
|
+
def rewind
|
36
|
+
@buffer.rewind
|
37
|
+
@buffer
|
38
|
+
end
|
39
|
+
|
40
|
+
def close
|
41
|
+
if @buffer.instance_of?(Tempfile)
|
42
|
+
@buffer.close!
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
data/lib/rhebok/version.rb
CHANGED
@@ -0,0 +1,46 @@
|
|
1
|
+
require 'rack'
|
2
|
+
require File.expand_path('../testrequest', __FILE__)
|
3
|
+
require 'timeout'
|
4
|
+
require 'socket'
|
5
|
+
require 'rack/handler/rhebok'
|
6
|
+
|
7
|
+
describe Rhebok do
|
8
|
+
extend TestRequest::Helpers
|
9
|
+
begin
|
10
|
+
|
11
|
+
@host = '127.0.0.1'
|
12
|
+
@port = 9202
|
13
|
+
#@app = Rack::Lint.new(TestRequest.new) Lint requires Content-Length or Transfer-Eoncoding
|
14
|
+
@app = TestRequest.new
|
15
|
+
@pid = fork
|
16
|
+
if @pid == nil
|
17
|
+
#child
|
18
|
+
Rack::Handler::Rhebok.run(@app, :Host=>'127.0.0.1', :Port=>9202, :MaxWorkers=>1,
|
19
|
+
:BeforeFork => proc { ENV["TEST_FOO"] = "FOO" },
|
20
|
+
:AfterFork => proc { ENV["TEST_BAR"] = "BAR" },
|
21
|
+
)
|
22
|
+
exit!(true)
|
23
|
+
end
|
24
|
+
|
25
|
+
command = 'curl --stderr - -sv -X POST -T "'+File.expand_path('../testrequest.rb', __FILE__)+'" -H "Content-type: text/plain" --header "Transfer-Encoding: chunked" http://127.0.0.1:9202/remove_length'
|
26
|
+
curl_command(command)
|
27
|
+
should "with curl" do
|
28
|
+
@request["Transfer-Encoding"].should.equal "chunked"
|
29
|
+
@request["Expect"].should.equal "100-continue"
|
30
|
+
@response.key?("Transfer-Encoding").should.equal false
|
31
|
+
@response["CONTENT_LENGTH"].should.equal File.stat(File.expand_path('../testrequest.rb', __FILE__)).size.to_s
|
32
|
+
@response["test.postdata"].bytesize.should.equal File.stat(File.expand_path('../testrequest.rb', __FILE__)).size
|
33
|
+
@header["Transfer-Encoding"].should.equal "chunked"
|
34
|
+
@header["Connection"].should.equal "close"
|
35
|
+
@header.key?("HTTP/1.1 100 Continue").should.equal true
|
36
|
+
end
|
37
|
+
|
38
|
+
ensure
|
39
|
+
sleep 1
|
40
|
+
if @pid != nil
|
41
|
+
Process.kill(:TERM, @pid)
|
42
|
+
Process.wait()
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
end
|
data/test/testrequest.rb
CHANGED
@@ -23,7 +23,10 @@ class TestRequest
|
|
23
23
|
ENV.has_key?("TEST_BAR") and minienv["TEST_BAR"] = ENV["TEST_BAR"]
|
24
24
|
body = minienv.to_yaml
|
25
25
|
size = body.respond_to?(:bytesize) ? body.bytesize : body.size
|
26
|
-
res_header = {"Content-
|
26
|
+
res_header = {"Content-Length" => size.to_s, "Content-Type" => "text/yaml", "X-Foo" => "Foo\nBar", "X-Bar"=>"Foo\n\nBar", "X-Baz"=>"\nBaz", "X-Fuga"=>"Fuga\n"}
|
27
|
+
if env["PATH_INFO"] =~ /remove_length/
|
28
|
+
res_header.delete("Content-Length")
|
29
|
+
end
|
27
30
|
[status, res_header.merge(test_header), [body]]
|
28
31
|
end
|
29
32
|
|
@@ -74,6 +77,36 @@ class TestRequest
|
|
74
77
|
}
|
75
78
|
}
|
76
79
|
end
|
80
|
+
|
81
|
+
def curl_command(command)
|
82
|
+
body = ""
|
83
|
+
header = {}
|
84
|
+
request = {}
|
85
|
+
open("|" + command) { |f|
|
86
|
+
while (line = f.gets)
|
87
|
+
next if line.match(/^(\*|}|{) /)
|
88
|
+
if line.match(/^> /)
|
89
|
+
line.sub!(/^> /,"")
|
90
|
+
line.gsub!(/[\r\n]/,"")
|
91
|
+
key,val = line.split(/: /,2)
|
92
|
+
request[key.to_s] = val.to_s
|
93
|
+
next
|
94
|
+
end
|
95
|
+
if line.match(/^< /)
|
96
|
+
line.sub!(/^< /,"")
|
97
|
+
line.gsub!(/[\r\n]/,"")
|
98
|
+
key,val = line.split(/: /,2)
|
99
|
+
header[key.to_s] = val.to_s
|
100
|
+
next
|
101
|
+
end
|
102
|
+
line.sub!(/\* Closing connection #0\n/,"")
|
103
|
+
body += line
|
104
|
+
end
|
105
|
+
}
|
106
|
+
@request = request
|
107
|
+
@response = YAML.load(body)
|
108
|
+
@header = header
|
109
|
+
end
|
77
110
|
end
|
78
111
|
end
|
79
112
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rhebok
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.8.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Masahiro Nagano
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-01-
|
11
|
+
date: 2015-01-22 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: bundler
|
@@ -109,6 +109,7 @@ files:
|
|
109
109
|
- ext/rhebok/rhebok.c
|
110
110
|
- lib/rack/handler/rhebok.rb
|
111
111
|
- lib/rhebok.rb
|
112
|
+
- lib/rhebok/buffered.rb
|
112
113
|
- lib/rhebok/config.rb
|
113
114
|
- lib/rhebok/version.rb
|
114
115
|
- rhebok.gemspec
|
@@ -117,6 +118,7 @@ files:
|
|
117
118
|
- test/spec_03_unix.rb
|
118
119
|
- test/spec_04_hook.rb
|
119
120
|
- test/spec_05_config.rb
|
121
|
+
- test/spec_06_curl.rb
|
120
122
|
- test/testconfig.rb
|
121
123
|
- test/testrequest.rb
|
122
124
|
homepage: https://github.com/kazeburo/rhebok
|
@@ -149,5 +151,6 @@ test_files:
|
|
149
151
|
- test/spec_03_unix.rb
|
150
152
|
- test/spec_04_hook.rb
|
151
153
|
- test/spec_05_config.rb
|
154
|
+
- test/spec_06_curl.rb
|
152
155
|
- test/testconfig.rb
|
153
156
|
- test/testrequest.rb
|