puma 2.2.0 → 8.0.2

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 (136) hide show
  1. checksums.yaml +7 -0
  2. data/History.md +3334 -0
  3. data/LICENSE +23 -20
  4. data/README.md +387 -100
  5. data/bin/puma-wild +25 -0
  6. data/bin/pumactl +1 -1
  7. data/docs/5.0-Upgrade.md +98 -0
  8. data/docs/6.0-Upgrade.md +56 -0
  9. data/docs/7.0-Upgrade.md +52 -0
  10. data/docs/8.0-Upgrade.md +100 -0
  11. data/docs/architecture.md +74 -0
  12. data/docs/compile_options.md +55 -0
  13. data/docs/deployment.md +137 -0
  14. data/docs/fork_worker.md +41 -0
  15. data/docs/grpc.md +62 -0
  16. data/docs/images/favicon.svg +1 -0
  17. data/docs/images/puma-connection-flow-no-reactor.png +0 -0
  18. data/docs/images/puma-connection-flow.png +0 -0
  19. data/docs/images/puma-general-arch.png +0 -0
  20. data/docs/images/running-puma.svg +1 -0
  21. data/docs/images/standard-logo.svg +1 -0
  22. data/docs/java_options.md +54 -0
  23. data/docs/jungle/README.md +9 -0
  24. data/docs/jungle/rc.d/README.md +74 -0
  25. data/docs/jungle/rc.d/puma +61 -0
  26. data/docs/jungle/rc.d/puma.conf +10 -0
  27. data/docs/kubernetes.md +73 -0
  28. data/docs/nginx.md +5 -5
  29. data/docs/plugins.md +42 -0
  30. data/docs/rails_dev_mode.md +28 -0
  31. data/docs/restart.md +65 -0
  32. data/docs/signals.md +98 -0
  33. data/docs/stats.md +148 -0
  34. data/docs/systemd.md +253 -0
  35. data/docs/testing_benchmarks_local_files.md +150 -0
  36. data/docs/testing_test_rackup_ci_files.md +36 -0
  37. data/ext/puma_http11/PumaHttp11Service.java +2 -2
  38. data/ext/puma_http11/extconf.rb +59 -2
  39. data/ext/puma_http11/http11_parser.c +319 -487
  40. data/ext/puma_http11/http11_parser.h +15 -13
  41. data/ext/puma_http11/http11_parser.java.rl +64 -94
  42. data/ext/puma_http11/http11_parser.rl +27 -24
  43. data/ext/puma_http11/http11_parser_common.rl +8 -8
  44. data/ext/puma_http11/mini_ssl.c +696 -38
  45. data/ext/puma_http11/no_ssl/PumaHttp11Service.java +15 -0
  46. data/ext/puma_http11/org/jruby/puma/EnvKey.java +241 -0
  47. data/ext/puma_http11/org/jruby/puma/Http11.java +241 -145
  48. data/ext/puma_http11/org/jruby/puma/Http11Parser.java +174 -221
  49. data/ext/puma_http11/org/jruby/puma/MiniSSL.java +413 -193
  50. data/ext/puma_http11/puma_http11.c +183 -175
  51. data/lib/puma/app/status.rb +77 -29
  52. data/lib/puma/binder.rb +349 -119
  53. data/lib/puma/cli.rb +163 -801
  54. data/lib/puma/client.rb +627 -144
  55. data/lib/puma/client_env.rb +171 -0
  56. data/lib/puma/cluster/worker.rb +183 -0
  57. data/lib/puma/cluster/worker_handle.rb +127 -0
  58. data/lib/puma/cluster.rb +634 -0
  59. data/lib/puma/cluster_accept_loop_delay.rb +91 -0
  60. data/lib/puma/commonlogger.rb +115 -0
  61. data/lib/puma/configuration.rb +420 -198
  62. data/lib/puma/const.rb +266 -115
  63. data/lib/puma/control_cli.rb +219 -120
  64. data/lib/puma/detect.rb +56 -2
  65. data/lib/puma/dsl.rb +1562 -0
  66. data/lib/puma/error_logger.rb +115 -0
  67. data/lib/puma/events.rb +44 -60
  68. data/lib/puma/io_buffer.rb +48 -5
  69. data/lib/puma/jruby_restart.rb +2 -51
  70. data/lib/puma/json_serialization.rb +96 -0
  71. data/lib/puma/launcher/bundle_pruner.rb +102 -0
  72. data/lib/puma/launcher.rb +501 -0
  73. data/lib/puma/log_writer.rb +153 -0
  74. data/lib/puma/minissl/context_builder.rb +96 -0
  75. data/lib/puma/minissl.rb +355 -37
  76. data/lib/puma/null_io.rb +79 -12
  77. data/lib/puma/plugin/systemd.rb +90 -0
  78. data/lib/puma/plugin/tmp_restart.rb +36 -0
  79. data/lib/puma/plugin.rb +111 -0
  80. data/lib/puma/rack/builder.rb +297 -0
  81. data/lib/puma/rack/urlmap.rb +93 -0
  82. data/lib/puma/rack_default.rb +21 -4
  83. data/lib/puma/reactor.rb +102 -133
  84. data/lib/puma/response.rb +532 -0
  85. data/lib/puma/runner.rb +211 -0
  86. data/lib/puma/sd_notify.rb +146 -0
  87. data/lib/puma/server.rb +582 -445
  88. data/lib/puma/server_plugin_control.rb +32 -0
  89. data/lib/puma/single.rb +72 -0
  90. data/lib/puma/state_file.rb +69 -0
  91. data/lib/puma/thread_pool.rb +389 -57
  92. data/lib/puma/util.rb +125 -0
  93. data/lib/puma.rb +80 -6
  94. data/lib/rack/handler/puma.rb +125 -47
  95. data/tools/Dockerfile +26 -0
  96. data/tools/trickletest.rb +44 -0
  97. metadata +88 -148
  98. data/COPYING +0 -55
  99. data/Gemfile +0 -10
  100. data/History.txt +0 -302
  101. data/Manifest.txt +0 -60
  102. data/Rakefile +0 -165
  103. data/TODO +0 -5
  104. data/docs/config.md +0 -0
  105. data/ext/puma_http11/ext_help.h +0 -15
  106. data/ext/puma_http11/io_buffer.c +0 -154
  107. data/lib/puma/accept_nonblock.rb +0 -23
  108. data/lib/puma/capistrano.rb +0 -34
  109. data/lib/puma/compat.rb +0 -11
  110. data/lib/puma/daemon_ext.rb +0 -20
  111. data/lib/puma/delegation.rb +0 -11
  112. data/lib/puma/java_io_buffer.rb +0 -45
  113. data/lib/puma/rack_patch.rb +0 -25
  114. data/puma.gemspec +0 -45
  115. data/test/test_app_status.rb +0 -88
  116. data/test/test_cli.rb +0 -171
  117. data/test/test_config.rb +0 -16
  118. data/test/test_http10.rb +0 -27
  119. data/test/test_http11.rb +0 -126
  120. data/test/test_integration.rb +0 -154
  121. data/test/test_iobuffer.rb +0 -38
  122. data/test/test_minissl.rb +0 -25
  123. data/test/test_null_io.rb +0 -31
  124. data/test/test_persistent.rb +0 -238
  125. data/test/test_puma_server.rb +0 -224
  126. data/test/test_rack_handler.rb +0 -10
  127. data/test/test_rack_server.rb +0 -141
  128. data/test/test_thread_pool.rb +0 -146
  129. data/test/test_unix_socket.rb +0 -39
  130. data/test/test_ws.rb +0 -89
  131. data/tools/jungle/init.d/README.md +0 -54
  132. data/tools/jungle/init.d/puma +0 -332
  133. data/tools/jungle/init.d/run-puma +0 -3
  134. data/tools/jungle/upstart/README.md +0 -61
  135. data/tools/jungle/upstart/puma-manager.conf +0 -31
  136. data/tools/jungle/upstart/puma.conf +0 -52
@@ -1,154 +0,0 @@
1
- #include "ruby.h"
2
-
3
- #include <sys/types.h>
4
-
5
- struct buf_int {
6
- uint8_t* top;
7
- uint8_t* cur;
8
-
9
- size_t size;
10
- };
11
-
12
- #define BUF_DEFAULT_SIZE 4096
13
- #define BUF_TOLERANCE 32
14
-
15
- static void buf_free(struct buf_int* internal) {
16
- free(internal->top);
17
- free(internal);
18
- }
19
-
20
- static VALUE buf_alloc(VALUE self) {
21
- VALUE buf;
22
- struct buf_int* internal;
23
-
24
- buf = Data_Make_Struct(self, struct buf_int, 0, buf_free, internal);
25
-
26
- internal->size = BUF_DEFAULT_SIZE;
27
- internal->top = malloc(BUF_DEFAULT_SIZE);
28
- internal->cur = internal->top;
29
-
30
- return buf;
31
- }
32
-
33
- static VALUE buf_append(VALUE self, VALUE str) {
34
- struct buf_int* b;
35
- size_t used, str_len, new_size;
36
-
37
- Data_Get_Struct(self, struct buf_int, b);
38
-
39
- used = b->cur - b->top;
40
-
41
- StringValue(str);
42
- str_len = RSTRING_LEN(str);
43
-
44
- new_size = used + str_len;
45
-
46
- if(new_size > b->size) {
47
- size_t n = b->size + (b->size / 2);
48
- uint8_t* top;
49
- uint8_t* old;
50
-
51
- new_size = (n > new_size ? n : new_size + BUF_TOLERANCE);
52
-
53
- top = malloc(new_size);
54
- old = b->top;
55
- memcpy(top, old, used);
56
- b->top = top;
57
- b->cur = top + used;
58
- b->size = new_size;
59
- free(old);
60
- }
61
-
62
- memcpy(b->cur, RSTRING_PTR(str), str_len);
63
- b->cur += str_len;
64
-
65
- return self;
66
- }
67
-
68
- static VALUE buf_append2(int argc, VALUE* argv, VALUE self) {
69
- struct buf_int* b;
70
- size_t used, new_size;
71
- int i;
72
- VALUE str;
73
-
74
- Data_Get_Struct(self, struct buf_int, b);
75
-
76
- used = b->cur - b->top;
77
- new_size = used;
78
-
79
- for(i = 0; i < argc; i++) {
80
- StringValue(argv[i]);
81
-
82
- str = argv[i];
83
-
84
- new_size += RSTRING_LEN(str);
85
- }
86
-
87
- if(new_size > b->size) {
88
- size_t n = b->size + (b->size / 2);
89
- uint8_t* top;
90
- uint8_t* old;
91
-
92
- new_size = (n > new_size ? n : new_size + BUF_TOLERANCE);
93
-
94
- top = malloc(new_size);
95
- old = b->top;
96
- memcpy(top, old, used);
97
- b->top = top;
98
- b->cur = top + used;
99
- b->size = new_size;
100
- free(old);
101
- }
102
-
103
- for(i = 0; i < argc; i++) {
104
- long str_len;
105
- str = argv[i];
106
- str_len = RSTRING_LEN(str);
107
- memcpy(b->cur, RSTRING_PTR(str), str_len);
108
- b->cur += str_len;
109
- }
110
-
111
- return self;
112
- }
113
-
114
- static VALUE buf_to_str(VALUE self) {
115
- struct buf_int* b;
116
- Data_Get_Struct(self, struct buf_int, b);
117
-
118
- return rb_str_new(b->top, b->cur - b->top);
119
- }
120
-
121
- static VALUE buf_used(VALUE self) {
122
- struct buf_int* b;
123
- Data_Get_Struct(self, struct buf_int, b);
124
-
125
- return INT2FIX(b->cur - b->top);
126
- }
127
-
128
- static VALUE buf_capa(VALUE self) {
129
- struct buf_int* b;
130
- Data_Get_Struct(self, struct buf_int, b);
131
-
132
- return INT2FIX(b->size);
133
- }
134
-
135
- static VALUE buf_reset(VALUE self) {
136
- struct buf_int* b;
137
- Data_Get_Struct(self, struct buf_int, b);
138
-
139
- b->cur = b->top;
140
- return self;
141
- }
142
-
143
- void Init_io_buffer(VALUE puma) {
144
- VALUE buf = rb_define_class_under(puma, "IOBuffer", rb_cObject);
145
-
146
- rb_define_alloc_func(buf, buf_alloc);
147
- rb_define_method(buf, "<<", buf_append, 1);
148
- rb_define_method(buf, "append", buf_append2, -1);
149
- rb_define_method(buf, "to_str", buf_to_str, 0);
150
- rb_define_method(buf, "to_s", buf_to_str, 0);
151
- rb_define_method(buf, "used", buf_used, 0);
152
- rb_define_method(buf, "capacity", buf_capa, 0);
153
- rb_define_method(buf, "reset", buf_reset, 0);
154
- }
@@ -1,23 +0,0 @@
1
- require 'openssl'
2
-
3
- module OpenSSL
4
- module SSL
5
- class SSLServer
6
- unless public_method_defined? :accept_nonblock
7
- def accept_nonblock
8
- sock = @svr.accept_nonblock
9
-
10
- begin
11
- ssl = OpenSSL::SSL::SSLSocket.new(sock, @ctx)
12
- ssl.sync_close = true
13
- ssl.accept if @start_immediately
14
- ssl
15
- rescue SSLError => ex
16
- sock.close
17
- raise ex
18
- end
19
- end
20
- end
21
- end
22
- end
23
- end
@@ -1,34 +0,0 @@
1
- Capistrano::Configuration.instance.load do
2
- after 'deploy:stop', 'puma:stop'
3
- after 'deploy:start', 'puma:start'
4
- after 'deploy:restart', 'puma:restart'
5
-
6
- # Ensure the tmp/sockets directory is created by the deploy:setup task and
7
- # symlinked in by the deploy:update task. This is not handled by Capistrano
8
- # v2 but is fixed in v3.
9
- shared_children.push('tmp/sockets')
10
-
11
- _cset(:puma_cmd) { "#{fetch(:bundle_cmd, 'bundle')} exec puma" }
12
- _cset(:pumactl_cmd) { "#{fetch(:bundle_cmd, 'bundle')} exec pumactl" }
13
- _cset(:puma_state) { "#{shared_path}/sockets/puma.state" }
14
- _cset(:puma_socket) { "unix://#{shared_path}/sockets/puma.sock" }
15
- _cset(:puma_role) { :app }
16
-
17
- namespace :puma do
18
- desc 'Start puma'
19
- task :start, :roles => lambda { fetch(:puma_role) }, :on_no_matching_servers => :continue do
20
- puma_env = fetch(:rack_env, fetch(:rails_env, 'production'))
21
- run "cd #{current_path} && #{fetch(:puma_cmd)} -q -d -e #{puma_env} -b '#{fetch(:puma_socket)}' -S #{fetch(:puma_state)} --control 'unix://#{shared_path}/sockets/pumactl.sock'", :pty => false
22
- end
23
-
24
- desc 'Stop puma'
25
- task :stop, :roles => lambda { fetch(:puma_role) }, :on_no_matching_servers => :continue do
26
- run "cd #{current_path} && #{fetch(:pumactl_cmd)} -S #{fetch(:puma_state)} stop"
27
- end
28
-
29
- desc 'Restart puma'
30
- task :restart, :roles => lambda { fetch(:puma_role) }, :on_no_matching_servers => :continue do
31
- run "cd #{current_path} && #{fetch(:pumactl_cmd)} -S #{fetch(:puma_state)} restart"
32
- end
33
- end
34
- end
data/lib/puma/compat.rb DELETED
@@ -1,11 +0,0 @@
1
- # Provides code to work properly on 1.8 and 1.9
2
-
3
- class String
4
- unless method_defined? :bytesize
5
- alias_method :bytesize, :size
6
- end
7
-
8
- unless method_defined? :byteslice
9
- alias_method :byteslice, :[]
10
- end
11
- end
@@ -1,20 +0,0 @@
1
- module Process
2
- def self.daemon(nochdir=false, noclose=false)
3
- exit if fork # Parent exits, child continues.
4
-
5
- Process.setsid # Become session leader.
6
-
7
- exit if fork # Zap session leader. See [1].
8
-
9
- Dir.chdir "/" unless nochdir # Release old working directory.
10
-
11
- if !noclose
12
- null = File.open "/dev/null", "w+"
13
- STDIN.reopen null
14
- STDOUT.reopen null
15
- STDERR.reopen null
16
- end
17
-
18
- 0
19
- end unless respond_to?(:daemon)
20
- end
@@ -1,11 +0,0 @@
1
- module Puma
2
- module Delegation
3
- def forward(what, who)
4
- module_eval <<-CODE
5
- def #{what}(*args, &blk)
6
- #{who}.#{what}(*args, &blk)
7
- end
8
- CODE
9
- end
10
- end
11
- end
@@ -1,45 +0,0 @@
1
- require 'java'
2
-
3
- # Conservative native JRuby/Java implementation of IOBuffer
4
- # backed by a ByteArrayOutputStream and conversion between
5
- # Ruby String and Java bytes
6
- module Puma
7
- class JavaIOBuffer < java.io.ByteArrayOutputStream
8
- field_reader :buf
9
- end
10
-
11
- class IOBuffer
12
- BUF_DEFAULT_SIZE = 4096
13
-
14
- def initialize
15
- @buf = JavaIOBuffer.new(BUF_DEFAULT_SIZE)
16
- end
17
-
18
- def reset
19
- @buf.reset
20
- end
21
-
22
- def <<(str)
23
- bytes = str.to_java_bytes
24
- @buf.write(bytes, 0, bytes.length)
25
- end
26
-
27
- def append(*strs)
28
- strs.each { |s| self << s; }
29
- end
30
-
31
- def to_s
32
- String.from_java_bytes @buf.to_byte_array
33
- end
34
-
35
- alias_method :to_str, :to_s
36
-
37
- def used
38
- @buf.size
39
- end
40
-
41
- def capacity
42
- @buf.buf.length
43
- end
44
- end
45
- end
@@ -1,25 +0,0 @@
1
- require 'rack/commonlogger'
2
-
3
- module Rack
4
- # Patch CommonLogger to use after_reply.
5
- #
6
- # Simply request this file and CommonLogger will be a bit more
7
- # efficient.
8
- class CommonLogger
9
- remove_method :call
10
-
11
- def call(env)
12
- began_at = Time.now
13
- status, header, body = @app.call(env)
14
- header = Utils::HeaderHash.new(header)
15
-
16
- if ary = env['rack.after_reply']
17
- ary << lambda { log(env, status, header, began_at) }
18
- else
19
- body = BodyProxy.new(body) { log(env, status, header, began_at) }
20
- end
21
-
22
- [status, header, body]
23
- end
24
- end
25
- end
data/puma.gemspec DELETED
@@ -1,45 +0,0 @@
1
- # -*- encoding: utf-8 -*-
2
-
3
- Gem::Specification.new do |s|
4
- s.name = "puma"
5
- s.version = "2.2.0"
6
-
7
- s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
8
- s.authors = ["Evan Phoenix"]
9
- s.date = "2013-07-02"
10
- s.description = "Puma is a simple, fast, threaded, and highly concurrent HTTP 1.1 server for Ruby/Rack applications. Puma is intended for use in both development and production environments. In order to get the best throughput, it is highly recommended that you use a Ruby implementation with real threads like Rubinius or JRuby."
11
- s.email = ["evan@phx.io"]
12
- s.executables = ["puma", "pumactl"]
13
- s.extensions = ["ext/puma_http11/extconf.rb"]
14
- s.extra_rdoc_files = ["History.txt", "Manifest.txt", "README.md", "docs/config.md", "docs/nginx.md", "tools/jungle/init.d/README.md", "tools/jungle/upstart/README.md"]
15
- s.files = ["COPYING", "Gemfile", "History.txt", "LICENSE", "Manifest.txt", "README.md", "Rakefile", "TODO", "bin/puma", "bin/pumactl", "docs/config.md", "docs/nginx.md", "ext/puma_http11/PumaHttp11Service.java", "ext/puma_http11/ext_help.h", "ext/puma_http11/extconf.rb", "ext/puma_http11/http11_parser.c", "ext/puma_http11/http11_parser.h", "ext/puma_http11/http11_parser.java.rl", "ext/puma_http11/http11_parser.rl", "ext/puma_http11/http11_parser_common.rl", "ext/puma_http11/io_buffer.c", "ext/puma_http11/mini_ssl.c", "ext/puma_http11/org/jruby/puma/Http11.java", "ext/puma_http11/org/jruby/puma/Http11Parser.java", "ext/puma_http11/org/jruby/puma/MiniSSL.java", "ext/puma_http11/puma_http11.c", "lib/puma.rb", "lib/puma/accept_nonblock.rb", "lib/puma/app/status.rb", "lib/puma/binder.rb", "lib/puma/capistrano.rb", "lib/puma/cli.rb", "lib/puma/client.rb", "lib/puma/compat.rb", "lib/puma/configuration.rb", "lib/puma/const.rb", "lib/puma/control_cli.rb", "lib/puma/daemon_ext.rb", "lib/puma/delegation.rb", "lib/puma/detect.rb", "lib/puma/events.rb", "lib/puma/io_buffer.rb", "lib/puma/java_io_buffer.rb", "lib/puma/jruby_restart.rb", "lib/puma/minissl.rb", "lib/puma/null_io.rb", "lib/puma/rack_default.rb", "lib/puma/rack_patch.rb", "lib/puma/reactor.rb", "lib/puma/server.rb", "lib/puma/thread_pool.rb", "lib/puma/util.rb", "lib/rack/handler/puma.rb", "puma.gemspec", "tools/jungle/init.d/README.md", "tools/jungle/init.d/puma", "tools/jungle/init.d/run-puma", "tools/jungle/upstart/README.md", "tools/jungle/upstart/puma-manager.conf", "tools/jungle/upstart/puma.conf", "test/test_app_status.rb", "test/test_cli.rb", "test/test_config.rb", "test/test_http10.rb", "test/test_http11.rb", "test/test_integration.rb", "test/test_iobuffer.rb", "test/test_minissl.rb", "test/test_null_io.rb", "test/test_persistent.rb", "test/test_puma_server.rb", "test/test_rack_handler.rb", "test/test_rack_server.rb", "test/test_thread_pool.rb", "test/test_unix_socket.rb", "test/test_ws.rb"]
16
- s.homepage = "http://puma.io"
17
- s.rdoc_options = ["--main", "README.md"]
18
- s.require_paths = ["lib"]
19
- s.required_ruby_version = Gem::Requirement.new(">= 1.8.7")
20
- s.rubyforge_project = "puma"
21
- s.rubygems_version = "1.8.25"
22
- s.summary = "Puma is a simple, fast, threaded, and highly concurrent HTTP 1.1 server for Ruby/Rack applications"
23
- s.test_files = ["test/test_app_status.rb", "test/test_cli.rb", "test/test_config.rb", "test/test_http10.rb", "test/test_http11.rb", "test/test_integration.rb", "test/test_iobuffer.rb", "test/test_minissl.rb", "test/test_null_io.rb", "test/test_persistent.rb", "test/test_puma_server.rb", "test/test_rack_handler.rb", "test/test_rack_server.rb", "test/test_thread_pool.rb", "test/test_unix_socket.rb", "test/test_ws.rb"]
24
-
25
- if s.respond_to? :specification_version then
26
- s.specification_version = 3
27
-
28
- if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
29
- s.add_runtime_dependency(%q<rack>, ["< 2.0", ">= 1.1"])
30
- s.add_development_dependency(%q<rdoc>, ["~> 4.0"])
31
- s.add_development_dependency(%q<rake-compiler>, ["~> 0.8.0"])
32
- s.add_development_dependency(%q<hoe>, ["~> 3.6"])
33
- else
34
- s.add_dependency(%q<rack>, ["< 2.0", ">= 1.1"])
35
- s.add_dependency(%q<rdoc>, ["~> 4.0"])
36
- s.add_dependency(%q<rake-compiler>, ["~> 0.8.0"])
37
- s.add_dependency(%q<hoe>, ["~> 3.6"])
38
- end
39
- else
40
- s.add_dependency(%q<rack>, ["< 2.0", ">= 1.1"])
41
- s.add_dependency(%q<rdoc>, ["~> 4.0"])
42
- s.add_dependency(%q<rake-compiler>, ["~> 0.8.0"])
43
- s.add_dependency(%q<hoe>, ["~> 3.6"])
44
- end
45
- end
@@ -1,88 +0,0 @@
1
- require 'test/unit'
2
- require 'rack'
3
- require 'puma/app/status'
4
-
5
- class TestAppStatus < Test::Unit::TestCase
6
- class FakeServer
7
- def initialize
8
- @status = :running
9
- @backlog = 0
10
- @running = 0
11
- end
12
-
13
- attr_reader :status
14
- attr_accessor :backlog, :running
15
-
16
- def stop
17
- @status = :stop
18
- end
19
-
20
- def halt
21
- @status = :halt
22
- end
23
- end
24
-
25
- def setup
26
- @server = FakeServer.new
27
- @app = Puma::App::Status.new(@server, @server)
28
- @app.auth_token = nil
29
- end
30
-
31
- def lint(uri)
32
- app = Rack::Lint.new @app
33
- mock_env = Rack::MockRequest.env_for uri
34
- app.call mock_env
35
- end
36
-
37
- def test_bad_token
38
- @app.auth_token = "abcdef"
39
-
40
- status, _, _ = lint('/whatever')
41
-
42
- assert_equal 403, status
43
- end
44
-
45
- def test_good_token
46
- @app.auth_token = "abcdef"
47
-
48
- status, _, _ = lint('/whatever?token=abcdef')
49
-
50
- assert_equal 404, status
51
- end
52
-
53
- def test_unsupported
54
- status, _, _ = lint('/not-real')
55
-
56
- assert_equal 404, status
57
- end
58
-
59
- def test_stop
60
- status, _ , app = lint('/stop')
61
-
62
- assert_equal :stop, @server.status
63
- assert_equal 200, status
64
- assert_equal ['{ "status": "ok" }'], app.enum_for.to_a
65
- end
66
-
67
- def test_halt
68
- status, _ , app = lint('/halt')
69
-
70
- assert_equal :halt, @server.status
71
- assert_equal 200, status
72
- assert_equal ['{ "status": "ok" }'], app.enum_for.to_a
73
- end
74
-
75
- def test_stats
76
- @server.backlog = 1
77
- @server.running = 9
78
- status, _ , app = lint('/stats')
79
-
80
- assert_equal 200, status
81
- assert_equal ['{ "backlog": 1, "running": 9 }'], app.enum_for.to_a
82
- end
83
-
84
- def test_alternate_location
85
- status, _ , _ = lint('__alternatE_location_/stats')
86
- assert_equal 200, status
87
- end
88
- end
data/test/test_cli.rb DELETED
@@ -1,171 +0,0 @@
1
- require "rbconfig"
2
- require 'test/unit'
3
- require 'puma/cli'
4
- require 'tempfile'
5
-
6
- class TestCLI < Test::Unit::TestCase
7
- def setup
8
- @environment = 'production'
9
- @tmp_file = Tempfile.new("puma-test")
10
- @tmp_path = @tmp_file.path
11
- @tmp_file.close!
12
-
13
- @tmp_path2 = "#{@tmp_path}2"
14
-
15
- File.unlink @tmp_path if File.exist? @tmp_path
16
- File.unlink @tmp_path2 if File.exist? @tmp_path2
17
- end
18
-
19
- def teardown
20
- File.unlink @tmp_path if File.exist? @tmp_path
21
- File.unlink @tmp_path2 if File.exist? @tmp_path2
22
- end
23
-
24
- def test_pid_file
25
- cli = Puma::CLI.new ["--pidfile", @tmp_path]
26
- cli.parse_options
27
- cli.write_pid
28
-
29
- assert_equal File.read(@tmp_path).strip.to_i, Process.pid
30
-
31
- cli.stop
32
- assert !File.exist?(@tmp_path), "Pid file shouldn't exist anymore"
33
- end
34
-
35
- def test_control_for_tcp
36
- url = "tcp://127.0.0.1:9877/"
37
- sin = StringIO.new
38
- sout = StringIO.new
39
- cli = Puma::CLI.new ["-b", "tcp://127.0.0.1:9876",
40
- "--control", url,
41
- "--control-token", "",
42
- "test/lobster.ru"], sin, sout
43
- cli.parse_options
44
-
45
- thread_exception = nil
46
- t = Thread.new do
47
- begin
48
- cli.run
49
- rescue Exception => e
50
- thread_exception = e
51
- end
52
- end
53
-
54
- sleep 1
55
-
56
- s = TCPSocket.new "127.0.0.1", 9877
57
- s << "GET /stats HTTP/1.0\r\n\r\n"
58
- body = s.read
59
- assert_equal '{ "backlog": 0, "running": 0 }', body.split("\r\n").last
60
-
61
- cli.stop
62
- t.join
63
- assert_equal nil, thread_exception
64
- end
65
-
66
- unless defined?(JRUBY_VERSION) || RbConfig::CONFIG["host_os"] =~ /mingw|mswin/
67
- def test_control
68
- url = "unix://#{@tmp_path}"
69
-
70
- sin = StringIO.new
71
- sout = StringIO.new
72
-
73
- cli = Puma::CLI.new ["-b", "unix://#{@tmp_path2}",
74
- "--control", url,
75
- "--control-token", "",
76
- "test/lobster.ru"], sin, sout
77
- cli.parse_options
78
-
79
- t = Thread.new { cli.run }
80
-
81
- sleep 1
82
-
83
- s = UNIXSocket.new @tmp_path
84
- s << "GET /stats HTTP/1.0\r\n\r\n"
85
- body = s.read
86
-
87
- assert_equal '{ "backlog": 0, "running": 0 }', body.split("\r\n").last
88
-
89
- cli.stop
90
- t.join
91
- end
92
-
93
- def test_control_stop
94
- url = "unix://#{@tmp_path}"
95
-
96
- sin = StringIO.new
97
- sout = StringIO.new
98
-
99
- cli = Puma::CLI.new ["-b", "unix://#{@tmp_path2}",
100
- "--control", url,
101
- "--control-token", "",
102
- "test/lobster.ru"], sin, sout
103
- cli.parse_options
104
-
105
- t = Thread.new { cli.run }
106
-
107
- sleep 1
108
-
109
- s = UNIXSocket.new @tmp_path
110
- s << "GET /stop HTTP/1.0\r\n\r\n"
111
- body = s.read
112
-
113
- assert_equal '{ "status": "ok" }', body.split("\r\n").last
114
-
115
- t.join
116
- end
117
-
118
- def test_tmp_control
119
- url = "tcp://127.0.0.1:8232"
120
- cli = Puma::CLI.new ["--state", @tmp_path, "--control", "auto"]
121
- cli.parse_options
122
- cli.write_state
123
-
124
- data = YAML.load File.read(@tmp_path)
125
-
126
- assert_equal Process.pid, data["pid"]
127
-
128
- url = data["config"].options[:control_url]
129
-
130
- m = %r!unix://(.*)!.match(url)
131
-
132
- assert m, "'#{url}' is not a URL"
133
- end
134
- end # JRUBY or Windows
135
-
136
- def test_state
137
- url = "tcp://127.0.0.1:8232"
138
- cli = Puma::CLI.new ["--state", @tmp_path, "--control", url]
139
- cli.parse_options
140
- cli.write_state
141
-
142
- data = YAML.load File.read(@tmp_path)
143
-
144
- assert_equal Process.pid, data["pid"]
145
- assert_equal url, data["config"].options[:control_url]
146
- end
147
-
148
- def test_load_path
149
- cli = Puma::CLI.new ["--include", 'foo/bar']
150
- cli.parse_options
151
-
152
- assert_equal 'foo/bar', $LOAD_PATH[0]
153
- $LOAD_PATH.shift
154
-
155
- cli = Puma::CLI.new ["--include", 'foo/bar:baz/qux']
156
- cli.parse_options
157
-
158
- assert_equal 'foo/bar', $LOAD_PATH[0]
159
- $LOAD_PATH.shift
160
- assert_equal 'baz/qux', $LOAD_PATH[0]
161
- $LOAD_PATH.shift
162
- end
163
-
164
- def test_environment
165
- cli = Puma::CLI.new ["--environment", @environment]
166
- cli.parse_options
167
- cli.set_rack_environment
168
-
169
- assert_equal ENV['RACK_ENV'], @environment
170
- end
171
- end
data/test/test_config.rb DELETED
@@ -1,16 +0,0 @@
1
- require 'test/unit'
2
-
3
- require 'puma'
4
- require 'puma/configuration'
5
-
6
- class TestConfigFile < Test::Unit::TestCase
7
- def test_app_from_app_DSL
8
- opts = { :config_file => "test/config/app.rb" }
9
- conf = Puma::Configuration.new opts
10
- conf.load
11
-
12
- app = conf.app
13
-
14
- assert_equal [200, {}, ["embedded app"]], app.call({})
15
- end
16
- end
data/test/test_http10.rb DELETED
@@ -1,27 +0,0 @@
1
- require 'test/testhelp'
2
-
3
- class Http10ParserTest < Test::Unit::TestCase
4
- include Puma
5
-
6
- def test_parse_simple
7
- parser = HttpParser.new
8
- req = {}
9
- http = "GET / HTTP/1.0\r\n\r\n"
10
- nread = parser.execute(req, http, 0)
11
-
12
- assert nread == http.length, "Failed to parse the full HTTP request"
13
- assert parser.finished?, "Parser didn't finish"
14
- assert !parser.error?, "Parser had error"
15
- assert nread == parser.nread, "Number read returned from execute does not match"
16
-
17
- assert_equal '/', req['REQUEST_PATH']
18
- assert_equal 'HTTP/1.0', req['HTTP_VERSION']
19
- assert_equal '/', req['REQUEST_URI']
20
- assert_equal 'GET', req['REQUEST_METHOD']
21
- assert_nil req['FRAGMENT']
22
- assert_nil req['QUERY_STRING']
23
-
24
- parser.reset
25
- assert parser.nread == 0, "Number read after reset should be 0"
26
- end
27
- end