puma 3.5.2 → 3.6.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of puma might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/History.txt +16 -0
- data/ext/puma_http11/mini_ssl.c +5 -0
- data/lib/puma/binder.rb +1 -3
- data/lib/puma/cli.rb +1 -1
- data/lib/puma/client.rb +112 -2
- data/lib/puma/cluster.rb +3 -1
- data/lib/puma/const.rb +8 -2
- data/lib/puma/detect.rb +1 -1
- data/lib/puma/launcher.rb +10 -1
- data/lib/puma/minissl.rb +12 -0
- data/lib/puma/plugin.rb +12 -1
- data/lib/puma/runner.rb +4 -0
- data/lib/puma/server.rb +20 -1
- data/lib/puma/single.rb +3 -0
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 59a23e7e6ba37bf306a2ae94c314daa0abf2f592
|
4
|
+
data.tar.gz: c9228af1cebabc34902fd222965a4c851efd84e0
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 91433445f3ec432dfe5dd29361c06d8726e6c253351d2a66906442329edc6fe7e6b4dc47f120786a7a1adc11aae6b650ce7f0f6e829f63979ee8aa738d33e0ca
|
7
|
+
data.tar.gz: 2aea9f4334fdf09dd1ff5ff8b6a71a61ad0ef5527f3e08d98a73b17cf940d85c56e5bae6221ea4ddc09d8b12cc368359227462b3fc93a372da0327041300c397
|
data/History.txt
CHANGED
@@ -1,3 +1,19 @@
|
|
1
|
+
=== 3.6.0 / 2016-07-24
|
2
|
+
|
3
|
+
* 12 bug fixes:
|
4
|
+
* Add ability to detect a shutting down server. Fixes #932
|
5
|
+
* Add support for Expect: 100-continue. Fixes #519
|
6
|
+
* Check SSLContext better. Fixes #828
|
7
|
+
* Clarify behavior of '-t <num>'. Fixes #984
|
8
|
+
* Don't default to VERIFY_PEER. Fixes #1028
|
9
|
+
* Don't use ENV['PWD'] on windows. Fixes #1023
|
10
|
+
* Enlarge the scope of catching app exceptions. Fixes #1027
|
11
|
+
* Execute background hooks after daemonizing. Fixes #925
|
12
|
+
* Handle HUP as a stop unless there is IO redirection. Fixes #911
|
13
|
+
* Implement chunked request handling. Fixes #620
|
14
|
+
* Just rescue exception to return a 500. Fixes #1027
|
15
|
+
* Redirect IO in the jruby daemon mode. Fixes #778
|
16
|
+
|
1
17
|
=== 3.5.2 / 2016-07-20
|
2
18
|
|
3
19
|
* 1 bug fix:
|
data/ext/puma_http11/mini_ssl.c
CHANGED
@@ -134,9 +134,13 @@ VALUE engine_init_server(VALUE self, VALUE mini_ssl_ctx) {
|
|
134
134
|
ID sym_key = rb_intern("key");
|
135
135
|
VALUE key = rb_funcall(mini_ssl_ctx, sym_key, 0);
|
136
136
|
|
137
|
+
StringValue(key);
|
138
|
+
|
137
139
|
ID sym_cert = rb_intern("cert");
|
138
140
|
VALUE cert = rb_funcall(mini_ssl_ctx, sym_cert, 0);
|
139
141
|
|
142
|
+
StringValue(cert);
|
143
|
+
|
140
144
|
ID sym_ca = rb_intern("ca");
|
141
145
|
VALUE ca = rb_funcall(mini_ssl_ctx, sym_ca, 0);
|
142
146
|
|
@@ -150,6 +154,7 @@ VALUE engine_init_server(VALUE self, VALUE mini_ssl_ctx) {
|
|
150
154
|
SSL_CTX_use_PrivateKey_file(ctx, RSTRING_PTR(key), SSL_FILETYPE_PEM);
|
151
155
|
|
152
156
|
if (!NIL_P(ca)) {
|
157
|
+
StringValue(ca);
|
153
158
|
SSL_CTX_load_verify_locations(ctx, RSTRING_PTR(ca), NULL);
|
154
159
|
}
|
155
160
|
|
data/lib/puma/binder.rb
CHANGED
@@ -181,7 +181,7 @@ module Puma
|
|
181
181
|
ctx.ca = params['ca'] if params['ca']
|
182
182
|
end
|
183
183
|
|
184
|
-
if
|
184
|
+
if params['verify_mode']
|
185
185
|
ctx.verify_mode = case params['verify_mode']
|
186
186
|
when "peer"
|
187
187
|
MiniSSL::VERIFY_PEER
|
@@ -193,8 +193,6 @@ module Puma
|
|
193
193
|
@events.error "Please specify a valid verify_mode="
|
194
194
|
MiniSSL::VERIFY_NONE
|
195
195
|
end
|
196
|
-
else
|
197
|
-
ctx.verify_mode = MiniSSL::VERIFY_PEER
|
198
196
|
end
|
199
197
|
|
200
198
|
if fd = @inherited_fds.delete(str)
|
data/lib/puma/cli.rb
CHANGED
data/lib/puma/client.rb
CHANGED
@@ -8,6 +8,7 @@ end
|
|
8
8
|
|
9
9
|
require 'puma/detect'
|
10
10
|
require 'puma/delegation'
|
11
|
+
require 'tempfile'
|
11
12
|
|
12
13
|
if Puma::IS_JRUBY
|
13
14
|
# We have to work around some OpenSSL buffer/io-readiness bugs
|
@@ -117,9 +118,116 @@ module Puma
|
|
117
118
|
# no body share this one object since it has no state.
|
118
119
|
EmptyBody = NullIO.new
|
119
120
|
|
121
|
+
def setup_chunked_body(body)
|
122
|
+
@chunked_body = true
|
123
|
+
@partial_part_left = 0
|
124
|
+
@prev_chunk = ""
|
125
|
+
|
126
|
+
@body = Tempfile.new(Const::PUMA_TMP_BASE)
|
127
|
+
@body.binmode
|
128
|
+
@tempfile = @body
|
129
|
+
|
130
|
+
return decode_chunk(body)
|
131
|
+
end
|
132
|
+
|
133
|
+
def decode_chunk(chunk)
|
134
|
+
if @partial_part_left > 0
|
135
|
+
if @partial_part_left <= chunk.size
|
136
|
+
@body << chunk[0..(@partial_part_left-3)] # skip the \r\n
|
137
|
+
chunk = chunk[@partial_part_left..-1]
|
138
|
+
else
|
139
|
+
@body << chunk
|
140
|
+
@partial_part_left -= chunk.size
|
141
|
+
return false
|
142
|
+
end
|
143
|
+
end
|
144
|
+
|
145
|
+
if @prev_chunk.empty?
|
146
|
+
io = StringIO.new(chunk)
|
147
|
+
else
|
148
|
+
io = StringIO.new(@prev_chunk+chunk)
|
149
|
+
@prev_chunk = ""
|
150
|
+
end
|
151
|
+
|
152
|
+
while !io.eof?
|
153
|
+
line = io.gets
|
154
|
+
if line.end_with?("\r\n")
|
155
|
+
len = line.strip.to_i(16)
|
156
|
+
if len == 0
|
157
|
+
@body.rewind
|
158
|
+
@buffer = nil
|
159
|
+
@requests_served += 1
|
160
|
+
@ready = true
|
161
|
+
return true
|
162
|
+
end
|
163
|
+
|
164
|
+
len += 2
|
165
|
+
|
166
|
+
part = io.read(len)
|
167
|
+
|
168
|
+
unless part
|
169
|
+
@partial_part_left = len
|
170
|
+
next
|
171
|
+
end
|
172
|
+
|
173
|
+
got = part.size
|
174
|
+
|
175
|
+
case
|
176
|
+
when got == len
|
177
|
+
@body << part[0..-3] # to skip the ending \r\n
|
178
|
+
when got <= len - 2
|
179
|
+
@body << part
|
180
|
+
@partial_part_left = len - part.size
|
181
|
+
when got == len - 1 # edge where we get just \r but not \n
|
182
|
+
@body << part[0..-2]
|
183
|
+
@partial_part_left = len - part.size
|
184
|
+
end
|
185
|
+
else
|
186
|
+
@prev_chunk = line
|
187
|
+
return false
|
188
|
+
end
|
189
|
+
end
|
190
|
+
|
191
|
+
return false
|
192
|
+
end
|
193
|
+
|
194
|
+
def read_chunked_body
|
195
|
+
while true
|
196
|
+
begin
|
197
|
+
chunk = @io.read_nonblock(4096)
|
198
|
+
rescue Errno::EAGAIN
|
199
|
+
return false
|
200
|
+
rescue SystemCallError, IOError
|
201
|
+
raise ConnectionError, "Connection error detected during read"
|
202
|
+
end
|
203
|
+
|
204
|
+
# No chunk means a closed socket
|
205
|
+
unless chunk
|
206
|
+
@body.close
|
207
|
+
@buffer = nil
|
208
|
+
@requests_served += 1
|
209
|
+
@ready = true
|
210
|
+
raise EOFError
|
211
|
+
end
|
212
|
+
|
213
|
+
return true if decode_chunk(chunk)
|
214
|
+
end
|
215
|
+
end
|
216
|
+
|
120
217
|
def setup_body
|
121
218
|
@in_data_phase = true
|
219
|
+
@read_header = false
|
220
|
+
|
122
221
|
body = @parser.body
|
222
|
+
|
223
|
+
te = @env[TRANSFER_ENCODING2]
|
224
|
+
|
225
|
+
if te == CHUNKED
|
226
|
+
return setup_chunked_body(body)
|
227
|
+
end
|
228
|
+
|
229
|
+
@chunked_body = false
|
230
|
+
|
123
231
|
cl = @env[CONTENT_LENGTH]
|
124
232
|
|
125
233
|
unless cl
|
@@ -154,8 +262,6 @@ module Puma
|
|
154
262
|
|
155
263
|
@body_remain = remain
|
156
264
|
|
157
|
-
@read_header = false
|
158
|
-
|
159
265
|
return false
|
160
266
|
end
|
161
267
|
|
@@ -246,6 +352,10 @@ module Puma
|
|
246
352
|
end
|
247
353
|
|
248
354
|
def read_body
|
355
|
+
if @chunked_body
|
356
|
+
return read_chunked_body
|
357
|
+
end
|
358
|
+
|
249
359
|
# Read an odd sized chunk so we can read even sized ones
|
250
360
|
# after this
|
251
361
|
remain = @body_remain
|
data/lib/puma/cluster.rb
CHANGED
@@ -413,10 +413,12 @@ module Puma
|
|
413
413
|
|
414
414
|
redirect_io
|
415
415
|
|
416
|
-
|
416
|
+
Plugins.fire_background
|
417
417
|
|
418
418
|
@launcher.write_state
|
419
419
|
|
420
|
+
start_control
|
421
|
+
|
420
422
|
@master_read, @worker_write = read, @wakeup
|
421
423
|
|
422
424
|
@launcher.config.run_hooks :before_fork, nil
|
data/lib/puma/const.rb
CHANGED
@@ -100,8 +100,8 @@ module Puma
|
|
100
100
|
# too taxing on performance.
|
101
101
|
module Const
|
102
102
|
|
103
|
-
PUMA_VERSION = VERSION = "3.
|
104
|
-
CODE_NAME = "
|
103
|
+
PUMA_VERSION = VERSION = "3.6.0".freeze
|
104
|
+
CODE_NAME = "Sleepy Sunday Serenity".freeze
|
105
105
|
PUMA_SERVER_STRING = ['puma', PUMA_VERSION, CODE_NAME].join(' ').freeze
|
106
106
|
|
107
107
|
FAST_TRACK_KA_TIMEOUT = 0.2
|
@@ -219,7 +219,10 @@ module Puma
|
|
219
219
|
|
220
220
|
HTTP_VERSION = "HTTP_VERSION".freeze
|
221
221
|
HTTP_CONNECTION = "HTTP_CONNECTION".freeze
|
222
|
+
HTTP_EXPECT = "HTTP_EXPECT".freeze
|
223
|
+
CONTINUE = "100-continue".freeze
|
222
224
|
|
225
|
+
HTTP_11_100 = "HTTP/1.1 100 Continue\r\n\r\n".freeze
|
223
226
|
HTTP_11_200 = "HTTP/1.1 200 OK\r\n".freeze
|
224
227
|
HTTP_10_200 = "HTTP/1.0 200 OK\r\n".freeze
|
225
228
|
|
@@ -229,6 +232,7 @@ module Puma
|
|
229
232
|
CONTENT_LENGTH2 = "content-length".freeze
|
230
233
|
CONTENT_LENGTH_S = "Content-Length: ".freeze
|
231
234
|
TRANSFER_ENCODING = "transfer-encoding".freeze
|
235
|
+
TRANSFER_ENCODING2 = "HTTP_TRANSFER_ENCODING".freeze
|
232
236
|
|
233
237
|
CONNECTION_CLOSE = "Connection: close\r\n".freeze
|
234
238
|
CONNECTION_KEEP_ALIVE = "Connection: Keep-Alive\r\n".freeze
|
@@ -236,6 +240,8 @@ module Puma
|
|
236
240
|
TRANSFER_ENCODING_CHUNKED = "Transfer-Encoding: chunked\r\n".freeze
|
237
241
|
CLOSE_CHUNKED = "0\r\n\r\n".freeze
|
238
242
|
|
243
|
+
CHUNKED = "chunked".freeze
|
244
|
+
|
239
245
|
COLON = ": ".freeze
|
240
246
|
|
241
247
|
NEWLINE = "\n".freeze
|
data/lib/puma/detect.rb
CHANGED
data/lib/puma/launcher.rb
CHANGED
@@ -316,6 +316,11 @@ module Puma
|
|
316
316
|
if dir = @options[:directory]
|
317
317
|
@restart_dir = dir
|
318
318
|
|
319
|
+
elsif Puma.windows?
|
320
|
+
# I guess the value of PWD is garbage on windows so don't bother
|
321
|
+
# using it.
|
322
|
+
@restart_dir = Dir.pwd
|
323
|
+
|
319
324
|
# Use the same trick as unicorn, namely favor PWD because
|
320
325
|
# it will contain an unresolved symlink, useful for when
|
321
326
|
# the pwd is /data/releases/current.
|
@@ -382,7 +387,11 @@ module Puma
|
|
382
387
|
|
383
388
|
begin
|
384
389
|
Signal.trap "SIGHUP" do
|
385
|
-
@runner.
|
390
|
+
if @runner.redirected_io?
|
391
|
+
@runner.redirect_io
|
392
|
+
else
|
393
|
+
stop
|
394
|
+
end
|
386
395
|
end
|
387
396
|
rescue Exception
|
388
397
|
log "*** SIGHUP not implemented, signal based logs reopening unavailable!"
|
data/lib/puma/minissl.rb
CHANGED
@@ -118,6 +118,11 @@ module Puma
|
|
118
118
|
raise ArgumentError, "No such keystore file '#{keystore}'" unless File.exist? keystore
|
119
119
|
@keystore = keystore
|
120
120
|
end
|
121
|
+
|
122
|
+
def check
|
123
|
+
raise "Keystore not configured" unless @keystore
|
124
|
+
end
|
125
|
+
|
121
126
|
else
|
122
127
|
# non-jruby Context properties
|
123
128
|
attr_reader :key
|
@@ -138,6 +143,11 @@ module Puma
|
|
138
143
|
raise ArgumentError, "No such ca file '#{ca}'" unless File.exist? ca
|
139
144
|
@ca = ca
|
140
145
|
end
|
146
|
+
|
147
|
+
def check
|
148
|
+
raise "Key not configured" unless @key
|
149
|
+
raise "Cert not configured" unless @cert
|
150
|
+
end
|
141
151
|
end
|
142
152
|
end
|
143
153
|
|
@@ -156,6 +166,7 @@ module Puma
|
|
156
166
|
end
|
157
167
|
|
158
168
|
def accept
|
169
|
+
@ctx.check
|
159
170
|
io = @socket.accept
|
160
171
|
engine = Engine.server @ctx
|
161
172
|
|
@@ -163,6 +174,7 @@ module Puma
|
|
163
174
|
end
|
164
175
|
|
165
176
|
def accept_nonblock
|
177
|
+
@ctx.check
|
166
178
|
io = @socket.accept_nonblock
|
167
179
|
engine = Engine.server @ctx
|
168
180
|
|
data/lib/puma/plugin.rb
CHANGED
@@ -28,6 +28,7 @@ module Puma
|
|
28
28
|
class PluginRegistry
|
29
29
|
def initialize
|
30
30
|
@plugins = {}
|
31
|
+
@background = []
|
31
32
|
end
|
32
33
|
|
33
34
|
def register(name, cls)
|
@@ -53,6 +54,16 @@ module Puma
|
|
53
54
|
|
54
55
|
raise UnknownPlugin, "file failed to register a plugin"
|
55
56
|
end
|
57
|
+
|
58
|
+
def add_background(blk)
|
59
|
+
@background << blk
|
60
|
+
end
|
61
|
+
|
62
|
+
def fire_background
|
63
|
+
@background.each do |b|
|
64
|
+
Thread.new(&b)
|
65
|
+
end
|
66
|
+
end
|
56
67
|
end
|
57
68
|
|
58
69
|
Plugins = PluginRegistry.new
|
@@ -93,7 +104,7 @@ module Puma
|
|
93
104
|
end
|
94
105
|
|
95
106
|
def in_background(&blk)
|
96
|
-
|
107
|
+
Plugins.add_background blk
|
97
108
|
end
|
98
109
|
|
99
110
|
def workers_supported?
|
data/lib/puma/runner.rb
CHANGED
data/lib/puma/server.rb
CHANGED
@@ -242,6 +242,10 @@ module Puma
|
|
242
242
|
@thread_pool = ThreadPool.new(@min_threads,
|
243
243
|
@max_threads,
|
244
244
|
IOBuffer) do |client, buffer|
|
245
|
+
|
246
|
+
# Advertise this server into the thread
|
247
|
+
Thread.current[ThreadLocalKey] = self
|
248
|
+
|
245
249
|
process_now = false
|
246
250
|
|
247
251
|
begin
|
@@ -399,6 +403,11 @@ module Puma
|
|
399
403
|
#
|
400
404
|
def process_client(client, buffer)
|
401
405
|
begin
|
406
|
+
|
407
|
+
if client.env[HTTP_EXPECT] == CONTINUE
|
408
|
+
client.io << HTTP_11_100
|
409
|
+
end
|
410
|
+
|
402
411
|
clean_thread_locals = @options[:clean_thread_locals]
|
403
412
|
close_socket = true
|
404
413
|
|
@@ -587,7 +596,7 @@ module Puma
|
|
587
596
|
headers = {}
|
588
597
|
res_body = ["Request was internally terminated early\n"]
|
589
598
|
|
590
|
-
rescue
|
599
|
+
rescue Exception => e
|
591
600
|
@events.unknown_error self, e, "Rack app", env
|
592
601
|
|
593
602
|
status, headers, res_body = lowlevel_error(e, env)
|
@@ -911,5 +920,15 @@ module Puma
|
|
911
920
|
end
|
912
921
|
end
|
913
922
|
private :fast_write
|
923
|
+
|
924
|
+
ThreadLocalKey = :puma_server
|
925
|
+
|
926
|
+
def self.current
|
927
|
+
Thread.current[ThreadLocalKey]
|
928
|
+
end
|
929
|
+
|
930
|
+
def shutting_down?
|
931
|
+
@status == :stop || @status == :restart
|
932
|
+
end
|
914
933
|
end
|
915
934
|
end
|
data/lib/puma/single.rb
CHANGED
@@ -44,6 +44,7 @@ module Puma
|
|
44
44
|
if JRubyRestart.daemon?
|
45
45
|
# load and bind before redirecting IO so errors show up on stdout/stderr
|
46
46
|
load_and_bind
|
47
|
+
redirect_io
|
47
48
|
end
|
48
49
|
|
49
50
|
already_daemon = JRubyRestart.daemon_init
|
@@ -84,6 +85,8 @@ module Puma
|
|
84
85
|
load_and_bind
|
85
86
|
end
|
86
87
|
|
88
|
+
Plugins.fire_background
|
89
|
+
|
87
90
|
@launcher.write_state
|
88
91
|
|
89
92
|
start_control
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: puma
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.
|
4
|
+
version: 3.6.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Evan Phoenix
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-07-
|
11
|
+
date: 2016-07-25 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rdoc
|