puma 2.7.0 → 3.1.1
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 +5 -13
- data/DEPLOYMENT.md +91 -0
- data/Gemfile +3 -2
- data/History.txt +624 -1
- data/Manifest.txt +15 -3
- data/README.md +129 -14
- data/Rakefile +3 -3
- data/bin/puma-wild +31 -0
- data/bin/pumactl +1 -1
- data/docs/nginx.md +1 -1
- data/docs/signals.md +43 -0
- data/ext/puma_http11/extconf.rb +7 -2
- data/ext/puma_http11/http11_parser.java.rl +5 -5
- data/ext/puma_http11/io_buffer.c +1 -1
- data/ext/puma_http11/mini_ssl.c +233 -18
- data/ext/puma_http11/org/jruby/puma/Http11.java +12 -3
- data/ext/puma_http11/org/jruby/puma/Http11Parser.java +39 -39
- data/ext/puma_http11/org/jruby/puma/MiniSSL.java +245 -195
- data/ext/puma_http11/puma_http11.c +12 -4
- data/lib/puma.rb +1 -0
- data/lib/puma/app/status.rb +7 -0
- data/lib/puma/binder.rb +108 -39
- data/lib/puma/capistrano.rb +23 -6
- data/lib/puma/cli.rb +141 -446
- data/lib/puma/client.rb +48 -1
- data/lib/puma/cluster.rb +207 -58
- data/lib/puma/commonlogger.rb +107 -0
- data/lib/puma/configuration.rb +262 -235
- data/lib/puma/const.rb +97 -14
- data/lib/puma/control_cli.rb +85 -77
- data/lib/puma/convenient.rb +23 -0
- data/lib/puma/daemon_ext.rb +11 -4
- data/lib/puma/detect.rb +8 -1
- data/lib/puma/dsl.rb +456 -0
- data/lib/puma/events.rb +35 -18
- data/lib/puma/jruby_restart.rb +1 -1
- data/lib/puma/launcher.rb +399 -0
- data/lib/puma/minissl.rb +49 -20
- data/lib/puma/null_io.rb +15 -0
- data/lib/puma/plugin.rb +104 -0
- data/lib/puma/plugin/tmp_restart.rb +35 -0
- data/lib/puma/rack/backports/uri/common_18.rb +56 -0
- data/lib/puma/rack/backports/uri/common_192.rb +52 -0
- data/lib/puma/rack/backports/uri/common_193.rb +29 -0
- data/lib/puma/rack/builder.rb +295 -0
- data/lib/puma/rack/urlmap.rb +90 -0
- data/lib/puma/reactor.rb +14 -1
- data/lib/puma/runner.rb +35 -17
- data/lib/puma/server.rb +161 -58
- data/lib/puma/single.rb +15 -10
- data/lib/puma/state_file.rb +29 -0
- data/lib/puma/thread_pool.rb +88 -13
- data/lib/puma/util.rb +123 -0
- data/lib/rack/handler/puma.rb +35 -29
- data/puma.gemspec +2 -4
- data/tools/jungle/init.d/README.md +2 -2
- data/tools/jungle/init.d/puma +69 -7
- data/tools/jungle/upstart/puma.conf +8 -2
- metadata +51 -71
- data/COPYING +0 -55
- data/TODO +0 -5
- data/lib/puma/rack_patch.rb +0 -45
- data/test/test_app_status.rb +0 -92
- data/test/test_cli.rb +0 -173
- data/test/test_config.rb +0 -16
- data/test/test_http10.rb +0 -27
- data/test/test_http11.rb +0 -145
- data/test/test_integration.rb +0 -165
- data/test/test_iobuffer.rb +0 -38
- data/test/test_minissl.rb +0 -25
- data/test/test_null_io.rb +0 -31
- data/test/test_persistent.rb +0 -238
- data/test/test_puma_server.rb +0 -292
- data/test/test_rack_handler.rb +0 -10
- data/test/test_rack_server.rb +0 -141
- data/test/test_tcp_rack.rb +0 -42
- data/test/test_thread_pool.rb +0 -156
- data/test/test_unix_socket.rb +0 -39
- data/test/test_ws.rb +0 -89
data/lib/puma/const.rb
CHANGED
@@ -1,5 +1,4 @@
|
|
1
|
-
|
2
|
-
|
1
|
+
#encoding: utf-8
|
3
2
|
module Puma
|
4
3
|
class UnsupportedOption < RuntimeError
|
5
4
|
end
|
@@ -8,12 +7,85 @@ module Puma
|
|
8
7
|
# Every standard HTTP code mapped to the appropriate message. These are
|
9
8
|
# used so frequently that they are placed directly in Puma for easy
|
10
9
|
# access rather than Puma::Const itself.
|
11
|
-
|
10
|
+
|
11
|
+
# Every standard HTTP code mapped to the appropriate message.
|
12
|
+
# Generated with:
|
13
|
+
# curl -s https://www.iana.org/assignments/http-status-codes/http-status-codes-1.csv | \
|
14
|
+
# ruby -ne 'm = /^(\d{3}),(?!Unassigned|\(Unused\))([^,]+)/.match($_) and \
|
15
|
+
# puts "#{m[1]} => \x27#{m[2].strip}\x27,"'
|
16
|
+
HTTP_STATUS_CODES = {
|
17
|
+
100 => 'Continue',
|
18
|
+
101 => 'Switching Protocols',
|
19
|
+
102 => 'Processing',
|
20
|
+
200 => 'OK',
|
21
|
+
201 => 'Created',
|
22
|
+
202 => 'Accepted',
|
23
|
+
203 => 'Non-Authoritative Information',
|
24
|
+
204 => 'No Content',
|
25
|
+
205 => 'Reset Content',
|
26
|
+
206 => 'Partial Content',
|
27
|
+
207 => 'Multi-Status',
|
28
|
+
208 => 'Already Reported',
|
29
|
+
226 => 'IM Used',
|
30
|
+
300 => 'Multiple Choices',
|
31
|
+
301 => 'Moved Permanently',
|
32
|
+
302 => 'Found',
|
33
|
+
303 => 'See Other',
|
34
|
+
304 => 'Not Modified',
|
35
|
+
305 => 'Use Proxy',
|
36
|
+
307 => 'Temporary Redirect',
|
37
|
+
308 => 'Permanent Redirect',
|
38
|
+
400 => 'Bad Request',
|
39
|
+
401 => 'Unauthorized',
|
40
|
+
402 => 'Payment Required',
|
41
|
+
403 => 'Forbidden',
|
42
|
+
404 => 'Not Found',
|
43
|
+
405 => 'Method Not Allowed',
|
44
|
+
406 => 'Not Acceptable',
|
45
|
+
407 => 'Proxy Authentication Required',
|
46
|
+
408 => 'Request Timeout',
|
47
|
+
409 => 'Conflict',
|
48
|
+
410 => 'Gone',
|
49
|
+
411 => 'Length Required',
|
50
|
+
412 => 'Precondition Failed',
|
51
|
+
413 => 'Payload Too Large',
|
52
|
+
414 => 'URI Too Long',
|
53
|
+
415 => 'Unsupported Media Type',
|
54
|
+
416 => 'Range Not Satisfiable',
|
55
|
+
417 => 'Expectation Failed',
|
56
|
+
422 => 'Unprocessable Entity',
|
57
|
+
423 => 'Locked',
|
58
|
+
424 => 'Failed Dependency',
|
59
|
+
426 => 'Upgrade Required',
|
60
|
+
428 => 'Precondition Required',
|
61
|
+
429 => 'Too Many Requests',
|
62
|
+
431 => 'Request Header Fields Too Large',
|
63
|
+
500 => 'Internal Server Error',
|
64
|
+
501 => 'Not Implemented',
|
65
|
+
502 => 'Bad Gateway',
|
66
|
+
503 => 'Service Unavailable',
|
67
|
+
504 => 'Gateway Timeout',
|
68
|
+
505 => 'HTTP Version Not Supported',
|
69
|
+
506 => 'Variant Also Negotiates',
|
70
|
+
507 => 'Insufficient Storage',
|
71
|
+
508 => 'Loop Detected',
|
72
|
+
510 => 'Not Extended',
|
73
|
+
511 => 'Network Authentication Required'
|
74
|
+
}
|
75
|
+
|
76
|
+
SYMBOL_TO_STATUS_CODE = Hash[*HTTP_STATUS_CODES.map { |code, message|
|
77
|
+
[message.downcase.gsub(/\s|-|'/, '_').to_sym, code]
|
78
|
+
}.flatten]
|
12
79
|
|
13
80
|
# For some HTTP status codes the client only expects headers.
|
14
|
-
|
15
|
-
|
16
|
-
}
|
81
|
+
#
|
82
|
+
|
83
|
+
no_body = {}
|
84
|
+
((100..199).to_a << 204 << 205 << 304).each do |code|
|
85
|
+
no_body[code] = true
|
86
|
+
end
|
87
|
+
|
88
|
+
STATUS_WITH_NO_ENTITY_BODY = no_body
|
17
89
|
|
18
90
|
# Frequently used constants when constructing requests or responses. Many times
|
19
91
|
# the constant just refers to a string with the same contents. Using these constants
|
@@ -28,9 +100,10 @@ module Puma
|
|
28
100
|
# too taxing on performance.
|
29
101
|
module Const
|
30
102
|
|
31
|
-
PUMA_VERSION = VERSION = "
|
32
|
-
CODE_NAME = "
|
33
|
-
|
103
|
+
PUMA_VERSION = VERSION = "3.1.1".freeze
|
104
|
+
CODE_NAME = "El Niño Winter Wonderland".freeze
|
105
|
+
PUMA_SERVER_STRING = ['puma', PUMA_VERSION, CODE_NAME].join(' ').freeze
|
106
|
+
|
34
107
|
FAST_TRACK_KA_TIMEOUT = 0.2
|
35
108
|
|
36
109
|
# The default number of seconds for another request within a persistent
|
@@ -41,6 +114,10 @@ module Puma
|
|
41
114
|
# for the request
|
42
115
|
FIRST_DATA_TIMEOUT = 30
|
43
116
|
|
117
|
+
# How long to wait when getting some write blocking on the socket when
|
118
|
+
# sending data back
|
119
|
+
WRITE_TIMEOUT = 10
|
120
|
+
|
44
121
|
DATE = "Date".freeze
|
45
122
|
|
46
123
|
SCRIPT_NAME = "SCRIPT_NAME".freeze
|
@@ -54,15 +131,18 @@ module Puma
|
|
54
131
|
PUMA_TMP_BASE = "puma".freeze
|
55
132
|
|
56
133
|
# Indicate that we couldn't parse the request
|
57
|
-
ERROR_400_RESPONSE = "HTTP/1.1 400 Bad Request\r\n\r\n"
|
134
|
+
ERROR_400_RESPONSE = "HTTP/1.1 400 Bad Request\r\n\r\n".freeze
|
58
135
|
|
59
136
|
# The standard empty 404 response for bad requests. Use Error4040Handler for custom stuff.
|
60
137
|
ERROR_404_RESPONSE = "HTTP/1.1 404 Not Found\r\nConnection: close\r\nServer: Puma #{PUMA_VERSION}\r\n\r\nNOT FOUND".freeze
|
61
138
|
|
139
|
+
# The standard empty 408 response for requests that timed out.
|
140
|
+
ERROR_408_RESPONSE = "HTTP/1.1 408 Request Timeout\r\nConnection: close\r\nServer: Puma #{PUMA_VERSION}\r\n\r\n".freeze
|
141
|
+
|
62
142
|
CONTENT_LENGTH = "CONTENT_LENGTH".freeze
|
63
143
|
|
64
144
|
# Indicate that there was an internal error, obviously.
|
65
|
-
ERROR_500_RESPONSE = "HTTP/1.1 500 Internal Server Error\r\n\r\n"
|
145
|
+
ERROR_500_RESPONSE = "HTTP/1.1 500 Internal Server Error\r\n\r\n".freeze
|
66
146
|
|
67
147
|
# A common header for indicating the server is too busy. Not used yet.
|
68
148
|
ERROR_503_RESPONSE = "HTTP/1.1 503 Service Unavailable\r\n\r\nBUSY".freeze
|
@@ -104,6 +184,8 @@ module Puma
|
|
104
184
|
PORT_80 = "80".freeze
|
105
185
|
PORT_443 = "443".freeze
|
106
186
|
LOCALHOST = "localhost".freeze
|
187
|
+
LOCALHOST_IP = "127.0.0.1".freeze
|
188
|
+
LOCALHOST_ADDR = "127.0.0.1:0".freeze
|
107
189
|
|
108
190
|
SERVER_PROTOCOL = "SERVER_PROTOCOL".freeze
|
109
191
|
HTTP_11 = "HTTP/1.1".freeze
|
@@ -122,6 +204,7 @@ module Puma
|
|
122
204
|
RACK_AFTER_REPLY = "rack.after_reply".freeze
|
123
205
|
PUMA_SOCKET = "puma.socket".freeze
|
124
206
|
PUMA_CONFIG = "puma.config".freeze
|
207
|
+
PUMA_PEERCERT = "puma.peercert".freeze
|
125
208
|
|
126
209
|
HTTP = "http".freeze
|
127
210
|
HTTPS = "https".freeze
|
@@ -135,11 +218,11 @@ module Puma
|
|
135
218
|
HTTP_10_200 = "HTTP/1.0 200 OK\r\n".freeze
|
136
219
|
|
137
220
|
CLOSE = "close".freeze
|
138
|
-
KEEP_ALIVE = "
|
221
|
+
KEEP_ALIVE = "keep-alive".freeze
|
139
222
|
|
140
|
-
CONTENT_LENGTH2 = "
|
223
|
+
CONTENT_LENGTH2 = "content-length".freeze
|
141
224
|
CONTENT_LENGTH_S = "Content-Length: ".freeze
|
142
|
-
TRANSFER_ENCODING = "
|
225
|
+
TRANSFER_ENCODING = "transfer-encoding".freeze
|
143
226
|
|
144
227
|
CONNECTION_CLOSE = "Connection: close\r\n".freeze
|
145
228
|
CONNECTION_KEEP_ALIVE = "Connection: Keep-Alive\r\n".freeze
|
data/lib/puma/control_cli.rb
CHANGED
@@ -1,53 +1,60 @@
|
|
1
1
|
require 'optparse'
|
2
|
+
require 'puma'
|
2
3
|
require 'puma/const'
|
4
|
+
require 'puma/detect'
|
3
5
|
require 'puma/configuration'
|
4
|
-
require 'yaml'
|
5
6
|
require 'uri'
|
6
7
|
require 'socket'
|
8
|
+
|
7
9
|
module Puma
|
8
10
|
class ControlCLI
|
9
11
|
|
10
|
-
COMMANDS = %w{halt restart phased-restart start stats status stop}
|
11
|
-
|
12
|
-
def is_windows?
|
13
|
-
RUBY_PLATFORM =~ /(win|w)32$/ ? true : false
|
14
|
-
end
|
12
|
+
COMMANDS = %w{halt restart phased-restart start stats status stop reload-worker-directory}
|
15
13
|
|
16
14
|
def initialize(argv, stdout=STDOUT, stderr=STDERR)
|
17
|
-
@
|
15
|
+
@state = nil
|
16
|
+
@quiet = false
|
17
|
+
@pidfile = nil
|
18
|
+
@pid = nil
|
19
|
+
@control_url = nil
|
20
|
+
@control_auth_token = nil
|
21
|
+
@config_file = nil
|
22
|
+
@command = nil
|
23
|
+
|
24
|
+
@argv = argv.dup
|
18
25
|
@stdout = stdout
|
19
26
|
@stderr = stderr
|
20
|
-
@
|
27
|
+
@cli_options = {}
|
21
28
|
|
22
29
|
opts = OptionParser.new do |o|
|
23
30
|
o.banner = "Usage: pumactl (-p PID | -P pidfile | -S status_file | -C url -T token | -F config.rb) (#{COMMANDS.join("|")})"
|
24
31
|
|
25
32
|
o.on "-S", "--state PATH", "Where the state file to use is" do |arg|
|
26
|
-
@
|
33
|
+
@state = arg
|
27
34
|
end
|
28
35
|
|
29
36
|
o.on "-Q", "--quiet", "Not display messages" do |arg|
|
30
|
-
@
|
37
|
+
@quiet = true
|
31
38
|
end
|
32
39
|
|
33
40
|
o.on "-P", "--pidfile PATH", "Pid file" do |arg|
|
34
|
-
@
|
41
|
+
@pidfile = arg
|
35
42
|
end
|
36
43
|
|
37
44
|
o.on "-p", "--pid PID", "Pid" do |arg|
|
38
|
-
@
|
45
|
+
@pid = arg.to_i
|
39
46
|
end
|
40
47
|
|
41
48
|
o.on "-C", "--control-url URL", "The bind url to use for the control server" do |arg|
|
42
|
-
@
|
49
|
+
@control_url = arg
|
43
50
|
end
|
44
51
|
|
45
52
|
o.on "-T", "--control-token TOKEN", "The token to use as authentication for the control server" do |arg|
|
46
|
-
@
|
53
|
+
@control_auth_token = arg
|
47
54
|
end
|
48
55
|
|
49
56
|
o.on "-F", "--config-file PATH", "Puma config script" do |arg|
|
50
|
-
@
|
57
|
+
@config_file = arg
|
51
58
|
end
|
52
59
|
|
53
60
|
o.on_tail("-H", "--help", "Show this message") do
|
@@ -63,18 +70,29 @@ module Puma
|
|
63
70
|
|
64
71
|
opts.order!(argv) { |a| opts.terminate a }
|
65
72
|
|
66
|
-
command = argv.shift
|
67
|
-
|
73
|
+
@command = argv.shift
|
74
|
+
|
75
|
+
unless @config_file == '-'
|
76
|
+
if @config_file.nil? and File.exist?('config/puma.rb')
|
77
|
+
@config_file = 'config/puma.rb'
|
78
|
+
end
|
68
79
|
|
69
|
-
|
80
|
+
if @config_file
|
81
|
+
config = Puma::Configuration.from_file @config_file
|
82
|
+
@state ||= config.options[:state]
|
83
|
+
@control_url ||= config.options[:control_url]
|
84
|
+
@control_auth_token ||= config.options[:control_auth_token]
|
85
|
+
@pidfile ||= config.options[:pidfile]
|
86
|
+
end
|
87
|
+
end
|
70
88
|
|
71
89
|
# check present of command
|
72
|
-
unless @
|
90
|
+
unless @command
|
73
91
|
raise "Available commands: #{COMMANDS.join(", ")}"
|
74
92
|
end
|
75
93
|
|
76
|
-
unless COMMANDS.include? @
|
77
|
-
raise "Invalid command: #{@
|
94
|
+
unless COMMANDS.include? @command
|
95
|
+
raise "Invalid command: #{@command}"
|
78
96
|
end
|
79
97
|
|
80
98
|
rescue => e
|
@@ -83,45 +101,29 @@ module Puma
|
|
83
101
|
end
|
84
102
|
|
85
103
|
def message(msg)
|
86
|
-
@stdout.puts msg unless @
|
104
|
+
@stdout.puts msg unless @quiet
|
87
105
|
end
|
88
106
|
|
89
107
|
def prepare_configuration
|
90
|
-
if @
|
91
|
-
unless File.exist? @
|
92
|
-
raise "
|
108
|
+
if @state
|
109
|
+
unless File.exist? @state
|
110
|
+
raise "State file not found: #{@state}"
|
93
111
|
end
|
94
112
|
|
95
|
-
|
96
|
-
|
97
|
-
if status.kind_of?(Hash) && status.has_key?("config")
|
98
|
-
|
99
|
-
conf = status["config"]
|
100
|
-
|
101
|
-
# get control_url
|
102
|
-
if url = conf.options[:control_url]
|
103
|
-
@options[:control_url] = url
|
104
|
-
end
|
113
|
+
sf = Puma::StateFile.new
|
114
|
+
sf.load @state
|
105
115
|
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
# get pid
|
112
|
-
@options[:pid] = status["pid"].to_i
|
113
|
-
else
|
114
|
-
raise "Invalid status file: #{@options[:state]}"
|
115
|
-
end
|
116
|
-
|
117
|
-
elsif @options.has_key? :pidfile
|
116
|
+
@control_url = sf.control_url
|
117
|
+
@control_auth_token = sf.control_auth_token
|
118
|
+
@pid = sf.pid
|
119
|
+
elsif @pidfile
|
118
120
|
# get pid from pid_file
|
119
|
-
@
|
121
|
+
@pid = File.open(@pidfile).gets.to_i
|
120
122
|
end
|
121
123
|
end
|
122
124
|
|
123
125
|
def send_request
|
124
|
-
uri = URI.parse @
|
126
|
+
uri = URI.parse @control_url
|
125
127
|
|
126
128
|
# create server object by scheme
|
127
129
|
@server = case uri.scheme
|
@@ -133,13 +135,13 @@ module Puma
|
|
133
135
|
raise "Invalid scheme: #{uri.scheme}"
|
134
136
|
end
|
135
137
|
|
136
|
-
if @
|
138
|
+
if @command == "status"
|
137
139
|
message "Puma is started"
|
138
140
|
else
|
139
|
-
url = "/#{@
|
141
|
+
url = "/#{@command}"
|
140
142
|
|
141
|
-
if @
|
142
|
-
url = url + "?token=#{@
|
143
|
+
if @control_auth_token
|
144
|
+
url = url + "?token=#{@control_auth_token}"
|
143
145
|
end
|
144
146
|
|
145
147
|
@server << "GET #{url} HTTP/1.0\r\n\r\n"
|
@@ -164,63 +166,66 @@ module Puma
|
|
164
166
|
raise "Bad response from server: #{@code}"
|
165
167
|
end
|
166
168
|
|
167
|
-
message "Command #{@
|
168
|
-
message response.last if @
|
169
|
+
message "Command #{@command} sent success"
|
170
|
+
message response.last if @command == "stats"
|
169
171
|
end
|
170
172
|
|
171
173
|
@server.close
|
172
174
|
end
|
173
175
|
|
174
176
|
def send_signal
|
175
|
-
unless
|
177
|
+
unless @pid
|
176
178
|
raise "Neither pid nor control url available"
|
177
179
|
end
|
178
180
|
|
179
181
|
begin
|
180
|
-
Process.getpgid pid
|
182
|
+
Process.getpgid @pid
|
181
183
|
rescue SystemCallError
|
182
|
-
if @
|
183
|
-
@options.delete(:command)
|
184
|
+
if @command == "restart"
|
184
185
|
start
|
185
186
|
else
|
186
|
-
raise "No pid '#{pid}' found"
|
187
|
+
raise "No pid '#{@pid}' found"
|
187
188
|
end
|
188
189
|
end
|
189
190
|
|
190
|
-
case @
|
191
|
+
case @command
|
191
192
|
when "restart"
|
192
|
-
Process.kill "SIGUSR2", pid
|
193
|
+
Process.kill "SIGUSR2", @pid
|
193
194
|
|
194
195
|
when "halt"
|
195
|
-
Process.kill "QUIT", pid
|
196
|
+
Process.kill "QUIT", @pid
|
196
197
|
|
197
198
|
when "stop"
|
198
|
-
Process.kill "SIGTERM", pid
|
199
|
+
Process.kill "SIGTERM", @pid
|
199
200
|
|
200
201
|
when "stats"
|
201
202
|
puts "Stats not available via pid only"
|
202
203
|
return
|
203
204
|
|
205
|
+
when "reload-worker-directory"
|
206
|
+
puts "reload-worker-directory not available via pid only"
|
207
|
+
return
|
208
|
+
|
204
209
|
when "phased-restart"
|
205
|
-
Process.kill "SIGUSR1", pid
|
210
|
+
Process.kill "SIGUSR1", @pid
|
206
211
|
|
207
212
|
else
|
208
213
|
message "Puma is started"
|
209
214
|
return
|
210
215
|
end
|
211
216
|
|
212
|
-
message "Command #{@
|
217
|
+
message "Command #{@command} sent success"
|
213
218
|
end
|
214
219
|
|
215
220
|
def run
|
216
|
-
start if @
|
221
|
+
start if @command == "start"
|
217
222
|
|
218
223
|
prepare_configuration
|
219
224
|
|
220
|
-
if
|
225
|
+
if Puma.windows?
|
221
226
|
send_request
|
222
227
|
else
|
223
|
-
@
|
228
|
+
@control_url ? send_request : send_signal
|
224
229
|
end
|
225
230
|
|
226
231
|
rescue => e
|
@@ -232,18 +237,21 @@ module Puma
|
|
232
237
|
def start
|
233
238
|
require 'puma/cli'
|
234
239
|
|
235
|
-
run_args =
|
240
|
+
run_args = []
|
236
241
|
|
237
|
-
|
238
|
-
|
239
|
-
|
240
|
-
|
241
|
-
|
242
|
-
|
243
|
-
end
|
242
|
+
run_args += ["-S", @state] if @state
|
243
|
+
run_args += ["-q"] if @quiet
|
244
|
+
run_args += ["--pidfile", @pidfile] if @pidfile
|
245
|
+
run_args += ["--control", @control_url] if @control_url
|
246
|
+
run_args += ["--control-token", @control_auth_token] if @control_auth_token
|
247
|
+
run_args += ["-C", @config_file] if @config_file
|
244
248
|
|
245
249
|
events = Puma::Events.new @stdout, @stderr
|
246
250
|
|
251
|
+
# replace $0 because puma use it to generate restart command
|
252
|
+
puma_cmd = $0.gsub(/pumactl$/, 'puma')
|
253
|
+
$0 = puma_cmd if File.exist?(puma_cmd)
|
254
|
+
|
247
255
|
cli = Puma::CLI.new run_args, events
|
248
256
|
cli.run
|
249
257
|
end
|