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
data/ext/common/Logging.h
CHANGED
@@ -64,8 +64,9 @@ void setDebugFile(const char *logFile = NULL);
|
|
64
64
|
strftime(datetime_buf, sizeof(datetime_buf), "%F %H:%M:%S", the_tm); \
|
65
65
|
gettimeofday(&tv, NULL); \
|
66
66
|
sstream << \
|
67
|
-
"[ pid=" << getpid() <<
|
68
|
-
"
|
67
|
+
"[ pid=" << ((unsigned long) getpid()) << \
|
68
|
+
" file=" << __FILE__ << ":" << (unsigned long) __LINE__ << \
|
69
|
+
" time=" << datetime_buf << "." << (unsigned long) (tv.tv_usec / 1000) << " ]:" << \
|
69
70
|
"\n " << expr << std::endl; \
|
70
71
|
*stream << sstream.str(); \
|
71
72
|
stream->flush(); \
|
data/ext/common/MessageChannel.h
CHANGED
@@ -570,11 +570,11 @@ public:
|
|
570
570
|
ret = syscalls::setsockopt(fd, SOL_SOCKET, SO_RCVTIMEO,
|
571
571
|
&tv, sizeof(tv));
|
572
572
|
#ifndef __SOLARIS__
|
573
|
-
|
574
|
-
|
575
|
-
|
576
|
-
|
577
|
-
|
573
|
+
// SO_RCVTIMEO is unimplemented and returns an error on Solaris
|
574
|
+
// 9 and 10 SPARC. Seems to work okay without it.
|
575
|
+
if (ret == -1) {
|
576
|
+
throw SystemException("Cannot set read timeout for socket", errno);
|
577
|
+
}
|
578
578
|
#endif
|
579
579
|
}
|
580
580
|
|
@@ -601,11 +601,11 @@ public:
|
|
601
601
|
ret = syscalls::setsockopt(fd, SOL_SOCKET, SO_SNDTIMEO,
|
602
602
|
&tv, sizeof(tv));
|
603
603
|
#ifndef __SOLARIS__
|
604
|
-
|
605
|
-
|
606
|
-
|
607
|
-
|
608
|
-
|
604
|
+
// SO_SNDTIMEO is unimplemented and returns an error on Solaris
|
605
|
+
// 9 and 10 SPARC. Seems to work okay without it.
|
606
|
+
if (ret == -1) {
|
607
|
+
throw SystemException("Cannot set read timeout for socket", errno);
|
608
|
+
}
|
609
609
|
#endif
|
610
610
|
}
|
611
611
|
};
|
data/ext/common/PoolOptions.h
CHANGED
@@ -26,7 +26,8 @@
|
|
26
26
|
#define _PASSENGER_SPAWN_OPTIONS_H_
|
27
27
|
|
28
28
|
#include <string>
|
29
|
-
#include
|
29
|
+
#include <vector>
|
30
|
+
#include "StringListCreator.h"
|
30
31
|
|
31
32
|
namespace Passenger {
|
32
33
|
|
@@ -147,6 +148,29 @@ struct PoolOptions {
|
|
147
148
|
*/
|
148
149
|
string restartDir;
|
149
150
|
|
151
|
+
/**
|
152
|
+
* If a new backend process is started, then the getItems() method
|
153
|
+
* on this object will be called, which is to return environment
|
154
|
+
* variables that should be passed to the newly spawned backend process.
|
155
|
+
* Odd indices in the resulting array contain keys, even indices contain
|
156
|
+
* the value for the key in the previous index.
|
157
|
+
*
|
158
|
+
* May be set to NULL.
|
159
|
+
*
|
160
|
+
* @invariant environmentVariables.size() is an even number.
|
161
|
+
*/
|
162
|
+
StringListCreatorPtr environmentVariables;
|
163
|
+
|
164
|
+
/**
|
165
|
+
* The base URI on which the application runs. If the application is
|
166
|
+
* running on the root URI, then this value must be "/".
|
167
|
+
*
|
168
|
+
* @invariant baseURI != ""
|
169
|
+
*/
|
170
|
+
string baseURI;
|
171
|
+
|
172
|
+
/*********************************/
|
173
|
+
|
150
174
|
/**
|
151
175
|
* Creates a new PoolOptions object with the default values filled in.
|
152
176
|
* One must still set appRoot manually, after having used this constructor.
|
@@ -163,6 +187,7 @@ struct PoolOptions {
|
|
163
187
|
memoryLimit = 0;
|
164
188
|
useGlobalQueue = false;
|
165
189
|
statThrottleRate = 0;
|
190
|
+
baseURI = "/";
|
166
191
|
}
|
167
192
|
|
168
193
|
/**
|
@@ -180,7 +205,8 @@ struct PoolOptions {
|
|
180
205
|
unsigned long memoryLimit = 0,
|
181
206
|
bool useGlobalQueue = false,
|
182
207
|
unsigned long statThrottleRate = 0,
|
183
|
-
const string &restartDir = ""
|
208
|
+
const string &restartDir = "",
|
209
|
+
const string &baseURI = "/"
|
184
210
|
) {
|
185
211
|
this->appRoot = appRoot;
|
186
212
|
this->lowerPrivilege = lowerPrivilege;
|
@@ -195,6 +221,7 @@ struct PoolOptions {
|
|
195
221
|
this->useGlobalQueue = useGlobalQueue;
|
196
222
|
this->statThrottleRate = statThrottleRate;
|
197
223
|
this->restartDir = restartDir;
|
224
|
+
this->baseURI = baseURI;
|
198
225
|
}
|
199
226
|
|
200
227
|
/**
|
@@ -230,16 +257,24 @@ struct PoolOptions {
|
|
230
257
|
useGlobalQueue = vec[startIndex + 21] == "true";
|
231
258
|
statThrottleRate = atol(vec[startIndex + 23]);
|
232
259
|
restartDir = vec[startIndex + 25];
|
260
|
+
baseURI = vec[startIndex + 27];
|
261
|
+
if (vec.size() > startIndex + 29) {
|
262
|
+
environmentVariables = ptr(new SimpleStringListCreator(vec[startIndex + 29]));
|
263
|
+
}
|
233
264
|
}
|
234
265
|
|
235
266
|
/**
|
236
267
|
* Append the information in this PoolOptions object to the given
|
237
268
|
* string vector. The resulting array could, for example, be used
|
238
269
|
* as a message to be sent to the spawn server.
|
270
|
+
*
|
271
|
+
* @param vec The vector to store the information in.
|
272
|
+
* @param storeEnvVars Whether to store environment variable information into vec as well.
|
273
|
+
* @throws Anything thrown by environmentVariables->getItems().
|
239
274
|
*/
|
240
|
-
void toVector(vector<string> &vec) const {
|
241
|
-
if (vec.capacity() < vec.size() +
|
242
|
-
vec.reserve(vec.size() +
|
275
|
+
void toVector(vector<string> &vec, bool storeEnvVars = true) const {
|
276
|
+
if (vec.capacity() < vec.size() + 30) {
|
277
|
+
vec.reserve(vec.size() + 30);
|
243
278
|
}
|
244
279
|
appendKeyValue (vec, "app_root", appRoot);
|
245
280
|
appendKeyValue (vec, "lower_privilege", lowerPrivilege ? "true" : "false");
|
@@ -254,6 +289,38 @@ struct PoolOptions {
|
|
254
289
|
appendKeyValue (vec, "use_global_queue", useGlobalQueue ? "true" : "false");
|
255
290
|
appendKeyValue3(vec, "stat_throttle_rate", statThrottleRate);
|
256
291
|
appendKeyValue (vec, "restart_dir", restartDir);
|
292
|
+
appendKeyValue (vec, "base_uri", baseURI);
|
293
|
+
if (storeEnvVars) {
|
294
|
+
vec.push_back("environment_variables");
|
295
|
+
vec.push_back(serializeEnvironmentVariables());
|
296
|
+
}
|
297
|
+
}
|
298
|
+
|
299
|
+
/**
|
300
|
+
* Serializes the items in environmentVariables into a string, which
|
301
|
+
* can be used to create a SimpleStringListCreator object.
|
302
|
+
*
|
303
|
+
* @throws Anything thrown by environmentVariables->getItems().
|
304
|
+
*/
|
305
|
+
string serializeEnvironmentVariables() const {
|
306
|
+
vector<string>::const_iterator it, end;
|
307
|
+
string result;
|
308
|
+
|
309
|
+
if (environmentVariables) {
|
310
|
+
result.reserve(1024);
|
311
|
+
|
312
|
+
StringListPtr items = environmentVariables->getItems();
|
313
|
+
end = items->end();
|
314
|
+
|
315
|
+
for (it = items->begin(); it != end; it++) {
|
316
|
+
result.append(*it);
|
317
|
+
result.append(1, '\0');
|
318
|
+
it++;
|
319
|
+
result.append(*it);
|
320
|
+
result.append(1, '\0');
|
321
|
+
}
|
322
|
+
}
|
323
|
+
return Base64::encode(result);
|
257
324
|
}
|
258
325
|
|
259
326
|
private:
|
data/ext/common/SpawnManager.h
CHANGED
@@ -265,15 +265,16 @@ private:
|
|
265
265
|
* @param PoolOptions The spawn options to use.
|
266
266
|
* @return An Application smart pointer, representing the spawned application.
|
267
267
|
* @throws SpawnException Something went wrong.
|
268
|
+
* @throws Anything thrown by options.environmentVariables->getItems().
|
268
269
|
*/
|
269
|
-
ApplicationPtr sendSpawnCommand(const PoolOptions &
|
270
|
+
ApplicationPtr sendSpawnCommand(const PoolOptions &options) {
|
270
271
|
TRACE_POINT();
|
271
272
|
vector<string> args;
|
272
273
|
int ownerPipe;
|
273
274
|
|
274
275
|
try {
|
275
276
|
args.push_back("spawn_application");
|
276
|
-
|
277
|
+
options.toVector(args);
|
277
278
|
channel.write(args);
|
278
279
|
} catch (const SystemException &e) {
|
279
280
|
throw SpawnException(string("Could not write 'spawn_application' "
|
@@ -346,15 +347,16 @@ private:
|
|
346
347
|
ret = chown(args[1].c_str(), getuid(), getgid());
|
347
348
|
} while (ret == -1 && errno == EINTR);
|
348
349
|
}
|
349
|
-
return ApplicationPtr(new Application(
|
350
|
+
return ApplicationPtr(new Application(options.appRoot,
|
350
351
|
pid, args[1], args[2], ownerPipe));
|
351
352
|
}
|
352
353
|
|
353
354
|
/**
|
354
355
|
* @throws boost::thread_interrupted
|
356
|
+
* @throws Anything thrown by options.environmentVariables->getItems().
|
355
357
|
*/
|
356
358
|
ApplicationPtr
|
357
|
-
handleSpawnException(const SpawnException &e, const PoolOptions &
|
359
|
+
handleSpawnException(const SpawnException &e, const PoolOptions &options) {
|
358
360
|
TRACE_POINT();
|
359
361
|
bool restarted;
|
360
362
|
try {
|
@@ -371,7 +373,7 @@ private:
|
|
371
373
|
restarted = false;
|
372
374
|
}
|
373
375
|
if (restarted) {
|
374
|
-
return sendSpawnCommand(
|
376
|
+
return sendSpawnCommand(options);
|
375
377
|
} else {
|
376
378
|
throw SpawnException("The spawn server died unexpectedly, and restarting it failed.");
|
377
379
|
}
|
@@ -500,17 +502,18 @@ public:
|
|
500
502
|
* spawned application.
|
501
503
|
* @throws SpawnException Something went wrong.
|
502
504
|
* @throws boost::thread_interrupted
|
505
|
+
* @throws Anything thrown by options.environmentVariables->getItems().
|
503
506
|
*/
|
504
|
-
ApplicationPtr spawn(const PoolOptions &
|
507
|
+
ApplicationPtr spawn(const PoolOptions &options) {
|
505
508
|
TRACE_POINT();
|
506
509
|
boost::mutex::scoped_lock l(lock);
|
507
510
|
try {
|
508
|
-
return sendSpawnCommand(
|
511
|
+
return sendSpawnCommand(options);
|
509
512
|
} catch (const SpawnException &e) {
|
510
513
|
if (e.hasErrorPage()) {
|
511
514
|
throw;
|
512
515
|
} else {
|
513
|
-
return handleSpawnException(e,
|
516
|
+
return handleSpawnException(e, options);
|
514
517
|
}
|
515
518
|
}
|
516
519
|
}
|
@@ -52,8 +52,8 @@
|
|
52
52
|
|
53
53
|
#include "ApplicationPool.h"
|
54
54
|
#include "Logging.h"
|
55
|
-
#include "
|
56
|
-
#include "CachedFileStat.
|
55
|
+
#include "FileChangeChecker.h"
|
56
|
+
#include "CachedFileStat.hpp"
|
57
57
|
#ifdef PASSENGER_USE_DUMMY_SPAWN_MANAGER
|
58
58
|
#include "DummySpawnManager.h"
|
59
59
|
#else
|
@@ -121,25 +121,6 @@ private:
|
|
121
121
|
AppContainerList instances;
|
122
122
|
unsigned int size;
|
123
123
|
unsigned long maxRequests;
|
124
|
-
FileChecker restartFileChecker;
|
125
|
-
CachedFileStat alwaysRestartFileStatter;
|
126
|
-
|
127
|
-
Domain(const PoolOptions &options)
|
128
|
-
: restartFileChecker(determineRestartDir(options) + "/restart.txt"),
|
129
|
-
alwaysRestartFileStatter(determineRestartDir(options) + "/always_restart.txt")
|
130
|
-
{
|
131
|
-
}
|
132
|
-
|
133
|
-
private:
|
134
|
-
static string determineRestartDir(const PoolOptions &options) {
|
135
|
-
if (options.restartDir.empty()) {
|
136
|
-
return options.appRoot + "/tmp";
|
137
|
-
} else if (options.restartDir[0] == '/') {
|
138
|
-
return options.restartDir;
|
139
|
-
} else {
|
140
|
-
return options.appRoot + "/" + options.restartDir;
|
141
|
-
}
|
142
|
-
}
|
143
124
|
};
|
144
125
|
|
145
126
|
struct AppContainer {
|
@@ -267,6 +248,8 @@ private:
|
|
267
248
|
unsigned int maxIdleTime;
|
268
249
|
unsigned int waitingOnGlobalQueue;
|
269
250
|
condition cleanerThreadSleeper;
|
251
|
+
CachedFileStat cstat;
|
252
|
+
FileChangeChecker fileChangeChecker;
|
270
253
|
|
271
254
|
// Shortcuts for instance variables in SharedData. Saves typing in get().
|
272
255
|
boost::mutex &lock;
|
@@ -364,12 +347,24 @@ private:
|
|
364
347
|
/**
|
365
348
|
* Checks whether the given application domain needs to be restarted.
|
366
349
|
*
|
367
|
-
* @throws
|
350
|
+
* @throws TimeRetrievalException Something went wrong while retrieving the system time.
|
368
351
|
* @throws boost::thread_interrupted
|
369
352
|
*/
|
370
|
-
bool needsRestart(const string &appRoot,
|
371
|
-
|
372
|
-
|
353
|
+
bool needsRestart(const string &appRoot, const PoolOptions &options) {
|
354
|
+
string restartDir;
|
355
|
+
if (options.restartDir.empty()) {
|
356
|
+
restartDir = appRoot + "/tmp";
|
357
|
+
} else if (options.restartDir[0] == '/') {
|
358
|
+
restartDir = options.restartDir;
|
359
|
+
} else {
|
360
|
+
restartDir = appRoot + "/" + options.restartDir;
|
361
|
+
}
|
362
|
+
|
363
|
+
string alwaysRestartFile = restartDir + "/always_restart.txt";
|
364
|
+
string restartFile = restartDir + "/restart.txt";
|
365
|
+
struct stat buf;
|
366
|
+
return cstat.stat(alwaysRestartFile, &buf, options.statThrottleRate) == 0 ||
|
367
|
+
fileChangeChecker.changed(restartFile, options.statThrottleRate);
|
373
368
|
}
|
374
369
|
|
375
370
|
void cleanerThreadMainLoop() {
|
@@ -430,6 +425,7 @@ private:
|
|
430
425
|
* @throws boost::thread_interrupted
|
431
426
|
* @throws SpawnException
|
432
427
|
* @throws SystemException
|
428
|
+
* @throws TimeRetrievalException Something went wrong while retrieving the system time.
|
433
429
|
*/
|
434
430
|
pair<AppContainerPtr, Domain *>
|
435
431
|
spawnOrUseExisting(boost::mutex::scoped_lock &l, const PoolOptions &options) {
|
@@ -446,21 +442,24 @@ private:
|
|
446
442
|
try {
|
447
443
|
DomainMap::iterator it(domains.find(appRoot));
|
448
444
|
|
449
|
-
if (
|
450
|
-
|
451
|
-
|
452
|
-
|
453
|
-
|
454
|
-
|
455
|
-
|
456
|
-
|
457
|
-
|
445
|
+
if (needsRestart(appRoot, options)) {
|
446
|
+
if (it != domains.end()) {
|
447
|
+
AppContainerList::iterator it2;
|
448
|
+
instances = &it->second->instances;
|
449
|
+
for (it2 = instances->begin(); it2 != instances->end(); it2++) {
|
450
|
+
container = *it2;
|
451
|
+
if (container->sessions == 0) {
|
452
|
+
inactiveApps.erase(container->ia_iterator);
|
453
|
+
} else {
|
454
|
+
active--;
|
455
|
+
}
|
456
|
+
it2--;
|
457
|
+
instances->erase(container->iterator);
|
458
|
+
count--;
|
458
459
|
}
|
459
|
-
|
460
|
-
instances->erase(container->iterator);
|
461
|
-
count--;
|
460
|
+
domains.erase(appRoot);
|
462
461
|
}
|
463
|
-
|
462
|
+
P_DEBUG("Restarting " << appRoot);
|
464
463
|
spawnManager.reload(appRoot);
|
465
464
|
it = domains.end();
|
466
465
|
activeOrMaxChanged.notify_all();
|
@@ -548,7 +547,7 @@ private:
|
|
548
547
|
container->sessions = 0;
|
549
548
|
it = domains.find(appRoot);
|
550
549
|
if (it == domains.end()) {
|
551
|
-
domain = new Domain(
|
550
|
+
domain = new Domain();
|
552
551
|
domain->size = 1;
|
553
552
|
domain->maxRequests = options.maxRequests;
|
554
553
|
domains[appRoot] = ptr(domain);
|
data/ext/common/StaticString.h
CHANGED
@@ -0,0 +1,83 @@
|
|
1
|
+
/*
|
2
|
+
* Phusion Passenger - http://www.modrails.com/
|
3
|
+
* Copyright (c) 2009 Phusion
|
4
|
+
*
|
5
|
+
* "Phusion Passenger" is a trademark of Hongli Lai & Ninh Bui.
|
6
|
+
*
|
7
|
+
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
8
|
+
* of this software and associated documentation files (the "Software"), to deal
|
9
|
+
* in the Software without restriction, including without limitation the rights
|
10
|
+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
11
|
+
* copies of the Software, and to permit persons to whom the Software is
|
12
|
+
* furnished to do so, subject to the following conditions:
|
13
|
+
*
|
14
|
+
* The above copyright notice and this permission notice shall be included in
|
15
|
+
* all copies or substantial portions of the Software.
|
16
|
+
*
|
17
|
+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
18
|
+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
19
|
+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
20
|
+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
21
|
+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
22
|
+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
23
|
+
* THE SOFTWARE.
|
24
|
+
*/
|
25
|
+
#ifndef _PASSENGER_STRING_LIST_CREATOR_H_
|
26
|
+
#define _PASSENGER_STRING_LIST_CREATOR_H_
|
27
|
+
|
28
|
+
#include <string>
|
29
|
+
#include <vector>
|
30
|
+
#include <boost/shared_ptr.hpp>
|
31
|
+
#include "Base64.h"
|
32
|
+
#include "Utils.h"
|
33
|
+
|
34
|
+
namespace Passenger {
|
35
|
+
|
36
|
+
using namespace std;
|
37
|
+
using namespace boost;
|
38
|
+
|
39
|
+
typedef vector<string> StringList;
|
40
|
+
typedef shared_ptr<StringList> StringListPtr;
|
41
|
+
|
42
|
+
|
43
|
+
class StringListCreator {
|
44
|
+
public:
|
45
|
+
virtual ~StringListCreator() {}
|
46
|
+
|
47
|
+
/** May throw arbitrary exceptions. */
|
48
|
+
virtual const StringListPtr getItems() const = 0;
|
49
|
+
};
|
50
|
+
|
51
|
+
typedef shared_ptr<StringListCreator> StringListCreatorPtr;
|
52
|
+
|
53
|
+
class SimpleStringListCreator: public StringListCreator {
|
54
|
+
public:
|
55
|
+
StringListPtr items;
|
56
|
+
|
57
|
+
SimpleStringListCreator() {
|
58
|
+
items = ptr(new StringList());
|
59
|
+
}
|
60
|
+
|
61
|
+
SimpleStringListCreator(const StaticString &data) {
|
62
|
+
items = ptr(new StringList());
|
63
|
+
string buffer = Base64::decode(data);
|
64
|
+
if (!buffer.empty()) {
|
65
|
+
string::size_type start = 0, pos;
|
66
|
+
const string &const_buffer(buffer);
|
67
|
+
while ((pos = const_buffer.find('\0', start)) != string::npos) {
|
68
|
+
items->push_back(const_buffer.substr(start, pos - start));
|
69
|
+
start = pos + 1;
|
70
|
+
}
|
71
|
+
}
|
72
|
+
}
|
73
|
+
|
74
|
+
virtual const StringListPtr getItems() const {
|
75
|
+
return items;
|
76
|
+
}
|
77
|
+
};
|
78
|
+
|
79
|
+
typedef shared_ptr<SimpleStringListCreator> SimpleStringListCreatorPtr;
|
80
|
+
|
81
|
+
} // namespace Passenger
|
82
|
+
|
83
|
+
#endif /* _PASSENGER_STRING_LIST_CREATOR_H_ */
|