jun-puma 1.0.1-java → 1.0.2-java

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.
Files changed (81) hide show
  1. checksums.yaml +4 -4
  2. data/lib/puma/puma_http11.jar +0 -0
  3. metadata +3 -81
  4. data/bin/puma-wild +0 -25
  5. data/docs/architecture.md +0 -74
  6. data/docs/compile_options.md +0 -55
  7. data/docs/deployment.md +0 -102
  8. data/docs/fork_worker.md +0 -31
  9. data/docs/images/puma-connection-flow-no-reactor.png +0 -0
  10. data/docs/images/puma-connection-flow.png +0 -0
  11. data/docs/images/puma-general-arch.png +0 -0
  12. data/docs/jungle/README.md +0 -9
  13. data/docs/jungle/rc.d/README.md +0 -74
  14. data/docs/jungle/rc.d/puma +0 -61
  15. data/docs/jungle/rc.d/puma.conf +0 -10
  16. data/docs/kubernetes.md +0 -78
  17. data/docs/nginx.md +0 -80
  18. data/docs/plugins.md +0 -38
  19. data/docs/rails_dev_mode.md +0 -28
  20. data/docs/restart.md +0 -64
  21. data/docs/signals.md +0 -98
  22. data/docs/stats.md +0 -142
  23. data/docs/systemd.md +0 -244
  24. data/docs/testing_benchmarks_local_files.md +0 -150
  25. data/docs/testing_test_rackup_ci_files.md +0 -36
  26. data/ext/puma_http11/PumaHttp11Service.java +0 -17
  27. data/ext/puma_http11/ext_help.h +0 -15
  28. data/ext/puma_http11/http11_parser.c +0 -1057
  29. data/ext/puma_http11/http11_parser.h +0 -65
  30. data/ext/puma_http11/http11_parser.java.rl +0 -145
  31. data/ext/puma_http11/http11_parser.rl +0 -149
  32. data/ext/puma_http11/http11_parser_common.rl +0 -54
  33. data/ext/puma_http11/mini_ssl.c +0 -832
  34. data/ext/puma_http11/no_ssl/PumaHttp11Service.java +0 -15
  35. data/ext/puma_http11/org/jruby/puma/Http11.java +0 -226
  36. data/ext/puma_http11/org/jruby/puma/Http11Parser.java +0 -455
  37. data/ext/puma_http11/org/jruby/puma/MiniSSL.java +0 -508
  38. data/ext/puma_http11/puma_http11.c +0 -492
  39. data/lib/puma/app/status.rb +0 -96
  40. data/lib/puma/binder.rb +0 -501
  41. data/lib/puma/cli.rb +0 -243
  42. data/lib/puma/client.rb +0 -632
  43. data/lib/puma/cluster/worker.rb +0 -182
  44. data/lib/puma/cluster/worker_handle.rb +0 -97
  45. data/lib/puma/cluster.rb +0 -562
  46. data/lib/puma/commonlogger.rb +0 -115
  47. data/lib/puma/configuration.rb +0 -391
  48. data/lib/puma/const.rb +0 -289
  49. data/lib/puma/control_cli.rb +0 -316
  50. data/lib/puma/detect.rb +0 -45
  51. data/lib/puma/dsl.rb +0 -1204
  52. data/lib/puma/error_logger.rb +0 -113
  53. data/lib/puma/events.rb +0 -57
  54. data/lib/puma/io_buffer.rb +0 -46
  55. data/lib/puma/jruby_restart.rb +0 -27
  56. data/lib/puma/json_serialization.rb +0 -96
  57. data/lib/puma/launcher/bundle_pruner.rb +0 -104
  58. data/lib/puma/launcher.rb +0 -484
  59. data/lib/puma/log_writer.rb +0 -147
  60. data/lib/puma/minissl/context_builder.rb +0 -95
  61. data/lib/puma/minissl.rb +0 -458
  62. data/lib/puma/null_io.rb +0 -61
  63. data/lib/puma/plugin/systemd.rb +0 -90
  64. data/lib/puma/plugin/tmp_restart.rb +0 -36
  65. data/lib/puma/plugin.rb +0 -111
  66. data/lib/puma/rack/builder.rb +0 -297
  67. data/lib/puma/rack/urlmap.rb +0 -93
  68. data/lib/puma/rack_default.rb +0 -24
  69. data/lib/puma/reactor.rb +0 -125
  70. data/lib/puma/request.rb +0 -671
  71. data/lib/puma/runner.rb +0 -213
  72. data/lib/puma/sd_notify.rb +0 -149
  73. data/lib/puma/server.rb +0 -664
  74. data/lib/puma/single.rb +0 -69
  75. data/lib/puma/state_file.rb +0 -68
  76. data/lib/puma/thread_pool.rb +0 -434
  77. data/lib/puma/util.rb +0 -141
  78. data/lib/puma.rb +0 -78
  79. data/lib/rack/handler/puma.rb +0 -141
  80. data/tools/Dockerfile +0 -16
  81. data/tools/trickletest.rb +0 -44
data/lib/puma/server.rb DELETED
@@ -1,664 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require 'stringio'
4
-
5
- require_relative 'thread_pool'
6
- require_relative 'const'
7
- require_relative 'log_writer'
8
- require_relative 'events'
9
- require_relative 'null_io'
10
- require_relative 'reactor'
11
- require_relative 'client'
12
- require_relative 'binder'
13
- require_relative 'util'
14
- require_relative 'request'
15
-
16
- require 'socket'
17
- require 'io/wait' unless Puma::HAS_NATIVE_IO_WAIT
18
-
19
- module Puma
20
-
21
- # The HTTP Server itself. Serves out a single Rack app.
22
- #
23
- # This class is used by the `Puma::Single` and `Puma::Cluster` classes
24
- # to generate one or more `Puma::Server` instances capable of handling requests.
25
- # Each Puma process will contain one `Puma::Server` instance.
26
- #
27
- # The `Puma::Server` instance pulls requests from the socket, adds them to a
28
- # `Puma::Reactor` where they get eventually passed to a `Puma::ThreadPool`.
29
- #
30
- # Each `Puma::Server` will have one reactor and one thread pool.
31
- class Server
32
- include Puma::Const
33
- include Request
34
-
35
- attr_reader :thread
36
- attr_reader :log_writer
37
- attr_reader :events
38
- attr_reader :min_threads, :max_threads # for #stats
39
- attr_reader :requests_count # @version 5.0.0
40
- attr_reader :idle_timeout_reached
41
-
42
- # @todo the following may be deprecated in the future
43
- attr_reader :auto_trim_time, :early_hints, :first_data_timeout,
44
- :leak_stack_on_error,
45
- :persistent_timeout, :reaping_time
46
-
47
- attr_accessor :app
48
- attr_accessor :binder
49
-
50
- THREAD_LOCAL_KEY = :puma_server
51
-
52
- # Create a server for the rack app +app+.
53
- #
54
- # +log_writer+ is a Puma::LogWriter object used to log info and error messages.
55
- #
56
- # +events+ is a Puma::Events object used to notify application status events.
57
- #
58
- # Server#run returns a thread that you can join on to wait for the server
59
- # to do its work.
60
- #
61
- # @note Several instance variables exist so they are available for testing,
62
- # and have default values set via +fetch+. Normally the values are set via
63
- # `::Puma::Configuration.puma_default_options`.
64
- #
65
- # @note The `events` parameter is set to nil, and set to `Events.new` in code.
66
- # Often `options` needs to be passed, but `events` does not. Using nil allows
67
- # calling code to not require events.rb.
68
- #
69
- def initialize(app, events = nil, options = {})
70
- @app = app
71
- @events = events || Events.new
72
-
73
- @check, @notify = nil
74
- @status = :stop
75
-
76
- @thread = nil
77
- @thread_pool = nil
78
-
79
- @options = if options.is_a?(UserFileDefaultOptions)
80
- options
81
- else
82
- UserFileDefaultOptions.new(options, Configuration::DEFAULTS)
83
- end
84
-
85
- @log_writer = @options.fetch :log_writer, LogWriter.stdio
86
- @early_hints = @options[:early_hints]
87
- @first_data_timeout = @options[:first_data_timeout]
88
- @persistent_timeout = @options[:persistent_timeout]
89
- @idle_timeout = @options[:idle_timeout]
90
- @min_threads = @options[:min_threads]
91
- @max_threads = @options[:max_threads]
92
- @queue_requests = @options[:queue_requests]
93
- @max_fast_inline = @options[:max_fast_inline]
94
- @io_selector_backend = @options[:io_selector_backend]
95
- @http_content_length_limit = @options[:http_content_length_limit]
96
-
97
- # make this a hash, since we prefer `key?` over `include?`
98
- @supported_http_methods =
99
- if @options[:supported_http_methods] == :any
100
- :any
101
- else
102
- if (ary = @options[:supported_http_methods])
103
- ary
104
- else
105
- SUPPORTED_HTTP_METHODS
106
- end.sort.product([nil]).to_h.freeze
107
- end
108
-
109
- temp = !!(@options[:environment] =~ /\A(development|test)\z/)
110
- @leak_stack_on_error = @options[:environment] ? temp : true
111
-
112
- @binder = Binder.new(log_writer)
113
-
114
- ENV['RACK_ENV'] ||= "development"
115
-
116
- @mode = :http
117
-
118
- @precheck_closing = true
119
-
120
- @requests_count = 0
121
-
122
- @idle_timeout_reached = false
123
- end
124
-
125
- def inherit_binder(bind)
126
- @binder = bind
127
- end
128
-
129
- class << self
130
- # @!attribute [r] current
131
- def current
132
- Thread.current[THREAD_LOCAL_KEY]
133
- end
134
-
135
- # :nodoc:
136
- # @version 5.0.0
137
- def tcp_cork_supported?
138
- Socket.const_defined?(:TCP_CORK) && Socket.const_defined?(:IPPROTO_TCP)
139
- end
140
-
141
- # :nodoc:
142
- # @version 5.0.0
143
- def closed_socket_supported?
144
- Socket.const_defined?(:TCP_INFO) && Socket.const_defined?(:IPPROTO_TCP)
145
- end
146
- private :tcp_cork_supported?
147
- private :closed_socket_supported?
148
- end
149
-
150
- # On Linux, use TCP_CORK to better control how the TCP stack
151
- # packetizes our stream. This improves both latency and throughput.
152
- # socket parameter may be an MiniSSL::Socket, so use to_io
153
- #
154
- if tcp_cork_supported?
155
- # 6 == Socket::IPPROTO_TCP
156
- # 3 == TCP_CORK
157
- # 1/0 == turn on/off
158
- def cork_socket(socket)
159
- skt = socket.to_io
160
- begin
161
- skt.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_CORK, 1) if skt.kind_of? TCPSocket
162
- rescue IOError, SystemCallError
163
- Puma::Util.purge_interrupt_queue
164
- end
165
- end
166
-
167
- def uncork_socket(socket)
168
- skt = socket.to_io
169
- begin
170
- skt.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_CORK, 0) if skt.kind_of? TCPSocket
171
- rescue IOError, SystemCallError
172
- Puma::Util.purge_interrupt_queue
173
- end
174
- end
175
- else
176
- def cork_socket(socket)
177
- end
178
-
179
- def uncork_socket(socket)
180
- end
181
- end
182
-
183
- if closed_socket_supported?
184
- UNPACK_TCP_STATE_FROM_TCP_INFO = "C".freeze
185
-
186
- def closed_socket?(socket)
187
- skt = socket.to_io
188
- return false unless skt.kind_of?(TCPSocket) && @precheck_closing
189
-
190
- begin
191
- tcp_info = skt.getsockopt(Socket::IPPROTO_TCP, Socket::TCP_INFO)
192
- rescue IOError, SystemCallError
193
- Puma::Util.purge_interrupt_queue
194
- @precheck_closing = false
195
- false
196
- else
197
- state = tcp_info.unpack(UNPACK_TCP_STATE_FROM_TCP_INFO)[0]
198
- # TIME_WAIT: 6, CLOSE: 7, CLOSE_WAIT: 8, LAST_ACK: 9, CLOSING: 11
199
- (state >= 6 && state <= 9) || state == 11
200
- end
201
- end
202
- else
203
- def closed_socket?(socket)
204
- false
205
- end
206
- end
207
-
208
- # @!attribute [r] backlog
209
- def backlog
210
- @thread_pool&.backlog
211
- end
212
-
213
- # @!attribute [r] running
214
- def running
215
- @thread_pool&.spawned
216
- end
217
-
218
-
219
- # This number represents the number of requests that
220
- # the server is capable of taking right now.
221
- #
222
- # For example if the number is 5 then it means
223
- # there are 5 threads sitting idle ready to take
224
- # a request. If one request comes in, then the
225
- # value would be 4 until it finishes processing.
226
- # @!attribute [r] pool_capacity
227
- def pool_capacity
228
- @thread_pool&.pool_capacity
229
- end
230
-
231
- # Runs the server.
232
- #
233
- # If +background+ is true (the default) then a thread is spun
234
- # up in the background to handle requests. Otherwise requests
235
- # are handled synchronously.
236
- #
237
- def run(background=true, thread_name: 'srv')
238
- BasicSocket.do_not_reverse_lookup = true
239
-
240
- @events.fire :state, :booting
241
-
242
- @status = :run
243
-
244
- @thread_pool = ThreadPool.new(thread_name, @options) { |client| process_client client }
245
-
246
- if @queue_requests
247
- @reactor = Reactor.new(@io_selector_backend) { |c| reactor_wakeup c }
248
- @reactor.run
249
- end
250
-
251
-
252
- @thread_pool.auto_reap! if @options[:reaping_time]
253
- @thread_pool.auto_trim! if @options[:auto_trim_time]
254
-
255
- @check, @notify = Puma::Util.pipe unless @notify
256
-
257
- @events.fire :state, :running
258
-
259
- if background
260
- @thread = Thread.new do
261
- Puma.set_thread_name thread_name
262
- handle_servers
263
- end
264
- return @thread
265
- else
266
- handle_servers
267
- end
268
- end
269
-
270
- # This method is called from the Reactor thread when a queued Client receives data,
271
- # times out, or when the Reactor is shutting down.
272
- #
273
- # It is responsible for ensuring that a request has been completely received
274
- # before it starts to be processed by the ThreadPool. This may be known as read buffering.
275
- # If read buffering is not done, and no other read buffering is performed (such as by an application server
276
- # such as nginx) then the application would be subject to a slow client attack.
277
- #
278
- # For a graphical representation of how the request buffer works see [architecture.md](https://github.com/puma/puma/blob/master/docs/architecture.md#connection-pipeline).
279
- #
280
- # The method checks to see if it has the full header and body with
281
- # the `Puma::Client#try_to_finish` method. If the full request has been sent,
282
- # then the request is passed to the ThreadPool (`@thread_pool << client`)
283
- # so that a "worker thread" can pick up the request and begin to execute application logic.
284
- # The Client is then removed from the reactor (return `true`).
285
- #
286
- # If a client object times out, a 408 response is written, its connection is closed,
287
- # and the object is removed from the reactor (return `true`).
288
- #
289
- # If the Reactor is shutting down, all Clients are either timed out or passed to the
290
- # ThreadPool, depending on their current state (#can_close?).
291
- #
292
- # Otherwise, if the full request is not ready then the client will remain in the reactor
293
- # (return `false`). When the client sends more data to the socket the `Puma::Client` object
294
- # will wake up and again be checked to see if it's ready to be passed to the thread pool.
295
- def reactor_wakeup(client)
296
- shutdown = !@queue_requests
297
- if client.try_to_finish || (shutdown && !client.can_close?)
298
- @thread_pool << client
299
- elsif shutdown || client.timeout == 0
300
- client.timeout!
301
- else
302
- client.set_timeout(@first_data_timeout)
303
- false
304
- end
305
- rescue StandardError => e
306
- client_error(e, client)
307
- client.close
308
- true
309
- end
310
-
311
- def handle_servers
312
- begin
313
- check = @check
314
- sockets = [check] + @binder.ios
315
- pool = @thread_pool
316
- queue_requests = @queue_requests
317
- drain = @options[:drain_on_shutdown] ? 0 : nil
318
-
319
- addr_send_name, addr_value = case @options[:remote_address]
320
- when :value
321
- [:peerip=, @options[:remote_address_value]]
322
- when :header
323
- [:remote_addr_header=, @options[:remote_address_header]]
324
- when :proxy_protocol
325
- [:expect_proxy_proto=, @options[:remote_address_proxy_protocol]]
326
- else
327
- [nil, nil]
328
- end
329
-
330
- while @status == :run || (drain && shutting_down?)
331
- begin
332
- ios = IO.select sockets, nil, nil, (shutting_down? ? 0 : @idle_timeout)
333
- unless ios
334
- unless shutting_down?
335
- @idle_timeout_reached = true
336
- @status = :stop
337
- end
338
-
339
- break
340
- end
341
-
342
- ios.first.each do |sock|
343
- if sock == check
344
- break if handle_check
345
- else
346
- pool.wait_until_not_full
347
- pool.wait_for_less_busy_worker(@options[:wait_for_less_busy_worker])
348
-
349
- io = begin
350
- sock.accept_nonblock
351
- rescue IO::WaitReadable
352
- next
353
- end
354
- drain += 1 if shutting_down?
355
- pool << Client.new(io, @binder.env(sock)).tap { |c|
356
- c.listener = sock
357
- c.http_content_length_limit = @http_content_length_limit
358
- c.send(addr_send_name, addr_value) if addr_value
359
- }
360
- end
361
- end
362
- rescue IOError, Errno::EBADF
363
- # In the case that any of the sockets are unexpectedly close.
364
- raise
365
- rescue StandardError => e
366
- @log_writer.unknown_error e, nil, "Listen loop"
367
- end
368
- end
369
-
370
- @log_writer.debug "Drained #{drain} additional connections." if drain
371
- @events.fire :state, @status
372
-
373
- if queue_requests
374
- @queue_requests = false
375
- @reactor.shutdown
376
- end
377
-
378
- graceful_shutdown if @status == :stop || @status == :restart
379
- rescue Exception => e
380
- @log_writer.unknown_error e, nil, "Exception handling servers"
381
- ensure
382
- # Errno::EBADF is infrequently raised
383
- [@check, @notify].each do |io|
384
- begin
385
- io.close unless io.closed?
386
- rescue Errno::EBADF
387
- end
388
- end
389
- @notify = nil
390
- @check = nil
391
- end
392
-
393
- @events.fire :state, :done
394
- end
395
-
396
- # :nodoc:
397
- def handle_check
398
- cmd = @check.read(1)
399
-
400
- case cmd
401
- when STOP_COMMAND
402
- @status = :stop
403
- return true
404
- when HALT_COMMAND
405
- @status = :halt
406
- return true
407
- when RESTART_COMMAND
408
- @status = :restart
409
- return true
410
- end
411
-
412
- false
413
- end
414
-
415
- # Given a connection on +client+, handle the incoming requests,
416
- # or queue the connection in the Reactor if no request is available.
417
- #
418
- # This method is called from a ThreadPool worker thread.
419
- #
420
- # This method supports HTTP Keep-Alive so it may, depending on if the client
421
- # indicates that it supports keep alive, wait for another request before
422
- # returning.
423
- #
424
- # Return true if one or more requests were processed.
425
- def process_client(client)
426
- # Advertise this server into the thread
427
- Thread.current[THREAD_LOCAL_KEY] = self
428
-
429
- clean_thread_locals = @options[:clean_thread_locals]
430
- close_socket = true
431
-
432
- requests = 0
433
-
434
- begin
435
- if @queue_requests &&
436
- !client.eagerly_finish
437
-
438
- client.set_timeout(@first_data_timeout)
439
- if @reactor.add client
440
- close_socket = false
441
- return false
442
- end
443
- end
444
-
445
- with_force_shutdown(client) do
446
- client.finish(@first_data_timeout)
447
- end
448
-
449
- while true
450
- @requests_count += 1
451
- case handle_request(client, requests + 1)
452
- when false
453
- break
454
- when :async
455
- close_socket = false
456
- break
457
- when true
458
- ThreadPool.clean_thread_locals if clean_thread_locals
459
-
460
- requests += 1
461
-
462
- # As an optimization, try to read the next request from the
463
- # socket for a short time before returning to the reactor.
464
- fast_check = @status == :run
465
-
466
- # Always pass the client back to the reactor after a reasonable
467
- # number of inline requests if there are other requests pending.
468
- fast_check = false if requests >= @max_fast_inline &&
469
- @thread_pool.backlog > 0
470
-
471
- next_request_ready = with_force_shutdown(client) do
472
- client.reset(fast_check)
473
- end
474
-
475
- unless next_request_ready
476
- break unless @queue_requests
477
- client.set_timeout @persistent_timeout
478
- if @reactor.add client
479
- close_socket = false
480
- break
481
- end
482
- end
483
- end
484
- end
485
- true
486
- rescue StandardError => e
487
- client_error(e, client, requests)
488
- # The ensure tries to close +client+ down
489
- requests > 0
490
- ensure
491
- client.io_buffer.reset
492
-
493
- begin
494
- client.close if close_socket
495
- rescue IOError, SystemCallError
496
- Puma::Util.purge_interrupt_queue
497
- # Already closed
498
- rescue StandardError => e
499
- @log_writer.unknown_error e, nil, "Client"
500
- end
501
- end
502
- end
503
-
504
- # Triggers a client timeout if the thread-pool shuts down
505
- # during execution of the provided block.
506
- def with_force_shutdown(client, &block)
507
- @thread_pool.with_force_shutdown(&block)
508
- rescue ThreadPool::ForceShutdown
509
- client.timeout!
510
- end
511
-
512
- # :nocov:
513
-
514
- # Handle various error types thrown by Client I/O operations.
515
- def client_error(e, client, requests = 1)
516
- # Swallow, do not log
517
- return if [ConnectionError, EOFError].include?(e.class)
518
-
519
- case e
520
- when MiniSSL::SSLError
521
- lowlevel_error(e, client.env)
522
- @log_writer.ssl_error e, client.io
523
- when HttpParserError
524
- response_to_error(client, requests, e, 400)
525
- @log_writer.parse_error e, client
526
- when HttpParserError501
527
- response_to_error(client, requests, e, 501)
528
- @log_writer.parse_error e, client
529
- else
530
- response_to_error(client, requests, e, 500)
531
- @log_writer.unknown_error e, nil, "Read"
532
- end
533
- end
534
-
535
- # A fallback rack response if +@app+ raises as exception.
536
- #
537
- def lowlevel_error(e, env, status=500)
538
- if handler = @options[:lowlevel_error_handler]
539
- if handler.arity == 1
540
- return handler.call(e)
541
- elsif handler.arity == 2
542
- return handler.call(e, env)
543
- else
544
- return handler.call(e, env, status)
545
- end
546
- end
547
-
548
- if @leak_stack_on_error
549
- backtrace = e.backtrace.nil? ? '<no backtrace available>' : e.backtrace.join("\n")
550
- [status, {}, ["Puma caught this error: #{e.message} (#{e.class})\n#{backtrace}"]]
551
- else
552
- [status, {}, [""]]
553
- end
554
- end
555
-
556
- def response_to_error(client, requests, err, status_code)
557
- status, headers, res_body = lowlevel_error(err, client.env, status_code)
558
- prepare_response(status, headers, res_body, requests, client)
559
- client.write_error(status_code)
560
- end
561
- private :response_to_error
562
-
563
- # Wait for all outstanding requests to finish.
564
- #
565
- def graceful_shutdown
566
- if @options[:shutdown_debug]
567
- threads = Thread.list
568
- total = threads.size
569
-
570
- pid = Process.pid
571
-
572
- $stdout.syswrite "#{pid}: === Begin thread backtrace dump ===\n"
573
-
574
- threads.each_with_index do |t,i|
575
- $stdout.syswrite "#{pid}: Thread #{i+1}/#{total}: #{t.inspect}\n"
576
- $stdout.syswrite "#{pid}: #{t.backtrace.join("\n#{pid}: ")}\n\n"
577
- end
578
- $stdout.syswrite "#{pid}: === End thread backtrace dump ===\n"
579
- end
580
-
581
- if @status != :restart
582
- @binder.close
583
- end
584
-
585
- if @thread_pool
586
- if timeout = @options[:force_shutdown_after]
587
- @thread_pool.shutdown timeout.to_f
588
- else
589
- @thread_pool.shutdown
590
- end
591
- end
592
- end
593
-
594
- def notify_safely(message)
595
- @notify << message
596
- rescue IOError, NoMethodError, Errno::EPIPE, Errno::EBADF
597
- # The server, in another thread, is shutting down
598
- Puma::Util.purge_interrupt_queue
599
- rescue RuntimeError => e
600
- # Temporary workaround for https://bugs.ruby-lang.org/issues/13239
601
- if e.message.include?('IOError')
602
- Puma::Util.purge_interrupt_queue
603
- else
604
- raise e
605
- end
606
- end
607
- private :notify_safely
608
-
609
- # Stops the acceptor thread and then causes the worker threads to finish
610
- # off the request queue before finally exiting.
611
-
612
- def stop(sync=false)
613
- notify_safely(STOP_COMMAND)
614
- @thread.join if @thread && sync
615
- end
616
-
617
- def halt(sync=false)
618
- notify_safely(HALT_COMMAND)
619
- @thread.join if @thread && sync
620
- end
621
-
622
- def begin_restart(sync=false)
623
- notify_safely(RESTART_COMMAND)
624
- @thread.join if @thread && sync
625
- end
626
-
627
- def shutting_down?
628
- @status == :stop || @status == :restart
629
- end
630
-
631
- # List of methods invoked by #stats.
632
- # @version 5.0.0
633
- STAT_METHODS = [:backlog, :running, :pool_capacity, :max_threads, :requests_count].freeze
634
-
635
- # Returns a hash of stats about the running server for reporting purposes.
636
- # @version 5.0.0
637
- # @!attribute [r] stats
638
- def stats
639
- STAT_METHODS.map {|name| [name, send(name) || 0]}.to_h
640
- end
641
-
642
- # below are 'delegations' to binder
643
- # remove in Puma 7?
644
-
645
-
646
- def add_tcp_listener(host, port, optimize_for_latency = true, backlog = 1024)
647
- @binder.add_tcp_listener host, port, optimize_for_latency, backlog
648
- end
649
-
650
- def add_ssl_listener(host, port, ctx, optimize_for_latency = true,
651
- backlog = 1024)
652
- @binder.add_ssl_listener host, port, ctx, optimize_for_latency, backlog
653
- end
654
-
655
- def add_unix_listener(path, umask = nil, mode = nil, backlog = 1024)
656
- @binder.add_unix_listener path, umask, mode, backlog
657
- end
658
-
659
- # @!attribute [r] connected_ports
660
- def connected_ports
661
- @binder.connected_ports
662
- end
663
- end
664
- end