passenger 2.2.2 → 2.2.3
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of passenger might be problematic. Click here for more details.
- data/DEVELOPERS.TXT +13 -3
- data/Rakefile +42 -33
- data/bin/passenger-install-apache2-module +1 -2
- data/bin/passenger-install-nginx-module +7 -19
- data/bin/passenger-status +64 -15
- data/bin/passenger-stress-test +2 -2
- data/doc/ApplicationPool algorithm.txt +26 -22
- data/doc/Users guide Apache.html +374 -149
- data/doc/Users guide Apache.txt +318 -51
- data/doc/Users guide Nginx.html +13 -13
- data/doc/Users guide Nginx.txt +7 -2
- data/doc/cxxapi/Bucket_8h-source.html +62 -25
- data/doc/cxxapi/Configuration_8h-source.html +343 -326
- data/doc/cxxapi/DirectoryMapper_8h-source.html +12 -12
- data/doc/cxxapi/Hooks_8h-source.html +1 -1
- data/doc/cxxapi/annotated.html +1 -1
- data/doc/cxxapi/classHooks-members.html +1 -1
- data/doc/cxxapi/classHooks.html +1 -1
- data/doc/cxxapi/classPassenger_1_1DirectoryMapper-members.html +2 -2
- data/doc/cxxapi/classPassenger_1_1DirectoryMapper.html +9 -9
- data/doc/cxxapi/classes.html +1 -1
- data/doc/cxxapi/definitions_8h-source.html +1 -1
- data/doc/cxxapi/files.html +1 -1
- data/doc/cxxapi/functions.html +2 -2
- data/doc/cxxapi/functions_func.html +2 -2
- data/doc/cxxapi/graph_legend.html +1 -1
- data/doc/cxxapi/group__Configuration.html +1 -1
- data/doc/cxxapi/group__Core.html +1 -1
- data/doc/cxxapi/group__Hooks.html +1 -1
- data/doc/cxxapi/group__Support.html +1 -1
- data/doc/cxxapi/main.html +1 -1
- data/doc/cxxapi/modules.html +1 -1
- data/doc/rdoc/classes/ConditionVariable.html +194 -0
- data/doc/rdoc/classes/Exception.html +120 -0
- data/doc/rdoc/classes/GC.html +113 -0
- data/doc/rdoc/classes/IO.html +169 -0
- data/doc/rdoc/classes/PhusionPassenger.html +238 -0
- data/doc/rdoc/classes/PhusionPassenger/AbstractInstaller.html +153 -0
- data/doc/rdoc/classes/PhusionPassenger/AbstractRequestHandler.html +517 -0
- data/doc/rdoc/classes/PhusionPassenger/AbstractServer.html +719 -0
- data/doc/rdoc/classes/PhusionPassenger/AbstractServer/ServerAlreadyStarted.html +97 -0
- data/doc/rdoc/classes/PhusionPassenger/AbstractServer/ServerError.html +96 -0
- data/doc/rdoc/classes/PhusionPassenger/AbstractServer/ServerNotStarted.html +97 -0
- data/doc/rdoc/classes/PhusionPassenger/AbstractServer/UnknownMessage.html +96 -0
- data/doc/rdoc/classes/PhusionPassenger/AbstractServerCollection.html +598 -0
- data/doc/rdoc/classes/PhusionPassenger/AdminTools.html +140 -0
- data/doc/rdoc/classes/PhusionPassenger/AdminTools/ControlProcess.html +317 -0
- data/doc/rdoc/classes/PhusionPassenger/AdminTools/ControlProcess/Instance.html +138 -0
- data/doc/rdoc/classes/PhusionPassenger/AppInitError.html +154 -0
- data/doc/rdoc/classes/PhusionPassenger/Application.html +283 -0
- data/doc/rdoc/classes/PhusionPassenger/ConsoleTextTemplate.html +172 -0
- data/doc/rdoc/classes/PhusionPassenger/FrameworkInitError.html +145 -0
- data/doc/rdoc/classes/PhusionPassenger/HTMLTemplate.html +175 -0
- data/doc/rdoc/classes/PhusionPassenger/InitializationError.html +141 -0
- data/doc/rdoc/classes/PhusionPassenger/InvalidPath.html +92 -0
- data/doc/rdoc/classes/PhusionPassenger/MessageChannel.html +489 -0
- data/doc/rdoc/classes/PhusionPassenger/NativeSupport.html +350 -0
- data/doc/rdoc/classes/PhusionPassenger/Rack.html +91 -0
- data/doc/rdoc/classes/PhusionPassenger/Rack/ApplicationSpawner.html +188 -0
- data/doc/rdoc/classes/PhusionPassenger/Rack/RequestHandler.html +194 -0
- data/doc/rdoc/classes/PhusionPassenger/Railz.html +95 -0
- data/doc/rdoc/classes/PhusionPassenger/Railz/ApplicationSpawner.html +442 -0
- data/doc/rdoc/classes/PhusionPassenger/Railz/ApplicationSpawner/Error.html +98 -0
- data/doc/rdoc/classes/PhusionPassenger/Railz/CGIFixed.html +200 -0
- data/doc/rdoc/classes/PhusionPassenger/Railz/FrameworkSpawner.html +436 -0
- data/doc/rdoc/classes/PhusionPassenger/Railz/FrameworkSpawner/Error.html +98 -0
- data/doc/rdoc/classes/PhusionPassenger/Railz/RequestHandler.html +155 -0
- data/doc/rdoc/classes/PhusionPassenger/SpawnManager.html +402 -0
- data/doc/rdoc/classes/PhusionPassenger/UnknownError.html +125 -0
- data/doc/rdoc/classes/PhusionPassenger/Utils.html +805 -0
- data/doc/rdoc/classes/PhusionPassenger/VersionNotFound.html +140 -0
- data/doc/rdoc/classes/PhusionPassenger/WSGI.html +89 -0
- data/doc/rdoc/classes/PhusionPassenger/WSGI/ApplicationSpawner.html +188 -0
- data/doc/rdoc/classes/PlatformInfo.html +831 -0
- data/doc/rdoc/classes/RakeExtensions.html +197 -0
- data/doc/rdoc/classes/Signal.html +131 -0
- data/doc/rdoc/created.rid +1 -0
- data/doc/rdoc/files/DEVELOPERS_TXT.html +255 -0
- data/doc/rdoc/files/README.html +157 -0
- data/doc/rdoc/files/ext/phusion_passenger/native_support_c.html +92 -0
- data/doc/rdoc/files/lib/phusion_passenger/abstract_installer_rb.html +129 -0
- data/doc/rdoc/files/lib/phusion_passenger/abstract_request_handler_rb.html +131 -0
- data/doc/rdoc/files/lib/phusion_passenger/abstract_server_collection_rb.html +126 -0
- data/doc/rdoc/files/lib/phusion_passenger/abstract_server_rb.html +130 -0
- data/doc/rdoc/files/lib/phusion_passenger/admin_tools/control_process_rb.html +130 -0
- data/doc/rdoc/files/lib/phusion_passenger/admin_tools_rb.html +122 -0
- data/doc/rdoc/files/lib/phusion_passenger/application_rb.html +127 -0
- data/doc/rdoc/files/lib/phusion_passenger/console_text_template_rb.html +126 -0
- data/doc/rdoc/files/lib/phusion_passenger/constants_rb.html +122 -0
- data/doc/rdoc/files/lib/phusion_passenger/dependencies_rb.html +134 -0
- data/doc/rdoc/files/lib/phusion_passenger/events_rb.html +122 -0
- data/doc/rdoc/files/lib/phusion_passenger/exceptions_rb.html +122 -0
- data/doc/rdoc/files/lib/phusion_passenger/html_template_rb.html +126 -0
- data/doc/rdoc/files/lib/phusion_passenger/message_channel_rb.html +122 -0
- data/doc/rdoc/files/lib/phusion_passenger/packaging_rb.html +122 -0
- data/doc/rdoc/files/lib/phusion_passenger/platform_info_rb.html +127 -0
- data/doc/rdoc/files/lib/phusion_passenger/rack/application_spawner_rb.html +133 -0
- data/doc/rdoc/files/lib/phusion_passenger/rack/request_handler_rb.html +127 -0
- data/doc/rdoc/files/lib/phusion_passenger/railz/application_spawner_rb.html +143 -0
- data/doc/rdoc/files/lib/phusion_passenger/railz/cgi_fixed_rb.html +126 -0
- data/doc/rdoc/files/lib/phusion_passenger/railz/framework_spawner_rb.html +145 -0
- data/doc/rdoc/files/lib/phusion_passenger/railz/request_handler_rb.html +127 -0
- data/doc/rdoc/files/lib/phusion_passenger/simple_benchmarking_rb.html +122 -0
- data/doc/rdoc/files/lib/phusion_passenger/spawn_manager_rb.html +161 -0
- data/doc/rdoc/files/lib/phusion_passenger/utils_rb.html +175 -0
- data/doc/rdoc/files/lib/phusion_passenger/wsgi/application_spawner_rb.html +129 -0
- data/doc/rdoc/files/misc/rake/extensions_rb.html +130 -0
- data/doc/rdoc/fr_class_index.html +90 -0
- data/doc/rdoc/fr_file_index.html +76 -0
- data/doc/rdoc/fr_method_index.html +200 -0
- data/doc/rdoc/index.html +26 -0
- data/doc/rdoc/rdoc-style.css +187 -0
- data/doc/users_guide_snippets/rackup_specifications.txt +2 -8
- data/ext/apache2/Bucket.cpp +71 -38
- data/ext/apache2/Bucket.h +53 -16
- data/ext/apache2/Configuration.cpp +15 -0
- data/ext/apache2/Configuration.h +19 -2
- data/ext/apache2/DirectoryMapper.h +10 -10
- data/ext/apache2/Hooks.cpp +334 -74
- data/ext/boost/mpl/apply.hpp +5 -1
- data/ext/boost/mpl/apply_wrap.hpp +5 -2
- data/ext/boost/mpl/aux_/full_lambda.hpp +5 -1
- data/ext/boost/mpl/bind.hpp +5 -1
- data/ext/common/Application.h +11 -31
- data/ext/common/ApplicationPool.h +2 -1
- data/ext/common/ApplicationPoolServer.h +61 -20
- data/ext/common/ApplicationPoolServerExecutable.cpp +132 -4
- data/ext/common/ApplicationPoolStatusReporter.h +189 -65
- data/ext/common/Base64.cpp +143 -0
- data/ext/common/Base64.h +57 -0
- data/ext/common/CachedFileStat.cpp +25 -82
- data/ext/common/CachedFileStat.h +11 -125
- data/ext/common/CachedFileStat.hpp +243 -0
- data/ext/common/Exceptions.h +13 -0
- data/ext/common/FileChangeChecker.h +209 -0
- data/ext/common/Logging.h +3 -2
- data/ext/common/MessageChannel.h +10 -10
- data/ext/common/PoolOptions.h +72 -5
- data/ext/common/SpawnManager.h +11 -8
- data/ext/common/StandardApplicationPool.h +38 -39
- data/ext/common/StaticString.h +1 -0
- data/ext/common/StringListCreator.h +83 -0
- data/ext/common/SystemTime.h +3 -2
- data/ext/common/Timer.h +88 -0
- data/ext/common/Utils.cpp +161 -42
- data/ext/common/Utils.h +62 -31
- data/ext/common/Version.h +1 -1
- data/ext/nginx/Configuration.c +0 -4
- data/ext/nginx/ContentHandler.c +8 -6
- data/ext/nginx/HelperServer.cpp +45 -55
- data/ext/nginx/HttpStatusExtractor.h +4 -0
- data/ext/nginx/StaticContentHandler.c +25 -5
- data/ext/nginx/config +3 -0
- data/ext/nginx/ngx_http_passenger_module.c +72 -17
- data/ext/nginx/ngx_http_passenger_module.h +2 -2
- data/lib/phusion_passenger/abstract_request_handler.rb +15 -7
- data/lib/phusion_passenger/abstract_server.rb +16 -2
- data/lib/phusion_passenger/admin_tools/control_process.rb +36 -25
- data/lib/phusion_passenger/constants.rb +1 -1
- data/lib/phusion_passenger/dependencies.rb +10 -0
- data/lib/phusion_passenger/platform_info.rb +1 -1
- data/lib/phusion_passenger/rack/application_spawner.rb +21 -2
- data/lib/phusion_passenger/rack/request_handler.rb +10 -0
- data/lib/phusion_passenger/railz/application_spawner.rb +38 -2
- data/lib/phusion_passenger/railz/framework_spawner.rb +26 -28
- data/lib/phusion_passenger/railz/request_handler.rb +5 -1
- data/lib/phusion_passenger/spawn_manager.rb +6 -2
- data/lib/phusion_passenger/utils.rb +79 -27
- data/misc/rake/cplusplus.rb +5 -5
- data/test/ApplicationPoolServerTest.cpp +42 -0
- data/test/ApplicationPoolTest.cpp +255 -267
- data/test/Base64Test.cpp +48 -0
- data/test/CachedFileStatTest.cpp +243 -103
- data/test/FileChangeCheckerTest.cpp +331 -0
- data/test/PoolOptionsTest.cpp +80 -0
- data/test/UtilsTest.cpp +5 -17
- data/test/integration_tests/apache2_tests.rb +15 -4
- data/test/integration_tests/mycook_spec.rb +3 -4
- data/test/oxt/syscall_interruption_test.cpp +2 -14
- data/test/ruby/abstract_server_collection_spec.rb +1 -1
- data/test/ruby/abstract_server_spec.rb +35 -1
- data/test/ruby/rack/application_spawner_spec.rb +23 -6
- data/test/ruby/rails/application_spawner_spec.rb +6 -6
- data/test/ruby/rails/framework_spawner_spec.rb +6 -5
- data/test/ruby/rails/minimal_spawner_spec.rb +19 -0
- data/test/ruby/rails/spawner_error_handling_spec.rb +62 -7
- data/test/ruby/spawn_manager_spec.rb +10 -7
- data/test/ruby/spawn_server_spec.rb +1 -1
- data/test/ruby/utils_spec.rb +193 -20
- data/test/ruby/wsgi/application_spawner_spec.rb +3 -1
- data/test/stub/apache2/httpd.conf.erb +3 -0
- data/test/stub/rack/config.ru +1 -1
- data/test/stub/rails_apps/mycook/app/controllers/welcome_controller.rb +8 -0
- data/test/support/Support.cpp +84 -0
- data/test/support/Support.h +66 -8
- data/test/support/config.rb +14 -2
- data/test/support/test_helper.rb +5 -0
- data/vendor/rack-1.0.0-git/lib/rack/auth/openid.rb +123 -116
- data/vendor/rack-1.0.0-git/lib/rack/cascade.rb +17 -12
- data/vendor/rack-1.0.0-git/lib/rack/commonlogger.rb +34 -43
- data/vendor/rack-1.0.0-git/lib/rack/handler/cgi.rb +1 -1
- data/vendor/rack-1.0.0-git/lib/rack/handler/fastcgi.rb +1 -1
- data/vendor/rack-1.0.0-git/lib/rack/handler/lsws.rb +1 -1
- data/vendor/rack-1.0.0-git/lib/rack/handler/mongrel.rb +1 -1
- data/vendor/rack-1.0.0-git/lib/rack/handler/scgi.rb +1 -1
- data/vendor/rack-1.0.0-git/lib/rack/handler/webrick.rb +1 -1
- data/vendor/rack-1.0.0-git/lib/rack/mock.rb +4 -17
- data/vendor/rack-1.0.0-git/lib/rack/request.rb +3 -9
- data/vendor/rack-1.0.0-git/lib/rack/rewindable_input.rb +2 -0
- data/vendor/rack-1.0.0-git/lib/rack/utils.rb +38 -12
- metadata +231 -186
- data/ext/common/FileChecker.h +0 -112
- data/test/FileCheckerTest.cpp +0 -79
- data/test/stub/minimal-railsapp/README +0 -3
- data/test/stub/minimal-railsapp/config/application.rb +0 -0
- data/test/stub/minimal-railsapp/config/environment.rb +0 -3
- data/test/stub/minimal-railsapp/vendor/rails/actionmailer/lib/action_mailer.rb +0 -0
- data/test/stub/minimal-railsapp/vendor/rails/actionpack/lib/action_controller.rb +0 -10
- data/test/stub/minimal-railsapp/vendor/rails/actionpack/lib/action_pack.rb +0 -0
- data/test/stub/minimal-railsapp/vendor/rails/actionpack/lib/action_view.rb +0 -0
- data/test/stub/minimal-railsapp/vendor/rails/activerecord/lib/active_record.rb +0 -7
- data/test/stub/minimal-railsapp/vendor/rails/activeresource/lib/active_resource.rb +0 -0
- data/test/stub/minimal-railsapp/vendor/rails/activesupport/lib/active_support.rb +0 -17
- data/test/stub/minimal-railsapp/vendor/rails/activesupport/lib/active_support/whiny_nil.rb +0 -0
- data/test/stub/minimal-railsapp/vendor/rails/railties/lib/dispatcher.rb +0 -0
- data/test/stub/minimal-railsapp/vendor/rails/railties/lib/initializer.rb +0 -8
- data/test/stub/minimal-railsapp/vendor/rails/railties/lib/ruby_version_check.rb +0 -1
- data/test/stub/railsapp/app/controllers/application.rb +0 -12
- data/test/stub/railsapp/app/controllers/bar_controller.rb +0 -5
- data/test/stub/railsapp/app/controllers/bar_controller_1.txt +0 -5
- data/test/stub/railsapp/app/controllers/bar_controller_2.txt +0 -5
- data/test/stub/railsapp/app/controllers/foo_controller.rb +0 -9
- data/test/stub/railsapp/app/helpers/application_helper.rb +0 -3
- data/test/stub/railsapp/config/boot.rb +0 -108
- data/test/stub/railsapp/config/database.yml +0 -19
- data/test/stub/railsapp/config/environment.rb +0 -59
- data/test/stub/railsapp/config/environments/development.rb +0 -18
- data/test/stub/railsapp/config/environments/production.rb +0 -19
- data/test/stub/railsapp/config/initializers/inflections.rb +0 -10
- data/test/stub/railsapp/config/initializers/mime_types.rb +0 -5
- data/test/stub/railsapp/config/routes.rb +0 -35
- data/test/stub/railsapp/public/useless.txt +0 -1
- data/test/stub/railsapp2/app/controllers/application.rb +0 -12
- data/test/stub/railsapp2/app/controllers/foo_controller.rb +0 -5
- data/test/stub/railsapp2/app/helpers/application_helper.rb +0 -3
- data/test/stub/railsapp2/config/boot.rb +0 -108
- data/test/stub/railsapp2/config/database.yml +0 -19
- data/test/stub/railsapp2/config/environment.rb +0 -59
- data/test/stub/railsapp2/config/environments/development.rb +0 -18
- data/test/stub/railsapp2/config/environments/production.rb +0 -19
- data/test/stub/railsapp2/config/initializers/inflections.rb +0 -10
- data/test/stub/railsapp2/config/initializers/mime_types.rb +0 -5
- data/test/stub/railsapp2/config/routes.rb +0 -35
- data/test/stub/railsapp2/public/useless.txt +0 -1
@@ -3,7 +3,7 @@ require 'support/config'
|
|
3
3
|
require 'ruby/abstract_server_spec'
|
4
4
|
|
5
5
|
shared_examples_for "a spawn server" do
|
6
|
-
it_should_behave_like "AbstractServer"
|
6
|
+
it_should_behave_like "an AbstractServer"
|
7
7
|
|
8
8
|
it "raises an AbstractServer::ServerError if the server was killed" do
|
9
9
|
Process.kill('SIGABRT', @spawner.server_pid)
|
data/test/ruby/utils_spec.rb
CHANGED
@@ -2,6 +2,8 @@ require 'support/config'
|
|
2
2
|
|
3
3
|
require 'tmpdir'
|
4
4
|
require 'fileutils'
|
5
|
+
require 'stringio'
|
6
|
+
require 'phusion_passenger/message_channel'
|
5
7
|
require 'phusion_passenger/utils'
|
6
8
|
|
7
9
|
include PhusionPassenger
|
@@ -11,36 +13,204 @@ describe Utils do
|
|
11
13
|
|
12
14
|
specify "#close_all_io_objects_for_fds closes all IO objects that are associated with the given file descriptors" do
|
13
15
|
filename = "#{Dir.tmpdir}/passenger_test.#{Process.pid}.txt"
|
14
|
-
puts "#{$$}: 1"
|
15
16
|
begin
|
16
|
-
pid =
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
close_all_io_objects_for_fds([0, 1, 2])
|
22
|
-
puts "#{$$}: 4"
|
23
|
-
File.open(filename, "w") do |f|
|
24
|
-
f.write("#{a.closed?}, #{b.closed?}")
|
25
|
-
end
|
26
|
-
puts "#{$$}: 5"
|
27
|
-
rescue Exception => e
|
28
|
-
print_exception("utils_spec", e)
|
29
|
-
ensure
|
30
|
-
puts "#{$$}: 6"
|
31
|
-
exit!
|
17
|
+
pid = safe_fork('utils_spec') do
|
18
|
+
a, b = IO.pipe
|
19
|
+
close_all_io_objects_for_fds([0, 1, 2])
|
20
|
+
File.open(filename, "w") do |f|
|
21
|
+
f.write("#{a.closed?}, #{b.closed?}")
|
32
22
|
end
|
33
23
|
end
|
34
|
-
puts "#{$$}: 6"
|
35
24
|
Process.waitpid(pid) rescue nil
|
36
|
-
puts "#{$$}: 7"
|
37
25
|
File.read(filename).should == "true, true"
|
38
26
|
ensure
|
39
|
-
puts "#{$$}: 8"
|
40
27
|
File.unlink(filename) rescue nil
|
41
28
|
end
|
42
29
|
end
|
43
30
|
|
31
|
+
describe "#report_app_init_status" do
|
32
|
+
it "reports normal errors, which #unmarshal_and_raise_errors raises" do
|
33
|
+
a, b = IO.pipe
|
34
|
+
begin
|
35
|
+
pid = safe_fork('utils_spec') do
|
36
|
+
a.close
|
37
|
+
report_app_init_status(MessageChannel.new(b)) do
|
38
|
+
raise RuntimeError, "hello world"
|
39
|
+
end
|
40
|
+
end
|
41
|
+
b.close
|
42
|
+
lambda { unmarshal_and_raise_errors(MessageChannel.new(a)) }.should raise_error(/hello world/)
|
43
|
+
ensure
|
44
|
+
a.close rescue nil
|
45
|
+
b.close rescue nil
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
it "reports SystemExit errors, which #unmarshal_and_raise_errors raises" do
|
50
|
+
a, b = IO.pipe
|
51
|
+
begin
|
52
|
+
pid = safe_fork('utils_spec') do
|
53
|
+
a.close
|
54
|
+
report_app_init_status(MessageChannel.new(b)) do
|
55
|
+
exit
|
56
|
+
end
|
57
|
+
end
|
58
|
+
b.close
|
59
|
+
lambda { unmarshal_and_raise_errors(MessageChannel.new(a)) }.should raise_error(/exited during startup/)
|
60
|
+
ensure
|
61
|
+
a.close rescue nil
|
62
|
+
b.close rescue nil
|
63
|
+
end
|
64
|
+
end
|
65
|
+
|
66
|
+
it "returns whether the block succeeded" do
|
67
|
+
channel = MessageChannel.new(StringIO.new)
|
68
|
+
success = report_app_init_status(channel) do
|
69
|
+
false
|
70
|
+
end
|
71
|
+
success.should be_true
|
72
|
+
|
73
|
+
success = report_app_init_status(channel) do
|
74
|
+
raise StandardError, "hi"
|
75
|
+
end
|
76
|
+
success.should be_false
|
77
|
+
end
|
78
|
+
|
79
|
+
it "reports all data written to stderr" do
|
80
|
+
a, b = IO.pipe
|
81
|
+
begin
|
82
|
+
pid = safe_fork('utils_spec') do
|
83
|
+
a.close
|
84
|
+
report_app_init_status(MessageChannel.new(b)) do
|
85
|
+
STDERR.puts "Something went wrong!"
|
86
|
+
exit
|
87
|
+
end
|
88
|
+
end
|
89
|
+
b.close
|
90
|
+
|
91
|
+
begin
|
92
|
+
unmarshal_and_raise_errors(MessageChannel.new(a))
|
93
|
+
violated "No exception raised"
|
94
|
+
rescue AppInitError => e
|
95
|
+
e.stderr.should =~ /Something went wrong!/
|
96
|
+
end
|
97
|
+
ensure
|
98
|
+
a.close rescue nil
|
99
|
+
b.close rescue nil
|
100
|
+
end
|
101
|
+
end
|
102
|
+
|
103
|
+
it "writes all buffered stderr data to the 'write_stderr_contents_to' argument if the block failed" do
|
104
|
+
stderr_buffer = StringIO.new
|
105
|
+
report_app_init_status(MessageChannel.new(StringIO.new), stderr_buffer) do
|
106
|
+
STDERR.puts "Something went wrong!"
|
107
|
+
raise StandardError, ":-("
|
108
|
+
end
|
109
|
+
|
110
|
+
stderr_buffer.string.should =~ /Something went wrong!/
|
111
|
+
end
|
112
|
+
|
113
|
+
it "writes all buffered stderr data to the 'write_stderr_contents_to' argument if the block succeeded" do
|
114
|
+
stderr_buffer = StringIO.new
|
115
|
+
report_app_init_status(MessageChannel.new(StringIO.new), stderr_buffer) do
|
116
|
+
STDERR.puts "Something went wrong!"
|
117
|
+
end
|
118
|
+
|
119
|
+
stderr_buffer.string.should =~ /Something went wrong!/
|
120
|
+
end
|
121
|
+
end
|
122
|
+
|
123
|
+
specify "#safe_fork with double_fork == false reseeds the pseudo-random number generator" do
|
124
|
+
a, b = IO.pipe
|
125
|
+
begin
|
126
|
+
pid = safe_fork do
|
127
|
+
b.puts(rand)
|
128
|
+
end
|
129
|
+
Process.waitpid(pid) rescue nil
|
130
|
+
pid = safe_fork do
|
131
|
+
b.puts(rand)
|
132
|
+
end
|
133
|
+
Process.waitpid(pid) rescue nil
|
134
|
+
|
135
|
+
first_num = a.readline
|
136
|
+
second_num = a.readline
|
137
|
+
first_num.should_not == second_num
|
138
|
+
ensure
|
139
|
+
a.close rescue nil
|
140
|
+
b.close rescue nil
|
141
|
+
end
|
142
|
+
end
|
143
|
+
|
144
|
+
specify "#safe_fork with double_fork == true reseeds the pseudo-random number generator" do
|
145
|
+
a, b = IO.pipe
|
146
|
+
begin
|
147
|
+
# Seed the pseudo-random number generator here
|
148
|
+
# so that it doesn't happen in the child processes.
|
149
|
+
srand
|
150
|
+
|
151
|
+
safe_fork(self.class, true) do
|
152
|
+
b.puts(rand)
|
153
|
+
end
|
154
|
+
safe_fork(self.class, true) do
|
155
|
+
b.puts(rand)
|
156
|
+
end
|
157
|
+
|
158
|
+
first_num = a.readline
|
159
|
+
second_num = a.readline
|
160
|
+
first_num.should_not == second_num
|
161
|
+
ensure
|
162
|
+
a.close rescue nil
|
163
|
+
b.close rescue nil
|
164
|
+
end
|
165
|
+
end
|
166
|
+
|
167
|
+
describe "#unmarshal_and_raise_errors" do
|
168
|
+
before :each do
|
169
|
+
@a, @b = IO.pipe
|
170
|
+
@report_channel = MessageChannel.new(@a)
|
171
|
+
report_app_init_status(MessageChannel.new(@b)) do
|
172
|
+
raise StandardError, "Something went wrong!"
|
173
|
+
end
|
174
|
+
end
|
175
|
+
|
176
|
+
after :each do
|
177
|
+
@a.close rescue nil
|
178
|
+
@b.close rescue nil
|
179
|
+
end
|
180
|
+
|
181
|
+
it "prints the exception information to the 'print_exception' argument using #puts, if 'print_exception' responds to that" do
|
182
|
+
buffer = StringIO.new
|
183
|
+
lambda { unmarshal_and_raise_errors(@report_channel, buffer) }.should raise_error(AppInitError)
|
184
|
+
buffer.string.should =~ /Something went wrong!/
|
185
|
+
buffer.string.should =~ /utils\.rb/
|
186
|
+
buffer.string.should =~ /utils_spec\.rb/
|
187
|
+
end
|
188
|
+
|
189
|
+
it "appends the exception information to the file pointed to by 'print_exception', if 'print_exception' responds to #to_str" do
|
190
|
+
begin
|
191
|
+
lambda { unmarshal_and_raise_errors(@report_channel, "exception.txt") }.should raise_error(AppInitError)
|
192
|
+
data = File.read('exception.txt')
|
193
|
+
data.should =~ /Something went wrong!/
|
194
|
+
data.should =~ /utils\.rb/
|
195
|
+
data.should =~ /utils_spec\.rb/
|
196
|
+
ensure
|
197
|
+
File.unlink('exception.txt') rescue nil
|
198
|
+
end
|
199
|
+
end
|
200
|
+
end
|
201
|
+
|
202
|
+
specify "#to_boolean works" do
|
203
|
+
to_boolean(nil).should be_false
|
204
|
+
to_boolean(false).should be_false
|
205
|
+
to_boolean(true).should be_true
|
206
|
+
to_boolean(1).should be_true
|
207
|
+
to_boolean(0).should be_true
|
208
|
+
to_boolean("").should be_true
|
209
|
+
to_boolean("true").should be_true
|
210
|
+
to_boolean("false").should be_false
|
211
|
+
to_boolean("bla bla").should be_true
|
212
|
+
end
|
213
|
+
|
44
214
|
describe "#passenger_tmpdir" do
|
45
215
|
before :each do
|
46
216
|
@old_passenger_tmpdir = Utils.passenger_tmpdir
|
@@ -71,8 +241,11 @@ describe Utils do
|
|
71
241
|
begin
|
72
242
|
File.directory?('utils_spec.tmp').should be_true
|
73
243
|
ensure
|
244
|
+
FileUtils.chmod_R(0777, 'utils_spec.tmp')
|
74
245
|
FileUtils.rm_rf('utils_spec.tmp')
|
75
246
|
end
|
76
247
|
end
|
77
248
|
end
|
249
|
+
|
250
|
+
######################
|
78
251
|
end
|
@@ -5,6 +5,8 @@ require 'phusion_passenger/utils'
|
|
5
5
|
require 'fileutils'
|
6
6
|
require 'tempfile'
|
7
7
|
|
8
|
+
include PhusionPassenger
|
9
|
+
|
8
10
|
describe PhusionPassenger::WSGI::ApplicationSpawner do
|
9
11
|
include TestHelper
|
10
12
|
include PhusionPassenger::Utils
|
@@ -39,7 +41,7 @@ describe PhusionPassenger::WSGI::ApplicationSpawner do
|
|
39
41
|
|
40
42
|
specify "the backend process deletes its socket upon termination" do
|
41
43
|
spawn(@stub.app_root).close
|
42
|
-
sleep 0.
|
44
|
+
sleep 0.25 # Give it some time to terminate.
|
43
45
|
File.chmod(0700, "#{passenger_tmpdir}/backends")
|
44
46
|
Dir["#{passenger_tmpdir}/backends/wsgi_backend.*"].should be_empty
|
45
47
|
end
|
@@ -23,6 +23,9 @@ Listen 127.0.0.1:<%= @port %>
|
|
23
23
|
<% if !has_builtin_module?('mod_rewrite.c') && has_module?('mod_rewrite.so') %>
|
24
24
|
LoadModule rewrite_module "<%= modules_dir %>/mod_rewrite.so"
|
25
25
|
<% end %>
|
26
|
+
<% if !has_builtin_module?('mod_env.c') %>
|
27
|
+
LoadModule env_module "<%= modules_dir %>/mod_env.so"
|
28
|
+
<% end %>
|
26
29
|
LoadModule passenger_module "<%= @mod_passenger %>"
|
27
30
|
|
28
31
|
PassengerRoot "<%= @passenger_root %>"
|
data/test/stub/rack/config.ru
CHANGED
@@ -40,6 +40,14 @@ class WelcomeController < ApplicationController
|
|
40
40
|
def show_id
|
41
41
|
render :text => params[:id]
|
42
42
|
end
|
43
|
+
|
44
|
+
def environment
|
45
|
+
text = ""
|
46
|
+
ENV.each_pair do |key, value|
|
47
|
+
text << "#{key} = #{value}\n"
|
48
|
+
end
|
49
|
+
render :text => text
|
50
|
+
end
|
43
51
|
|
44
52
|
def request_uri
|
45
53
|
render :text => request.request_uri
|
@@ -0,0 +1,84 @@
|
|
1
|
+
#include <unistd.h>
|
2
|
+
#include "Support.h"
|
3
|
+
|
4
|
+
namespace Test {
|
5
|
+
|
6
|
+
string
|
7
|
+
readAll(int fd) {
|
8
|
+
string result;
|
9
|
+
char buf[1024 * 32];
|
10
|
+
ssize_t ret;
|
11
|
+
while (true) {
|
12
|
+
do {
|
13
|
+
ret = read(fd, buf, sizeof(buf));
|
14
|
+
} while (ret == -1 && errno == EINTR);
|
15
|
+
if (ret == 0) {
|
16
|
+
break;
|
17
|
+
} else if (ret == -1) {
|
18
|
+
throw SystemException("Cannot read from socket", errno);
|
19
|
+
} else {
|
20
|
+
result.append(buf, ret);
|
21
|
+
}
|
22
|
+
}
|
23
|
+
return result;
|
24
|
+
}
|
25
|
+
|
26
|
+
string
|
27
|
+
replaceString(const string &str, const string &toFind, const string &replaceWith) {
|
28
|
+
string::size_type pos = str.find(toFind);
|
29
|
+
if (pos == string::npos) {
|
30
|
+
return str;
|
31
|
+
} else {
|
32
|
+
string result(str);
|
33
|
+
return result.replace(pos, toFind.size(), replaceWith);
|
34
|
+
}
|
35
|
+
}
|
36
|
+
|
37
|
+
void
|
38
|
+
replaceStringInFile(const char *filename, const string &toFind, const string &replaceWith) {
|
39
|
+
FILE *f = fopen(filename, "r");
|
40
|
+
if (f == NULL) {
|
41
|
+
int e = errno;
|
42
|
+
string message = "Cannot open file '";
|
43
|
+
message.append(filename);
|
44
|
+
message.append("' for reading");
|
45
|
+
throw FileSystemException(message, e, filename);
|
46
|
+
}
|
47
|
+
string content(readAll(fileno(f)));
|
48
|
+
fclose(f);
|
49
|
+
|
50
|
+
f = fopen(filename, "w");
|
51
|
+
if (f == NULL) {
|
52
|
+
int e = errno;
|
53
|
+
string message = "Cannot open file '";
|
54
|
+
message.append(filename);
|
55
|
+
message.append("' for writing");
|
56
|
+
throw FileSystemException(message, e, filename);
|
57
|
+
}
|
58
|
+
content = replaceString(content, toFind, replaceWith);
|
59
|
+
fwrite(content.data(), 1, content.size(), f);
|
60
|
+
fclose(f);
|
61
|
+
}
|
62
|
+
|
63
|
+
void
|
64
|
+
touchFile(const char *filename, time_t timestamp) {
|
65
|
+
FILE *f = fopen(filename, "a");
|
66
|
+
if (f != NULL) {
|
67
|
+
fclose(f);
|
68
|
+
} else if (errno != EISDIR) {
|
69
|
+
int e = errno;
|
70
|
+
string message = "Cannot touch file '";
|
71
|
+
message.append(filename);
|
72
|
+
message.append("'");
|
73
|
+
throw FileSystemException(message, e, filename);
|
74
|
+
}
|
75
|
+
|
76
|
+
if (timestamp != (time_t) -1) {
|
77
|
+
struct utimbuf times;
|
78
|
+
times.actime = timestamp;
|
79
|
+
times.modtime = timestamp;
|
80
|
+
utime(filename, ×);
|
81
|
+
}
|
82
|
+
}
|
83
|
+
|
84
|
+
} // namespace Test
|
data/test/support/Support.h
CHANGED
@@ -6,12 +6,49 @@
|
|
6
6
|
#include <iostream>
|
7
7
|
#include <string>
|
8
8
|
#include <exception>
|
9
|
+
#include <cstdio>
|
9
10
|
#include <cerrno>
|
10
11
|
#include <cstring>
|
12
|
+
#include <utime.h>
|
13
|
+
|
14
|
+
#include "Exceptions.h"
|
15
|
+
#include "Utils.h"
|
11
16
|
|
12
17
|
namespace Test {
|
13
18
|
|
14
19
|
using namespace std;
|
20
|
+
using namespace Passenger;
|
21
|
+
|
22
|
+
/**
|
23
|
+
* Read all data from the given file descriptor until EOF.
|
24
|
+
*
|
25
|
+
* @throws SystemException
|
26
|
+
*/
|
27
|
+
string readAll(int fd);
|
28
|
+
|
29
|
+
/**
|
30
|
+
* Look for 'toFind' inside 'str', replace it with 'replaceWith' and return the result.
|
31
|
+
* Only the first occurence of 'toFind' is replaced.
|
32
|
+
*/
|
33
|
+
string replaceString(const string &str, const string &toFind, const string &replaceWith);
|
34
|
+
|
35
|
+
/**
|
36
|
+
* Look for 'toFind' inside the given file, replace it with 'replaceWith' and write
|
37
|
+
* the result back to the file. Only the first occurence of 'toFind' is replaced.
|
38
|
+
*
|
39
|
+
* @throws FileSystemException
|
40
|
+
*/
|
41
|
+
void replaceStringInFile(const char *filename, const string &toFind, const string &replaceWith);
|
42
|
+
|
43
|
+
/**
|
44
|
+
* Touch the given file: create the file if it doesn't exist, update its
|
45
|
+
* timestamp if it does. If the <tt>timestamp</tt> argument is -1, then
|
46
|
+
* the current system time will be used, otherwise the given timestamp
|
47
|
+
* will be used.
|
48
|
+
*
|
49
|
+
* @throws FileSystemException
|
50
|
+
*/
|
51
|
+
void touchFile(const char *filename, time_t timestamp = (time_t) - 1);
|
15
52
|
|
16
53
|
/**
|
17
54
|
* Class which creates a temporary directory of the given name, and deletes
|
@@ -25,17 +62,38 @@ public:
|
|
25
62
|
this->name = name;
|
26
63
|
if (mkdir(name.c_str(), S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH) != 0) {
|
27
64
|
int e = errno;
|
28
|
-
|
29
|
-
|
30
|
-
|
65
|
+
string message = "Cannot create directory '";
|
66
|
+
message.append(name);
|
67
|
+
message.append("'");
|
68
|
+
throw FileSystemException(message, e, name);
|
31
69
|
}
|
32
70
|
}
|
33
71
|
|
34
72
|
~TempDir() {
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
73
|
+
removeDirTree(name);
|
74
|
+
}
|
75
|
+
};
|
76
|
+
|
77
|
+
/**
|
78
|
+
* Creates a temporary copy of the given directory. This copy is deleted
|
79
|
+
* upon object destruction.
|
80
|
+
*/
|
81
|
+
class TempDirCopy {
|
82
|
+
private:
|
83
|
+
string dir;
|
84
|
+
public:
|
85
|
+
TempDirCopy(const string &source, const string &dest) {
|
86
|
+
dir = dest;
|
87
|
+
removeDirTree(dest);
|
88
|
+
|
89
|
+
char command[1024];
|
90
|
+
snprintf(command, sizeof(command), "cp -pR \"%s\" \"%s\"",
|
91
|
+
source.c_str(), dest.c_str());
|
92
|
+
system(command);
|
93
|
+
}
|
94
|
+
|
95
|
+
~TempDirCopy() {
|
96
|
+
removeDirTree(dir);
|
39
97
|
}
|
40
98
|
};
|
41
99
|
|
@@ -50,7 +108,7 @@ public:
|
|
50
108
|
this->filename = filename;
|
51
109
|
}
|
52
110
|
|
53
|
-
DeleteFileEventually() {
|
111
|
+
~DeleteFileEventually() {
|
54
112
|
unlink(filename.c_str());
|
55
113
|
}
|
56
114
|
};
|