passenger 5.0.21 → 5.0.22
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.
- checksums.yaml +8 -8
- checksums.yaml.gz.asc +7 -7
- data.tar.gz.asc +7 -7
- data/CHANGELOG +38 -2
- data/CONTRIBUTORS +3 -0
- data/README.md +5 -1
- data/bin/passenger-status +2 -7
- data/build/agent.rb +2 -0
- data/build/cxx_dependency_map.rb +1464 -162
- data/build/node_tests.rb +1 -1
- data/build/packaging.rb +1 -1
- data/dev/ci/run_travis.sh +1 -1
- data/dev/vagrant/provision.sh +1 -1
- data/npm-shrinkwrap.json +635 -125
- data/package.json +1 -1
- data/resources/templates/standalone/config.erb +33 -161
- data/resources/templates/standalone/global.erb +15 -0
- data/resources/templates/standalone/http.erb +40 -0
- data/resources/templates/standalone/mass_deployment_default_server.erb +11 -0
- data/resources/templates/standalone/rails_asset_pipeline.erb +22 -0
- data/resources/templates/standalone/server.erb +58 -0
- data/src/agent/Core/ApiServer.h +37 -32
- data/src/agent/Core/ApplicationPool/BasicGroupInfo.h +1 -1
- data/src/agent/Core/ApplicationPool/BasicProcessInfo.h +6 -0
- data/src/agent/Core/ApplicationPool/Common.h +1 -1
- data/src/agent/Core/ApplicationPool/Group/OutOfBandWork.cpp +1 -1
- data/src/agent/Core/ApplicationPool/Group/ProcessListManagement.cpp +4 -0
- data/src/agent/Core/ApplicationPool/Implementation.cpp +2 -2
- data/src/agent/Core/ApplicationPool/Options.h +18 -1
- data/src/agent/Core/ApplicationPool/Pool.h +1 -1
- data/src/agent/Core/ApplicationPool/Pool/AnalyticsCollection.cpp +6 -6
- data/src/agent/Core/ApplicationPool/Pool/GeneralUtils.cpp +3 -3
- data/src/agent/Core/ApplicationPool/Pool/InitializationAndShutdown.cpp +1 -1
- data/src/agent/Core/ApplicationPool/Pool/Miscellaneous.cpp +6 -0
- data/src/agent/Core/ApplicationPool/Process.h +6 -1
- data/src/agent/Core/ApplicationPool/Socket.h +9 -12
- data/src/agent/Core/Controller.h +422 -0
- data/src/agent/Core/{RequestHandler → Controller}/AppResponse.h +2 -0
- data/src/agent/Core/{RequestHandler → Controller}/BufferBody.cpp +27 -5
- data/src/agent/Core/{RequestHandler → Controller}/CheckoutSession.cpp +61 -31
- data/src/agent/Core/{RequestHandler → Controller}/Client.h +5 -2
- data/src/agent/Core/{RequestHandler → Controller}/ForwardResponse.cpp +93 -42
- data/src/agent/Core/{RequestHandler → Controller}/Hooks.cpp +107 -60
- data/src/agent/Core/Controller/Implementation.cpp +38 -0
- data/src/agent/Core/{RequestHandler → Controller}/InitRequest.cpp +134 -80
- data/src/agent/Core/Controller/InitializationAndShutdown.cpp +165 -0
- data/src/agent/Core/{RequestHandler/Utils.cpp → Controller/InternalUtils.cpp} +49 -32
- data/src/agent/Core/Controller/Miscellaneous.cpp +116 -0
- data/src/agent/Core/{RequestHandler → Controller}/Request.h +6 -4
- data/src/agent/Core/{RequestHandler → Controller}/SendRequest.cpp +205 -130
- data/src/agent/Core/Controller/StateInspectionAndConfiguration.cpp +161 -0
- data/src/agent/Core/{RequestHandler → Controller}/TurboCaching.h +3 -0
- data/src/agent/Core/CoreMain.cpp +62 -51
- data/src/agent/Core/OptionParser.h +24 -0
- data/src/agent/Core/ResponseCache.h +5 -5
- data/src/agent/Core/SpawningKit/Config.h +2 -2
- data/src/agent/Core/SpawningKit/SmartSpawner.h +1 -1
- data/src/agent/Core/UnionStation/{Core.h → Context.h} +14 -18
- data/src/agent/Core/UnionStation/StopwatchLog.h +3 -2
- data/src/agent/Core/UnionStation/Transaction.h +7 -7
- data/src/agent/Shared/ApiServerUtils.h +9 -1
- data/src/agent/UstRouter/ApiServer.h +5 -2
- data/src/agent/UstRouter/Controller.h +27 -9
- data/src/agent/UstRouter/UstRouterMain.cpp +1 -0
- data/src/agent/Watchdog/ApiServer.h +5 -2
- data/src/apache2_module/ConfigurationCommands.cpp +7 -0
- data/src/apache2_module/ConfigurationFields.hpp +2 -0
- data/src/apache2_module/ConfigurationSetters.cpp +24 -0
- data/src/apache2_module/CreateDirConfig.cpp +1 -0
- data/src/apache2_module/Hooks.cpp +6 -5
- data/src/apache2_module/MergeDirConfig.cpp +7 -0
- data/src/apache2_module/SetHeaders.cpp +5 -0
- data/src/cxx_supportlib/Constants.h +5 -3
- data/src/cxx_supportlib/SafeLibev.h +2 -1
- data/src/cxx_supportlib/UnionStationFilterSupport.h +2 -1
- data/src/cxx_supportlib/Utils/ReleaseableScopedPointer.h +70 -0
- data/src/cxx_supportlib/vendor-modified/boost/libs/regex/src/regex_raw_buffer.cpp +6 -6
- data/src/helper-scripts/node-loader.js +59 -0
- data/src/nginx_module/CacheLocationConfig.c +48 -0
- data/src/nginx_module/ConfigurationCommands.c +20 -0
- data/src/nginx_module/ConfigurationFields.h +4 -0
- data/src/nginx_module/CreateLocationConfig.c +8 -0
- data/src/nginx_module/MergeLocationConfig.c +12 -0
- data/src/nodejs_supportlib/phusion_passenger/log_express.js +106 -0
- data/src/nodejs_supportlib/phusion_passenger/log_mongodb.js +203 -0
- data/src/nodejs_supportlib/phusion_passenger/ustreporter.js +227 -0
- data/src/nodejs_supportlib/phusion_passenger/ustrouter_connector.js +446 -0
- data/src/nodejs_supportlib/vendor-copy/codify/codify.js +44 -0
- data/src/nodejs_supportlib/vendor-copy/codify/package.json +29 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/context.js +200 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/async-listener/glue.js +488 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/async-listener/index.js +407 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/async-listener/node_modules/shimmer/index.js +90 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/async-listener/node_modules/shimmer/package.json +40 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/async-listener/package.json +54 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/emitter-listener/listener.js +160 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/emitter-listener/node_modules/shimmer/index.js +90 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/emitter-listener/node_modules/shimmer/package.json +40 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/node_modules/emitter-listener/package.json +46 -0
- data/src/nodejs_supportlib/vendor-copy/continuation-local-storage/package.json +56 -0
- data/src/nodejs_supportlib/vendor-copy/network-byte-order/lib/index.js +102 -0
- data/src/nodejs_supportlib/vendor-copy/network-byte-order/package.json +51 -0
- data/src/nodejs_supportlib/vendor-copy/winston/LICENSE +19 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston.js +165 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/common.js +483 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/config.js +62 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/config/cli-config.js +35 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/config/npm-config.js +27 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/config/syslog-config.js +31 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/container.js +127 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/exception.js +56 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/logger.js +701 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/transports.js +34 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/transports/console.js +128 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/transports/daily-rotate-file.js +601 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/transports/file.js +675 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/transports/http.js +232 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/transports/memory.js +89 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/transports/transport.js +135 -0
- data/src/nodejs_supportlib/vendor-copy/winston/lib/winston/transports/webhook.js +146 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/async/LICENSE +19 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/async/lib/async.js +1283 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/async/package.json +66 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/async/support/sync-package-managers.js +53 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/MIT-LICENSE.txt +23 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/colors.js +176 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/custom/trap.js +45 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/custom/zalgo.js +104 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/extendStringPrototype.js +118 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/index.js +12 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/maps/america.js +12 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/maps/rainbow.js +13 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/maps/random.js +8 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/maps/zebra.js +5 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/styles.js +77 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/lib/system/supports-colors.js +61 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/package.json +35 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/safe.js +9 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/colors/themes/generic-logging.js +12 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/cycle/cycle.js +170 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/cycle/package.json +30 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/eyes/LICENSE +20 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/eyes/lib/eyes.js +236 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/eyes/package.json +42 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/isstream/LICENSE.md +11 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/isstream/isstream.js +27 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/isstream/package.json +42 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/pkginfo/LICENSE +19 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/pkginfo/lib/pkginfo.js +136 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/pkginfo/package.json +56 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/stack-trace/License +19 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/stack-trace/lib/stack-trace.js +111 -0
- data/src/nodejs_supportlib/vendor-copy/winston/node_modules/stack-trace/package.json +33 -0
- data/src/nodejs_supportlib/vendor-copy/winston/package.json +87 -0
- data/src/ruby_supportlib/phusion_passenger.rb +3 -4
- data/src/ruby_supportlib/phusion_passenger/admin_tools/instance.rb +19 -2
- data/src/ruby_supportlib/phusion_passenger/apache2/config_options.rb +8 -0
- data/src/ruby_supportlib/phusion_passenger/config/list_instances_command.rb +2 -6
- data/src/ruby_supportlib/phusion_passenger/config/reopen_logs_command.rb +13 -0
- data/src/ruby_supportlib/phusion_passenger/config/restart_app_command.rb +3 -0
- data/src/ruby_supportlib/phusion_passenger/config/utils.rb +9 -7
- data/src/ruby_supportlib/phusion_passenger/config/validate_install_command.rb +8 -1
- data/src/ruby_supportlib/phusion_passenger/constants.rb +3 -1
- data/src/ruby_supportlib/phusion_passenger/native_support.rb +20 -4
- data/src/ruby_supportlib/phusion_passenger/nginx/config_options.rb +8 -0
- data/src/ruby_supportlib/phusion_passenger/packaging.rb +1 -0
- data/src/ruby_supportlib/phusion_passenger/platform_info/apache_detector.rb +1 -1
- data/src/ruby_supportlib/phusion_passenger/platform_info/operating_system.rb +11 -4
- data/src/ruby_supportlib/phusion_passenger/rack/thread_handler_extension.rb +1 -1
- data/src/ruby_supportlib/phusion_passenger/standalone/config_options_list.rb +647 -0
- data/src/ruby_supportlib/phusion_passenger/standalone/config_utils.rb +229 -15
- data/src/ruby_supportlib/phusion_passenger/standalone/start_command.rb +35 -323
- data/src/ruby_supportlib/phusion_passenger/standalone/start_command/builtin_engine.rb +36 -12
- data/src/ruby_supportlib/phusion_passenger/standalone/start_command/nginx_engine.rb +123 -14
- data/src/ruby_supportlib/phusion_passenger/standalone/status_command.rb +32 -17
- data/src/ruby_supportlib/phusion_passenger/standalone/stop_command.rb +32 -21
- data/src/ruby_supportlib/phusion_passenger/standalone/version_command.rb +5 -5
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/README.md +2 -2
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/Rakefile +5 -1
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core.rb +68 -24
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core/api.rb +9 -1
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core/context.rb +9 -7
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core/request_reporter.rb +3 -2
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core/request_reporter/basics.rb +8 -5
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core/simple_json.rb +395 -0
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core/transaction.rb +10 -7
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core/utils.rb +14 -0
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/lib/union_station_hooks_core/version_data.rb +2 -2
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/ruby_versions.yml +4 -2
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/ruby_versions.yml.example +2 -2
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/ruby_versions.yml.travis +2 -2
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_core/ruby_versions.yml.travis-with-sudo +16 -0
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_rails/Gemfile +1 -1
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_rails/Gemfile.lock +2 -2
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_rails/README.md +1 -1
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_rails/lib/union_station_hooks_rails.rb +44 -17
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_rails/lib/union_station_hooks_rails/active_support_cache_subscriber.rb +16 -7
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_rails/lib/union_station_hooks_rails/version_data.rb +2 -2
- data/src/ruby_supportlib/phusion_passenger/vendor/union_station_hooks_rails/union_station_hooks_rails.gemspec +1 -1
- metadata +99 -16
- metadata.gz.asc +7 -7
- data/resources/oss-binaries.phusionpassenger.com.crt +0 -248
- data/src/agent/Core/RequestHandler.h +0 -471
@@ -46,7 +46,7 @@ class Group;
|
|
46
46
|
*
|
47
47
|
* Since Process and Session sometimes need to look up this basic group
|
48
48
|
* information, this struct also serves to ensure that Process and Session do
|
49
|
-
* not have a direct dependency on Group, but on
|
49
|
+
* not have a direct dependency on Group, but on BasicGroupInfo instead.
|
50
50
|
*/
|
51
51
|
class BasicGroupInfo {
|
52
52
|
public:
|
@@ -92,6 +92,12 @@ public:
|
|
92
92
|
: process(_process),
|
93
93
|
groupInfo(_groupInfo),
|
94
94
|
pid(getJsonIntField(json, "pid"))
|
95
|
+
// We initialize this in Process::initializeStickySessionId(),
|
96
|
+
// called from Group::attach().
|
97
|
+
// We should probably some day refactor this. The reason we do
|
98
|
+
// it the way we do right now is because some day we want to be able
|
99
|
+
// to attach external processes, so the best place to initialize this
|
100
|
+
// information is in Group::attach().
|
95
101
|
//stickySessionId(getJsonUintField(json, "sticky_session_id", 0))
|
96
102
|
{
|
97
103
|
StaticString gupid = getJsonStaticStringField(json, "gupid");
|
@@ -39,7 +39,7 @@
|
|
39
39
|
#include <Utils/VariantMap.h>
|
40
40
|
#include <Core/ApplicationPool/Options.h>
|
41
41
|
#include <Core/SpawningKit/Config.h>
|
42
|
-
#include <Core/UnionStation/
|
42
|
+
#include <Core/UnionStation/Context.h>
|
43
43
|
#include <Core/UnionStation/Transaction.h>
|
44
44
|
|
45
45
|
namespace tut {
|
@@ -225,7 +225,7 @@ Group::spawnThreadOOBWRequest(GroupPtr self, ProcessPtr process) {
|
|
225
225
|
connection.fail = true;
|
226
226
|
ScopeGuard guard(boost::bind(&Socket::checkinConnection, socket, connection));
|
227
227
|
|
228
|
-
// This is copied from
|
228
|
+
// This is copied from Core::Controller when it is sending data using the
|
229
229
|
// "session" protocol.
|
230
230
|
char sizeField[sizeof(boost::uint32_t)];
|
231
231
|
SmallVector<StaticString, 10> data;
|
@@ -411,6 +411,10 @@ Group::attach(const ProcessPtr &process,
|
|
411
411
|
}
|
412
412
|
|
413
413
|
process->initializeStickySessionId(generateStickySessionId());
|
414
|
+
if (options.forceMaxConcurrentRequestsPerProcess != -1) {
|
415
|
+
process->forceMaxConcurrency(options.forceMaxConcurrentRequestsPerProcess);
|
416
|
+
}
|
417
|
+
|
414
418
|
P_DEBUG("Attaching process " << process->inspect());
|
415
419
|
addProcessToList(process, enabledProcesses);
|
416
420
|
|
@@ -175,10 +175,10 @@ void processAndLogNewSpawnException(SpawnException &e, const Options &options,
|
|
175
175
|
char filename[PATH_MAX];
|
176
176
|
stringstream stream;
|
177
177
|
|
178
|
-
if (options.analytics && config->
|
178
|
+
if (options.analytics && config->unionStationContext != NULL) {
|
179
179
|
try {
|
180
180
|
UPDATE_TRACE_POINT();
|
181
|
-
transaction = config->
|
181
|
+
transaction = config->unionStationContext->newTransaction(
|
182
182
|
options.getAppGroupName(),
|
183
183
|
"exceptions",
|
184
184
|
options.unionStationKey);
|
@@ -36,7 +36,7 @@
|
|
36
36
|
#include <ResourceLocator.h>
|
37
37
|
#include <StaticString.h>
|
38
38
|
#include <Utils.h>
|
39
|
-
#include <Core/UnionStation/
|
39
|
+
#include <Core/UnionStation/Context.h>
|
40
40
|
#include <Core/UnionStation/Transaction.h>
|
41
41
|
|
42
42
|
namespace Passenger {
|
@@ -281,6 +281,15 @@ public:
|
|
281
281
|
*/
|
282
282
|
StaticString environmentVariables;
|
283
283
|
|
284
|
+
/**
|
285
|
+
* If set to a value that isn't -1, makes Passenger ignore the application's
|
286
|
+
* advertised socket concurrency, and believe that the concurrency should be
|
287
|
+
* the given value.
|
288
|
+
*
|
289
|
+
* Defaults to -1.
|
290
|
+
*/
|
291
|
+
int forceMaxConcurrentRequestsPerProcess;
|
292
|
+
|
284
293
|
/** Whether debugger support should be enabled. */
|
285
294
|
bool debugger;
|
286
295
|
|
@@ -350,6 +359,12 @@ public:
|
|
350
359
|
*/
|
351
360
|
unsigned int maxRequestQueueSize;
|
352
361
|
|
362
|
+
/**
|
363
|
+
* Whether websocket connections should be aborted on process shutdown
|
364
|
+
* or restart.
|
365
|
+
*/
|
366
|
+
bool abortWebsocketsOnProcessShutdown;
|
367
|
+
|
353
368
|
/**
|
354
369
|
* The Union Station key to use in case analytics logging is enabled.
|
355
370
|
* It is used by Pool::collectAnalytics() and other administrative
|
@@ -461,6 +476,7 @@ public:
|
|
461
476
|
ruby(DEFAULT_RUBY, sizeof(DEFAULT_RUBY) - 1),
|
462
477
|
python(DEFAULT_PYTHON, sizeof(DEFAULT_PYTHON) - 1),
|
463
478
|
nodejs(DEFAULT_NODEJS, sizeof(DEFAULT_NODEJS) - 1),
|
479
|
+
forceMaxConcurrentRequestsPerProcess(-1),
|
464
480
|
debugger(false),
|
465
481
|
loadShellEnvvars(true),
|
466
482
|
userSwitching(true),
|
@@ -472,6 +488,7 @@ public:
|
|
472
488
|
maxPreloaderIdleTime(-1),
|
473
489
|
maxOutOfBandWorkInstances(1),
|
474
490
|
maxRequestQueueSize(100),
|
491
|
+
abortWebsocketsOnProcessShutdown(true),
|
475
492
|
|
476
493
|
stickySessionId(0),
|
477
494
|
statThrottleRate(DEFAULT_STAT_THROTTLE_RATE),
|
@@ -405,7 +405,7 @@ public:
|
|
405
405
|
|
406
406
|
Context *getContext();
|
407
407
|
const SpawningKit::ConfigPtr &getSpawningKitConfig() const;
|
408
|
-
const UnionStation::
|
408
|
+
const UnionStation::ContextPtr &getUnionStationContext() const;
|
409
409
|
const RandomGeneratorPtr &getRandomGenerator() const;
|
410
410
|
|
411
411
|
|
@@ -112,8 +112,8 @@ void
|
|
112
112
|
Pool::prepareUnionStationProcessStateLogs(vector<UnionStationLogEntry> &logEntries,
|
113
113
|
const GroupPtr &group) const
|
114
114
|
{
|
115
|
-
const UnionStation::
|
116
|
-
if (group->options.analytics &&
|
115
|
+
const UnionStation::ContextPtr &unionStationContext = getUnionStationContext();
|
116
|
+
if (group->options.analytics && unionStationContext != NULL) {
|
117
117
|
logEntries.push_back(UnionStationLogEntry());
|
118
118
|
UnionStationLogEntry &entry = logEntries.back();
|
119
119
|
stringstream stream;
|
@@ -133,8 +133,8 @@ void
|
|
133
133
|
Pool::prepareUnionStationSystemMetricsLogs(vector<UnionStationLogEntry> &logEntries,
|
134
134
|
const GroupPtr &group) const
|
135
135
|
{
|
136
|
-
const UnionStation::
|
137
|
-
if (group->options.analytics &&
|
136
|
+
const UnionStation::ContextPtr &unionStationContext = getUnionStationContext();
|
137
|
+
if (group->options.analytics && unionStationContext != NULL) {
|
138
138
|
logEntries.push_back(UnionStationLogEntry());
|
139
139
|
UnionStationLogEntry &entry = logEntries.back();
|
140
140
|
stringstream stream;
|
@@ -228,12 +228,12 @@ Pool::realCollectAnalytics() {
|
|
228
228
|
l.unlock();
|
229
229
|
UPDATE_TRACE_POINT();
|
230
230
|
if (!logEntries.empty()) {
|
231
|
-
const UnionStation::
|
231
|
+
const UnionStation::ContextPtr &unionStationContext = getUnionStationContext();
|
232
232
|
P_DEBUG("Sending process and system metrics to Union Station");
|
233
233
|
while (!logEntries.empty()) {
|
234
234
|
UnionStationLogEntry &entry = logEntries.back();
|
235
235
|
UnionStation::TransactionPtr transaction =
|
236
|
-
|
236
|
+
unionStationContext->newTransaction(
|
237
237
|
entry.groupName,
|
238
238
|
entry.category,
|
239
239
|
entry.key);
|
@@ -227,9 +227,9 @@ Pool::getSpawningKitConfig() const {
|
|
227
227
|
return context.getSpawningKitConfig();
|
228
228
|
}
|
229
229
|
|
230
|
-
const UnionStation::
|
231
|
-
Pool::
|
232
|
-
return getSpawningKitConfig()->
|
230
|
+
const UnionStation::ContextPtr &
|
231
|
+
Pool::getUnionStationContext() const {
|
232
|
+
return getSpawningKitConfig()->unionStationContext;
|
233
233
|
}
|
234
234
|
|
235
235
|
const RandomGeneratorPtr &
|
@@ -91,7 +91,7 @@ Pool::initDebugging() {
|
|
91
91
|
* Should be called right after the agent has received
|
92
92
|
* the message to exit gracefully. This will tell processes to
|
93
93
|
* abort any long-running connections, e.g. WebSocket connections,
|
94
|
-
* because the
|
94
|
+
* because the Core::Controller has to wait until all connections are
|
95
95
|
* finished before proceeding with shutdown.
|
96
96
|
*/
|
97
97
|
void
|
@@ -25,6 +25,12 @@
|
|
25
25
|
*/
|
26
26
|
#include <Core/ApplicationPool/Pool.h>
|
27
27
|
|
28
|
+
/*************************************************************************
|
29
|
+
*
|
30
|
+
* Miscellaneous functions for ApplicationPool2::Pool
|
31
|
+
*
|
32
|
+
*************************************************************************/
|
33
|
+
|
28
34
|
namespace Passenger {
|
29
35
|
namespace ApplicationPool2 {
|
30
36
|
|
@@ -293,7 +293,7 @@ private:
|
|
293
293
|
Socket *socket = &(*it);
|
294
294
|
if (socket->protocol == "session" || socket->protocol == "http_session") {
|
295
295
|
if (sessionSocketCount == MAX_SESSION_SOCKETS) {
|
296
|
-
throw RuntimeException("The process has many session sockets. "
|
296
|
+
throw RuntimeException("The process has too many session sockets. "
|
297
297
|
"A maximum of " + toString(MAX_SESSION_SOCKETS) + " is allowed");
|
298
298
|
}
|
299
299
|
sessionSockets[sessionSocketCount] = socket;
|
@@ -480,6 +480,11 @@ public:
|
|
480
480
|
info.stickySessionId = value;
|
481
481
|
}
|
482
482
|
|
483
|
+
void forceMaxConcurrency(int value) {
|
484
|
+
assert(value >= 0);
|
485
|
+
concurrency = value;
|
486
|
+
}
|
487
|
+
|
483
488
|
void shutdownNotRequired() {
|
484
489
|
requiresShutdown = false;
|
485
490
|
}
|
@@ -226,20 +226,17 @@ public:
|
|
226
226
|
int busyness() const {
|
227
227
|
/* Different sockets within a Process may have different
|
228
228
|
* 'concurrency' values. We want:
|
229
|
-
* -
|
230
|
-
* - to give sockets with concurrency == 0 more priority
|
231
|
-
* with concurrency > 0.
|
232
|
-
* Therefore,
|
233
|
-
*
|
229
|
+
* - the socket with the smallest busyness to be be picked for routing.
|
230
|
+
* - to give sockets with concurrency == 0 more priority (in general)
|
231
|
+
* over sockets with concurrency > 0.
|
232
|
+
* Therefore, in case of sockets with concurrency > 0, we describe our
|
233
|
+
* busyness as a percentage of 'concurrency', with the percentage value
|
234
|
+
* in [0..INT_MAX] instead of [0..1]. That way, the busyness value
|
235
|
+
* of sockets with concurrency > 0 is usually higher than that of sockets
|
236
|
+
* with concurrency == 0.
|
234
237
|
*/
|
235
238
|
if (concurrency == 0) {
|
236
|
-
|
237
|
-
// idle sockets more priority.
|
238
|
-
if (sessions == 0) {
|
239
|
-
return 0;
|
240
|
-
} else {
|
241
|
-
return 1;
|
242
|
-
}
|
239
|
+
return sessions;
|
243
240
|
} else {
|
244
241
|
return (int) (((long long) sessions * INT_MAX) / (double) concurrency);
|
245
242
|
}
|
@@ -0,0 +1,422 @@
|
|
1
|
+
/*
|
2
|
+
* Phusion Passenger - https://www.phusionpassenger.com/
|
3
|
+
* Copyright (c) 2011-2015 Phusion Holding B.V.
|
4
|
+
*
|
5
|
+
* "Passenger", "Phusion Passenger" and "Union Station" are registered
|
6
|
+
* trademarks of Phusion Holding B.V.
|
7
|
+
*
|
8
|
+
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
9
|
+
* of this software and associated documentation files (the "Software"), to deal
|
10
|
+
* in the Software without restriction, including without limitation the rights
|
11
|
+
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
12
|
+
* copies of the Software, and to permit persons to whom the Software is
|
13
|
+
* furnished to do so, subject to the following conditions:
|
14
|
+
*
|
15
|
+
* The above copyright notice and this permission notice shall be included in
|
16
|
+
* all copies or substantial portions of the Software.
|
17
|
+
*
|
18
|
+
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
19
|
+
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
20
|
+
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
21
|
+
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
22
|
+
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
23
|
+
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
24
|
+
* THE SOFTWARE.
|
25
|
+
*/
|
26
|
+
|
27
|
+
#ifndef _PASSENGER_CORE_CONTROLLER_H_
|
28
|
+
#define _PASSENGER_CORE_CONTROLLER_H_
|
29
|
+
|
30
|
+
|
31
|
+
//#define DEBUG_CC_EVENT_LOOP_BLOCKING
|
32
|
+
|
33
|
+
#define CC_BENCHMARK_POINT(client, req, value) \
|
34
|
+
do { \
|
35
|
+
if (OXT_UNLIKELY(benchmarkMode == value)) { \
|
36
|
+
writeBenchmarkResponse(&client, &req); \
|
37
|
+
return; \
|
38
|
+
} \
|
39
|
+
} while (false)
|
40
|
+
|
41
|
+
|
42
|
+
#include <boost/shared_ptr.hpp>
|
43
|
+
#include <boost/make_shared.hpp>
|
44
|
+
#include <boost/cstdint.hpp>
|
45
|
+
#include <oxt/macros.hpp>
|
46
|
+
#include <ev++.h>
|
47
|
+
#include <ostream>
|
48
|
+
|
49
|
+
#if defined(__GLIBCXX__) || defined(__APPLE__)
|
50
|
+
#include <cxxabi.h>
|
51
|
+
#define CXX_ABI_API_AVAILABLE
|
52
|
+
#endif
|
53
|
+
|
54
|
+
#include <sys/types.h>
|
55
|
+
#include <sys/uio.h>
|
56
|
+
#include <utility>
|
57
|
+
#include <typeinfo>
|
58
|
+
#include <cstdio>
|
59
|
+
#include <cstdlib>
|
60
|
+
#include <cstddef>
|
61
|
+
#include <cassert>
|
62
|
+
#include <cctype>
|
63
|
+
|
64
|
+
#include <Logging.h>
|
65
|
+
#include <MessageReadersWriters.h>
|
66
|
+
#include <Constants.h>
|
67
|
+
#include <ServerKit/Errors.h>
|
68
|
+
#include <ServerKit/HttpServer.h>
|
69
|
+
#include <ServerKit/HttpHeaderParser.h>
|
70
|
+
#include <MemoryKit/palloc.h>
|
71
|
+
#include <DataStructures/LString.h>
|
72
|
+
#include <DataStructures/StringKeyTable.h>
|
73
|
+
#include <StaticString.h>
|
74
|
+
#include <Utils.h>
|
75
|
+
#include <Utils/StrIntUtils.h>
|
76
|
+
#include <Utils/IOUtils.h>
|
77
|
+
#include <Utils/JsonUtils.h>
|
78
|
+
#include <Utils/HttpConstants.h>
|
79
|
+
#include <Utils/VariantMap.h>
|
80
|
+
#include <Utils/Timer.h>
|
81
|
+
#include <Core/ApplicationPool/ErrorRenderer.h>
|
82
|
+
#include <Core/Controller/Client.h>
|
83
|
+
#include <Core/Controller/AppResponse.h>
|
84
|
+
#include <Core/Controller/TurboCaching.h>
|
85
|
+
#include <Core/UnionStation/Context.h>
|
86
|
+
|
87
|
+
namespace Passenger {
|
88
|
+
|
89
|
+
using namespace std;
|
90
|
+
using namespace boost;
|
91
|
+
using namespace oxt;
|
92
|
+
using namespace ApplicationPool2;
|
93
|
+
|
94
|
+
|
95
|
+
namespace ServerKit {
|
96
|
+
extern const HashedStaticString HTTP_COOKIE;
|
97
|
+
extern const HashedStaticString HTTP_SET_COOKIE;
|
98
|
+
}
|
99
|
+
|
100
|
+
namespace Core {
|
101
|
+
|
102
|
+
|
103
|
+
class Controller: public ServerKit::HttpServer<Controller, Client> {
|
104
|
+
public:
|
105
|
+
enum BenchmarkMode {
|
106
|
+
BM_NONE,
|
107
|
+
BM_AFTER_ACCEPT,
|
108
|
+
BM_BEFORE_CHECKOUT,
|
109
|
+
BM_AFTER_CHECKOUT,
|
110
|
+
BM_RESPONSE_BEGIN,
|
111
|
+
BM_UNKNOWN
|
112
|
+
};
|
113
|
+
|
114
|
+
private:
|
115
|
+
typedef ServerKit::HttpServer<Controller, Client> ParentClass;
|
116
|
+
typedef ServerKit::Channel Channel;
|
117
|
+
typedef ServerKit::FdSinkChannel FdSinkChannel;
|
118
|
+
typedef ServerKit::FdSourceChannel FdSourceChannel;
|
119
|
+
typedef ServerKit::FileBufferedChannel FileBufferedChannel;
|
120
|
+
typedef ServerKit::FileBufferedFdSinkChannel FileBufferedFdSinkChannel;
|
121
|
+
|
122
|
+
static const unsigned int MAX_SESSION_CHECKOUT_TRY = 10;
|
123
|
+
|
124
|
+
unsigned int statThrottleRate;
|
125
|
+
unsigned int responseBufferHighWatermark;
|
126
|
+
BenchmarkMode benchmarkMode: 3;
|
127
|
+
bool singleAppMode: 1;
|
128
|
+
bool showVersionInHeader: 1;
|
129
|
+
bool stickySessions: 1;
|
130
|
+
bool gracefulExit: 1;
|
131
|
+
|
132
|
+
const VariantMap *agentsOptions;
|
133
|
+
psg_pool_t *stringPool;
|
134
|
+
StringKeyTable< boost::shared_ptr<Options> > poolOptionsCache;
|
135
|
+
|
136
|
+
StaticString defaultRuby;
|
137
|
+
StaticString ustRouterAddress;
|
138
|
+
StaticString ustRouterPassword;
|
139
|
+
StaticString defaultUser;
|
140
|
+
StaticString defaultGroup;
|
141
|
+
StaticString defaultServerName;
|
142
|
+
StaticString defaultServerPort;
|
143
|
+
StaticString serverSoftware;
|
144
|
+
StaticString defaultStickySessionsCookieName;
|
145
|
+
StaticString defaultVaryTurbocacheByCookie;
|
146
|
+
|
147
|
+
HashedStaticString PASSENGER_APP_GROUP_NAME;
|
148
|
+
HashedStaticString PASSENGER_ENV_VARS;
|
149
|
+
HashedStaticString PASSENGER_MAX_REQUESTS;
|
150
|
+
HashedStaticString PASSENGER_STICKY_SESSIONS;
|
151
|
+
HashedStaticString PASSENGER_STICKY_SESSIONS_COOKIE_NAME;
|
152
|
+
HashedStaticString PASSENGER_REQUEST_OOB_WORK;
|
153
|
+
HashedStaticString UNION_STATION_SUPPORT;
|
154
|
+
HashedStaticString REMOTE_ADDR;
|
155
|
+
HashedStaticString REMOTE_PORT;
|
156
|
+
HashedStaticString REMOTE_USER;
|
157
|
+
HashedStaticString FLAGS;
|
158
|
+
HashedStaticString HTTP_COOKIE;
|
159
|
+
HashedStaticString HTTP_DATE;
|
160
|
+
HashedStaticString HTTP_HOST;
|
161
|
+
HashedStaticString HTTP_CONTENT_LENGTH;
|
162
|
+
HashedStaticString HTTP_CONTENT_TYPE;
|
163
|
+
HashedStaticString HTTP_EXPECT;
|
164
|
+
HashedStaticString HTTP_CONNECTION;
|
165
|
+
HashedStaticString HTTP_STATUS;
|
166
|
+
HashedStaticString HTTP_TRANSFER_ENCODING;
|
167
|
+
|
168
|
+
unsigned int threadNumber;
|
169
|
+
StaticString serverLogName;
|
170
|
+
|
171
|
+
friend class TurboCaching<Request>;
|
172
|
+
friend class ResponseCache<Request>;
|
173
|
+
struct ev_check checkWatcher;
|
174
|
+
TurboCaching<Request> turboCaching;
|
175
|
+
|
176
|
+
#ifdef DEBUG_CC_EVENT_LOOP_BLOCKING
|
177
|
+
struct ev_prepare prepareWatcher;
|
178
|
+
ev_tstamp timeBeforeBlocking;
|
179
|
+
#endif
|
180
|
+
|
181
|
+
|
182
|
+
/****** Stage: initiatelize request ******/
|
183
|
+
|
184
|
+
struct RequestAnalysis;
|
185
|
+
|
186
|
+
void initializeFlags(Client *client, Request *req, RequestAnalysis &analysis);
|
187
|
+
bool respondFromTurboCache(Client *client, Request *req);
|
188
|
+
void initializePoolOptions(Client *client, Request *req, RequestAnalysis &analysis);
|
189
|
+
void fillPoolOptionsFromAgentsOptions(Options &options);
|
190
|
+
static void fillPoolOption(Request *req, StaticString &field,
|
191
|
+
const HashedStaticString &name);
|
192
|
+
static void fillPoolOption(Request *req, int &field,
|
193
|
+
const HashedStaticString &name);
|
194
|
+
static void fillPoolOption(Request *req, bool &field,
|
195
|
+
const HashedStaticString &name);
|
196
|
+
static void fillPoolOption(Request *req, unsigned int &field,
|
197
|
+
const HashedStaticString &name);
|
198
|
+
static void fillPoolOption(Request *req, unsigned long &field,
|
199
|
+
const HashedStaticString &name);
|
200
|
+
static void fillPoolOption(Request *req, long &field,
|
201
|
+
const HashedStaticString &name);
|
202
|
+
static void fillPoolOptionSecToMsec(Request *req, unsigned int &field,
|
203
|
+
const HashedStaticString &name);
|
204
|
+
void createNewPoolOptions(Client *client, Request *req,
|
205
|
+
const HashedStaticString &appGroupName);
|
206
|
+
void initializeUnionStation(Client *client, Request *req, RequestAnalysis &analysis);
|
207
|
+
void setStickySessionId(Client *client, Request *req);
|
208
|
+
const LString *getStickySessionCookieName(Request *req);
|
209
|
+
|
210
|
+
|
211
|
+
/****** Stage: buffering body ******/
|
212
|
+
|
213
|
+
void beginBufferingBody(Client *client, Request *req);
|
214
|
+
Channel::Result whenBufferingBody_onRequestBody(Client *client, Request *req,
|
215
|
+
const MemoryKit::mbuf &buffer, int errcode);
|
216
|
+
|
217
|
+
|
218
|
+
/****** Stage: checkout session ******/
|
219
|
+
|
220
|
+
void checkoutSession(Client *client, Request *req);
|
221
|
+
static void sessionCheckedOut(const SessionPtr &session,
|
222
|
+
const ExceptionPtr &e, void *userData);
|
223
|
+
void sessionCheckedOutFromAnotherThread(Client *client, Request *req,
|
224
|
+
SessionPtr session, ExceptionPtr e);
|
225
|
+
void sessionCheckedOutFromEventLoopThread(Client *client, Request *req,
|
226
|
+
const SessionPtr &session, const ExceptionPtr &e);
|
227
|
+
void maybeSend100Continue(Client *client, Request *req);
|
228
|
+
void initiateSession(Client *client, Request *req);
|
229
|
+
static void checkoutSessionLater(Request *req);
|
230
|
+
void reportSessionCheckoutError(Client *client, Request *req,
|
231
|
+
const ExceptionPtr &e);
|
232
|
+
void writeRequestQueueFullExceptionErrorResponse(Client *client,
|
233
|
+
Request *req, const boost::shared_ptr<RequestQueueFullException> &e);
|
234
|
+
void writeSpawnExceptionErrorResponse(Client *client, Request *req,
|
235
|
+
const boost::shared_ptr<SpawnException> &e);
|
236
|
+
void writeOtherExceptionErrorResponse(Client *client, Request *req,
|
237
|
+
const ExceptionPtr &e);
|
238
|
+
void endRequestWithErrorResponse(Client **c, Request **r,
|
239
|
+
const StaticString &message, const SpawnException *e = NULL);
|
240
|
+
bool friendlyErrorPagesEnabled(Request *req);
|
241
|
+
|
242
|
+
|
243
|
+
/****** Stage: send request to application ******/
|
244
|
+
|
245
|
+
struct SessionProtocolWorkingState;
|
246
|
+
struct HttpHeaderConstructionCache;
|
247
|
+
|
248
|
+
void sendHeaderToApp(Client *client, Request *req);
|
249
|
+
void sendHeaderToAppWithSessionProtocol(Client *client, Request *req);
|
250
|
+
static void sendBodyToAppWhenAppSinkIdle(Channel *_channel, unsigned int size);
|
251
|
+
unsigned int determineHeaderSizeForSessionProtocol(Request *req,
|
252
|
+
SessionProtocolWorkingState &state, string delta_monotonic);
|
253
|
+
bool constructHeaderForSessionProtocol(Request *req, char * restrict buffer,
|
254
|
+
unsigned int &size, const SessionProtocolWorkingState &state, string delta_monotonic);
|
255
|
+
void sendHeaderToAppWithHttpProtocol(Client *client, Request *req);
|
256
|
+
bool constructHeaderBuffersForHttpProtocol(Request *req, struct iovec *buffers,
|
257
|
+
unsigned int maxbuffers, unsigned int & restrict_ref nbuffers,
|
258
|
+
unsigned int & restrict_ref dataSize, HttpHeaderConstructionCache &cache);
|
259
|
+
bool sendHeaderToAppWithHttpProtocolAndWritev(Request *req, ssize_t &bytesWritten,
|
260
|
+
HttpHeaderConstructionCache &cache);
|
261
|
+
void sendHeaderToAppWithHttpProtocolWithBuffering(Request *req, unsigned int offset,
|
262
|
+
HttpHeaderConstructionCache &cache);
|
263
|
+
void sendBodyToApp(Client *client, Request *req);
|
264
|
+
void halfCloseAppSink(Client *client, Request *req);
|
265
|
+
Channel::Result whenSendingRequest_onRequestBody(Client *client, Request *req,
|
266
|
+
const MemoryKit::mbuf &buffer, int errcode);
|
267
|
+
static void resumeRequestBodyChannelWhenAppSinkIdle(Channel *_channel,
|
268
|
+
unsigned int size);
|
269
|
+
void startBodyChannel(Client *client, Request *req);
|
270
|
+
void stopBodyChannel(Client *client, Request *req);
|
271
|
+
void logAppSocketWriteError(Client *client, int errcode);
|
272
|
+
|
273
|
+
|
274
|
+
/****** Stage: forward application response to client ******/
|
275
|
+
|
276
|
+
static Channel::Result _onAppSourceData(Channel *_channel,
|
277
|
+
const MemoryKit::mbuf &buffer, int errcode);
|
278
|
+
Channel::Result onAppSourceData(Client *client, Request *req,
|
279
|
+
const MemoryKit::mbuf &buffer, int errcode);
|
280
|
+
void onAppResponseBegin(Client *client, Request *req);
|
281
|
+
void prepareAppResponseCaching(Client *client, Request *req);
|
282
|
+
void onAppResponse100Continue(Client *client, Request *req);
|
283
|
+
bool constructHeaderBuffersForResponse(Request *req, struct iovec *buffers,
|
284
|
+
unsigned int maxbuffers, unsigned int & restrict_ref nbuffers,
|
285
|
+
unsigned int & restrict_ref dataSize,
|
286
|
+
unsigned int & restrict_ref nCacheableBuffers);
|
287
|
+
unsigned int constructDateHeaderBuffersForResponse(char *dateStr,
|
288
|
+
unsigned int bufsize);
|
289
|
+
bool sendResponseHeaderWithWritev(Client *client, Request *req,
|
290
|
+
ssize_t &bytesWritten);
|
291
|
+
void sendResponseHeaderWithBuffering(Client *client, Request *req,
|
292
|
+
unsigned int offset);
|
293
|
+
void logResponseHeaders(Client *client, Request *req, struct iovec *buffers,
|
294
|
+
unsigned int nbuffers, unsigned int dataSize);
|
295
|
+
void markHeaderBuffersForTurboCaching(Client *client, Request *req,
|
296
|
+
struct iovec *buffers, unsigned int nbuffers);
|
297
|
+
static ServerKit::HttpHeaderParser<AppResponse, ServerKit::HttpParseResponse>
|
298
|
+
createAppResponseHeaderParser(ServerKit::Context *ctx, Request *req);
|
299
|
+
static ServerKit::HttpChunkedBodyParser createAppResponseChunkedBodyParser(
|
300
|
+
Request *req);
|
301
|
+
static unsigned int formatAppResponseChunkedBodyParserLoggingPrefix(char *buf,
|
302
|
+
unsigned int bufsize, void *userData);
|
303
|
+
void prepareAppResponseChunkedBodyParsing(Client *client, Request *req);
|
304
|
+
void writeResponseAndMarkForTurboCaching(Client *client, Request *req,
|
305
|
+
const MemoryKit::mbuf &buffer);
|
306
|
+
void markResponsePartForTurboCaching(Client *client, Request *req,
|
307
|
+
const MemoryKit::mbuf &buffer);
|
308
|
+
void maybeThrottleAppSource(Client *client, Request *req);
|
309
|
+
static void _outputBuffersFlushed(FileBufferedChannel *_channel);
|
310
|
+
void outputBuffersFlushed(Client *client, Request *req);
|
311
|
+
static void _outputDataFlushed(FileBufferedChannel *_channel);
|
312
|
+
void outputDataFlushed(Client *client, Request *req);
|
313
|
+
void handleAppResponseBodyEnd(Client *client, Request *req);
|
314
|
+
OXT_FORCE_INLINE void keepAliveAppConnection(Client *client, Request *req);
|
315
|
+
void storeAppResponseInTurboCache(Client *client, Request *req);
|
316
|
+
void finalizeUnionStationWithSuccess(Client *client, Request *req);
|
317
|
+
|
318
|
+
|
319
|
+
/***** Hooks ******/
|
320
|
+
|
321
|
+
static Channel::Result onBodyBufferData(Channel *_channel,
|
322
|
+
const MemoryKit::mbuf &buffer, int errcode);
|
323
|
+
#ifdef DEBUG_CC_EVENT_LOOP_BLOCKING
|
324
|
+
static void onEventLoopPrepare(EV_P_ struct ev_prepare *w, int revents);
|
325
|
+
#endif
|
326
|
+
static void onEventLoopCheck(EV_P_ struct ev_check *w, int revents);
|
327
|
+
|
328
|
+
|
329
|
+
/****** Internal utility functions ******/
|
330
|
+
|
331
|
+
static TurboCaching<Request>::State getTurboCachingInitialState(
|
332
|
+
const VariantMap *agentsOptions);
|
333
|
+
void generateServerLogName(unsigned int number);
|
334
|
+
void disconnectWithClientSocketWriteError(Client **client, int e);
|
335
|
+
void disconnectWithAppSocketIncompleteResponseError(Client **client);
|
336
|
+
void disconnectWithAppSocketReadError(Client **client, int e);
|
337
|
+
void disconnectWithAppSocketWriteError(Client **client, int e);
|
338
|
+
void endRequestWithAppSocketIncompleteResponse(Client **client,
|
339
|
+
Request **req);
|
340
|
+
void endRequestWithAppSocketReadError(Client **client, Request **req,
|
341
|
+
int e);
|
342
|
+
void endRequestWithSimpleResponse(Client **c, Request **r,
|
343
|
+
const StaticString &body, int code = 200);
|
344
|
+
void endRequestAsBadGateway(Client **client, Request **req);
|
345
|
+
void writeBenchmarkResponse(Client **client, Request **req,
|
346
|
+
bool end = true);
|
347
|
+
bool getBoolOption(Request *req, const HashedStaticString &name,
|
348
|
+
bool defaultValue = false);
|
349
|
+
template<typename Number> static Number clamp(Number value,
|
350
|
+
Number min, Number max);
|
351
|
+
static void gatherBuffers(char * restrict dest, unsigned int size,
|
352
|
+
const struct iovec *buffers, unsigned int nbuffers);
|
353
|
+
static LString *resolveSymlink(const StaticString &path, psg_pool_t *pool);
|
354
|
+
void parseCookieHeader(psg_pool_t *pool, const LString *headerValue,
|
355
|
+
vector< pair<StaticString, StaticString> > &cookies) const;
|
356
|
+
#ifdef DEBUG_CC_EVENT_LOOP_BLOCKING
|
357
|
+
void reportLargeTimeDiff(Client *client, const char *name,
|
358
|
+
ev_tstamp fromTime, ev_tstamp toTime);
|
359
|
+
#endif
|
360
|
+
|
361
|
+
|
362
|
+
protected:
|
363
|
+
/****** Stage: initiatelize request ******/
|
364
|
+
|
365
|
+
virtual void onRequestBegin(Client *client, Request *req);
|
366
|
+
|
367
|
+
|
368
|
+
/****** Hooks ******/
|
369
|
+
|
370
|
+
virtual void onClientAccepted(Client *client);
|
371
|
+
virtual void onRequestObjectCreated(Client *client, Request *req);
|
372
|
+
virtual void deinitializeClient(Client *client);
|
373
|
+
virtual void reinitializeRequest(Client *client, Request *req);
|
374
|
+
virtual void deinitializeRequest(Client *client, Request *req);
|
375
|
+
void reinitializeAppResponse(Client *client, Request *req);
|
376
|
+
void deinitializeAppResponse(Client *client, Request *req);
|
377
|
+
virtual Channel::Result onRequestBody(Client *client, Request *req,
|
378
|
+
const MemoryKit::mbuf &buffer, int errcode);
|
379
|
+
virtual bool shouldDisconnectClientOnShutdown(Client *client);
|
380
|
+
virtual bool supportsUpgrade(Client *client, Request *req);
|
381
|
+
|
382
|
+
|
383
|
+
public:
|
384
|
+
ResourceLocator *resourceLocator;
|
385
|
+
PoolPtr appPool;
|
386
|
+
UnionStation::ContextPtr unionStationContext;
|
387
|
+
|
388
|
+
|
389
|
+
/****** Initialization and shutdown ******/
|
390
|
+
|
391
|
+
Controller(ServerKit::Context *context, const VariantMap *_agentsOptions,
|
392
|
+
unsigned int _threadNumber = 1);
|
393
|
+
~Controller();
|
394
|
+
void initialize();
|
395
|
+
|
396
|
+
|
397
|
+
/****** Hooks ******/
|
398
|
+
|
399
|
+
virtual unsigned int getClientName(const Client *client, char *buf, size_t size) const;
|
400
|
+
virtual StaticString getServerName() const;
|
401
|
+
|
402
|
+
|
403
|
+
/****** State inspection and configuration ******/
|
404
|
+
|
405
|
+
virtual Json::Value getConfigAsJson() const;
|
406
|
+
virtual void configure(const Json::Value &doc);
|
407
|
+
virtual Json::Value inspectStateAsJson() const;
|
408
|
+
virtual Json::Value inspectClientStateAsJson(const Client *client) const;
|
409
|
+
virtual Json::Value inspectRequestStateAsJson(const Request *req) const;
|
410
|
+
|
411
|
+
|
412
|
+
/****** Miscellaneous *******/
|
413
|
+
|
414
|
+
static BenchmarkMode parseBenchmarkMode(const StaticString mode);
|
415
|
+
void disconnectLongRunningConnections(const StaticString &gupid);
|
416
|
+
};
|
417
|
+
|
418
|
+
|
419
|
+
} // namespace Core
|
420
|
+
} // namespace Passenger
|
421
|
+
|
422
|
+
#endif /* _PASSENGER_CORE_CONTROLLER_H_ */
|