passenger 5.0.9 → 5.0.10

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.

Files changed (106) hide show
  1. checksums.yaml +8 -8
  2. checksums.yaml.gz.asc +7 -7
  3. data.tar.gz.asc +7 -7
  4. data/CHANGELOG +15 -0
  5. data/CONTRIBUTORS +6 -0
  6. data/README.md +1 -1
  7. data/bin/passenger-install-apache2-module +24 -11
  8. data/bin/passenger-status +29 -14
  9. data/build/agents.rb +12 -10
  10. data/build/cxx_tests.rb +30 -30
  11. data/doc/Design and Architecture.html +1 -10
  12. data/doc/Design and Architecture.txt +1 -6
  13. data/doc/Users guide Apache.html +1 -19
  14. data/doc/Users guide Apache.txt +1 -1
  15. data/doc/Users guide Nginx.html +2 -20
  16. data/doc/Users guide Nginx.txt +2 -2
  17. data/doc/users_guide_snippets/tips.txt +0 -9
  18. data/ext/common/ApplicationPool2/ApiKey.h +158 -0
  19. data/ext/common/ApplicationPool2/BasicGroupInfo.h +81 -0
  20. data/ext/common/ApplicationPool2/BasicProcessInfo.h +106 -0
  21. data/ext/common/ApplicationPool2/Common.h +5 -44
  22. data/ext/common/ApplicationPool2/Context.h +94 -0
  23. data/ext/common/ApplicationPool2/Group.h +130 -1205
  24. data/ext/common/ApplicationPool2/Group/InitializationAndShutdown.cpp +190 -0
  25. data/ext/common/ApplicationPool2/Group/InternalUtils.cpp +329 -0
  26. data/ext/common/ApplicationPool2/Group/LifetimeAndBasics.cpp +103 -0
  27. data/ext/common/ApplicationPool2/{Pool/Debug.h → Group/Miscellaneous.cpp} +40 -38
  28. data/ext/common/ApplicationPool2/Group/OutOfBandWork.cpp +323 -0
  29. data/ext/common/ApplicationPool2/Group/ProcessListManagement.cpp +606 -0
  30. data/ext/common/ApplicationPool2/Group/SessionManagement.cpp +337 -0
  31. data/ext/common/ApplicationPool2/Group/SpawningAndRestarting.cpp +478 -0
  32. data/ext/common/ApplicationPool2/Group/StateInspection.cpp +197 -0
  33. data/ext/common/ApplicationPool2/Group/Verification.cpp +159 -0
  34. data/ext/common/ApplicationPool2/Implementation.cpp +19 -1401
  35. data/ext/common/ApplicationPool2/Options.h +5 -5
  36. data/ext/common/ApplicationPool2/Pool.h +260 -815
  37. data/ext/common/ApplicationPool2/Pool/{AnalyticsCollection.h → AnalyticsCollection.cpp} +55 -56
  38. data/ext/common/ApplicationPool2/Pool/{GarbageCollection.h → GarbageCollection.cpp} +49 -49
  39. data/ext/common/ApplicationPool2/Pool/GeneralUtils.cpp +241 -0
  40. data/ext/common/ApplicationPool2/Pool/GroupUtils.cpp +276 -0
  41. data/ext/common/ApplicationPool2/Pool/InitializationAndShutdown.cpp +145 -0
  42. data/ext/common/ApplicationPool2/Pool/Miscellaneous.cpp +244 -0
  43. data/ext/common/ApplicationPool2/Pool/ProcessUtils.cpp +330 -0
  44. data/ext/common/ApplicationPool2/Pool/StateInspection.cpp +299 -0
  45. data/ext/common/ApplicationPool2/Process.h +399 -205
  46. data/ext/common/ApplicationPool2/Session.h +70 -28
  47. data/ext/common/ApplicationPool2/Socket.h +1 -0
  48. data/ext/common/Constants.h +11 -3
  49. data/ext/common/Exceptions.h +1 -1
  50. data/ext/common/Logging.cpp +9 -4
  51. data/ext/common/Logging.h +6 -0
  52. data/ext/common/ServerKit/HttpServer.h +225 -215
  53. data/ext/common/ServerKit/Server.h +57 -57
  54. data/ext/common/SpawningKit/BackgroundIOCapturer.h +160 -0
  55. data/ext/common/SpawningKit/Config.h +107 -0
  56. data/ext/common/{ApplicationPool2 → SpawningKit}/DirectSpawner.h +17 -16
  57. data/ext/common/{ApplicationPool2 → SpawningKit}/DummySpawner.h +33 -33
  58. data/ext/common/{ApplicationPool2/SpawnerFactory.h → SpawningKit/Factory.h} +17 -17
  59. data/ext/common/{ApplicationPool2/ComponentInfo.h → SpawningKit/Options.h} +8 -21
  60. data/ext/common/SpawningKit/PipeWatcher.h +148 -0
  61. data/ext/common/{ApplicationPool2/PipeWatcher.h → SpawningKit/Result.h} +15 -33
  62. data/ext/common/{ApplicationPool2 → SpawningKit}/SmartSpawner.h +52 -57
  63. data/ext/common/{ApplicationPool2 → SpawningKit}/Spawner.h +83 -371
  64. data/ext/common/SpawningKit/UserSwitchingRules.h +265 -0
  65. data/ext/common/Utils/BufferedIO.h +24 -0
  66. data/ext/common/{ApplicationPool2/SpawnObject.h → Utils/ClassUtils.h} +24 -51
  67. data/ext/common/Utils/IOUtils.cpp +70 -0
  68. data/ext/common/Utils/IOUtils.h +19 -0
  69. data/ext/common/Utils/JsonUtils.h +113 -0
  70. data/ext/common/Utils/StrIntUtils.h +29 -0
  71. data/ext/common/Utils/json.h +1 -1
  72. data/ext/common/agents/ApiServerUtils.h +941 -0
  73. data/ext/common/agents/HelperAgent/{AdminServer.h → ApiServer.h} +163 -365
  74. data/ext/common/agents/HelperAgent/Main.cpp +86 -88
  75. data/ext/common/agents/HelperAgent/OptionParser.h +9 -10
  76. data/ext/common/agents/HelperAgent/RequestHandler/BufferBody.cpp +3 -0
  77. data/ext/common/agents/HelperAgent/RequestHandler/ForwardResponse.cpp +2 -0
  78. data/ext/common/agents/HelperAgent/RequestHandler/Hooks.cpp +1 -1
  79. data/ext/common/agents/HelperAgent/RequestHandler/SendRequest.cpp +2 -2
  80. data/ext/common/agents/LoggingAgent/ApiServer.h +279 -0
  81. data/ext/common/agents/LoggingAgent/Main.cpp +41 -51
  82. data/ext/common/agents/LoggingAgent/OptionParser.h +11 -11
  83. data/ext/common/agents/Watchdog/ApiServer.h +311 -0
  84. data/ext/common/agents/Watchdog/Main.cpp +91 -65
  85. data/helper-scripts/prespawn +2 -0
  86. data/lib/phusion_passenger.rb +1 -1
  87. data/lib/phusion_passenger/admin_tools/instance.rb +1 -1
  88. data/lib/phusion_passenger/common_library.rb +27 -14
  89. data/lib/phusion_passenger/config/{admin_command_command.rb → api_call_command.rb} +19 -16
  90. data/lib/phusion_passenger/config/detach_process_command.rb +6 -3
  91. data/lib/phusion_passenger/config/main.rb +3 -5
  92. data/lib/phusion_passenger/config/reopen_logs_command.rb +29 -7
  93. data/lib/phusion_passenger/config/restart_app_command.rb +13 -4
  94. data/lib/phusion_passenger/config/utils.rb +15 -8
  95. data/lib/phusion_passenger/constants.rb +6 -2
  96. data/lib/phusion_passenger/platform_info/apache.rb +4 -0
  97. data/lib/phusion_passenger/platform_info/apache_detector.rb +18 -3
  98. data/resources/templates/apache2/mpm_unknown.txt.erb +20 -0
  99. metadata +42 -21
  100. metadata.gz.asc +7 -7
  101. data/ext/common/ApplicationPool2/Pool/GeneralUtils.h +0 -127
  102. data/ext/common/ApplicationPool2/Pool/Inspection.h +0 -219
  103. data/ext/common/ApplicationPool2/Pool/ProcessUtils.h +0 -85
  104. data/ext/common/ApplicationPool2/SuperGroup.h +0 -706
  105. data/ext/common/agents/LoggingAgent/AdminServer.h +0 -435
  106. data/ext/common/agents/Watchdog/AdminServer.h +0 -432
@@ -28,6 +28,7 @@ STDERR.sync = true
28
28
  require 'uri'
29
29
  require 'socket'
30
30
  require 'timeout'
31
+ require 'base64'
31
32
 
32
33
  class PrespawnLocation
33
34
  class InvalidURLError < RuntimeError
@@ -90,6 +91,7 @@ class PrespawnLocation
90
91
  def head_request
91
92
  socket.write("HEAD #{request_path} HTTP/1.1\r\n")
92
93
  socket.write("Host: #{request_host}\r\n")
94
+ socket.write("Authorization: Basic " + Base64.encode64(@uri.userinfo) + "\r\n") if @uri.userinfo
93
95
  socket.write("Connection: close\r\n")
94
96
  socket.write("\r\n")
95
97
 
@@ -30,7 +30,7 @@ module PhusionPassenger
30
30
 
31
31
  PACKAGE_NAME = 'passenger'
32
32
  # Run 'rake ext/common/Constants.h' after changing this number.
33
- VERSION_STRING = '5.0.9'
33
+ VERSION_STRING = '5.0.10'
34
34
 
35
35
  PREFERRED_NGINX_VERSION = '1.8.0'
36
36
  NGINX_SHA256_CHECKSUM = '23cca1239990c818d8f6da118320c4979aadf5386deda691b1b7c2c96b9df3d5'
@@ -174,7 +174,7 @@ module PhusionPassenger
174
174
 
175
175
  version_supported =
176
176
  major_version == PhusionPassenger::SERVER_INSTANCE_DIR_STRUCTURE_MAJOR_VERSION &&
177
- minor_version <= PhusionPassenger::SERVER_INSTANCE_DIR_STRUCTURE_MINOR_VERSION
177
+ minor_version >= PhusionPassenger::SERVER_INSTANCE_DIR_STRUCTURE_MIN_SUPPORTED_MINOR_VERSION
178
178
  if !version_supported
179
179
  @state = :structure_version_unsupported
180
180
  return
@@ -421,28 +421,41 @@ COMMON_LIBRARY = CommonLibraryBuilder.new do
421
421
  :source => 'ApplicationPool2/Implementation.cpp',
422
422
  :category => :other,
423
423
  :deps => %w(
424
- ApplicationPool2/Spawner.h
425
424
  ApplicationPool2/Common.h
426
425
  ApplicationPool2/Pool.h
427
- ApplicationPool2/Pool/AnalyticsCollection.h
428
- ApplicationPool2/Pool/GarbageCollection.h
429
- ApplicationPool2/Pool/GeneralUtils.h
430
- ApplicationPool2/Pool/ProcessUtils.h
431
- ApplicationPool2/Pool/Inspection.h
432
- ApplicationPool2/Pool/Debug.h
433
- ApplicationPool2/SuperGroup.h
426
+ ApplicationPool2/Pool/InitializationAndShutdown.cpp
427
+ ApplicationPool2/Pool/AnalyticsCollection.cpp
428
+ ApplicationPool2/Pool/GarbageCollection.cpp
429
+ ApplicationPool2/Pool/GeneralUtils.cpp
430
+ ApplicationPool2/Pool/GroupUtils.cpp
431
+ ApplicationPool2/Pool/ProcessUtils.cpp
432
+ ApplicationPool2/Pool/StateInspection.cpp
433
+ ApplicationPool2/Pool/Miscellaneous.cpp
434
434
  ApplicationPool2/Group.h
435
+ ApplicationPool2/Group/InitializationAndShutdown.cpp
436
+ ApplicationPool2/Group/LifetimeAndBasics.cpp
437
+ ApplicationPool2/Group/SessionManagement.cpp
438
+ ApplicationPool2/Group/SpawningAndRestarting.cpp
439
+ ApplicationPool2/Group/ProcessListManagement.cpp
440
+ ApplicationPool2/Group/OutOfBandWork.cpp
441
+ ApplicationPool2/Group/Miscellaneous.cpp
442
+ ApplicationPool2/Group/InternalUtils.cpp
443
+ ApplicationPool2/Group/StateInspection.cpp
444
+ ApplicationPool2/Group/Verification.cpp
445
+ ApplicationPool2/BasicGroupInfo.h
446
+ ApplicationPool2/BasicProcessInfo.h
447
+ ApplicationPool2/Context.h
435
448
  ApplicationPool2/Process.h
436
449
  ApplicationPool2/Socket.h
437
450
  ApplicationPool2/Session.h
438
451
  ApplicationPool2/Options.h
439
- ApplicationPool2/PipeWatcher.h
440
452
  ApplicationPool2/AppTypes.h
441
- ApplicationPool2/Spawner.h
442
- ApplicationPool2/SpawnerFactory.h
443
- ApplicationPool2/SmartSpawner.h
444
- ApplicationPool2/DirectSpawner.h
445
- ApplicationPool2/DummySpawner.h
453
+ SpawningKit/Spawner.h
454
+ SpawningKit/Factory.h
455
+ SpawningKit/SmartSpawner.h
456
+ SpawningKit/DirectSpawner.h
457
+ SpawningKit/DummySpawner.h
458
+ SpawningKit/PipeWatcher.h
446
459
  )
447
460
  define_component 'ApplicationPool2/AppTypes.o',
448
461
  :source => 'ApplicationPool2/AppTypes.cpp',
@@ -33,11 +33,11 @@ PhusionPassenger.require_passenger_lib 'utils/json'
33
33
  module PhusionPassenger
34
34
  module Config
35
35
 
36
- class AdminCommandCommand < Command
36
+ class ApiCallCommand < Command
37
37
  include PhusionPassenger::Config::Utils
38
38
 
39
39
  def self.create_default_options
40
- return { :agent_name => "server_admin" }
40
+ { :agent_name => "server_api" }
41
41
  end
42
42
 
43
43
  def run
@@ -51,29 +51,29 @@ module PhusionPassenger
51
51
  def self.create_option_parser(options)
52
52
  OptionParser.new do |opts|
53
53
  nl = "\n" + ' ' * 37
54
- opts.banner = "Usage: passenger-config invoke-command <METHOD> <PATH> [OPTIONS]\n"
54
+ opts.banner = "Usage: passenger-config api-call <METHOD> <PATH> [OPTIONS]\n"
55
55
  opts.separator ""
56
- opts.separator " Invoke an internal #{PROGRAM_NAME} admin command. #{PROGRAM_NAME} listens"
57
- opts.separator " on a local HTTP server for admin commands. Other `passenger-config` commands"
58
- opts.separator " are just shortcuts for sending specific HTTP requests to the"
59
- opts.separator " #{PROGRAM_NAME} admin HTTP server. `passenger-config invoke-command` allows"
60
- opts.separator " you to send requests directly."
56
+ opts.separator " Makes an API call to one of the #{PROGRAM_NAME} agents. #{PROGRAM_NAME}"
57
+ opts.separator " listens on a local HTTP server for admin commands. Many `passenger-config`"
58
+ opts.separator " commands are just shortcuts for sending HTTP API calls to the"
59
+ opts.separator " #{PROGRAM_NAME} admin HTTP server. `passenger-config api-call` allows"
60
+ opts.separator " you to send API calls directly."
61
61
  opts.separator ""
62
62
  opts.separator " METHOD is an HTTP verb, like 'GET', 'POST', 'PUT' or 'DELETE'."
63
63
  opts.separator " PATH is the admin URI. You can pass POST data with '-d'."
64
64
  opts.separator ""
65
- opts.separator " Example 1: passenger-config admin-command GET /server.json"
65
+ opts.separator " Example 1: passenger-config api-call GET /server.json"
66
66
  opts.separator " Sends the 'GET /server.json' command to the HTTP server agent."
67
67
  opts.separator ""
68
- opts.separator " Example 2: passenger-config admin-command PUT /config.json \\"
68
+ opts.separator " Example 2: passenger-config api-call PUT /config.json \\"
69
69
  opts.separator " -d '{\"log_level\", 7}'"
70
70
  opts.separator " Sends the 'PUT /config.json' command to the HTTP server agent, with the"
71
71
  opts.separator " given PUT data."
72
72
  opts.separator ""
73
- opts.separator " Example 3: passenger-config admin-command POST /shutdown.json -a watchdog"
73
+ opts.separator " Example 3: passenger-config api-call POST /shutdown.json -a watchdog"
74
74
  opts.separator " Sends the 'POST /shutdown.json' command to the watchdog, with no POST data."
75
75
  opts.separator ""
76
- opts.separator " Example 4: passenger-config admin-command POST /shutdown.json \\"
76
+ opts.separator " Example 4: passenger-config api-call POST /shutdown.json \\"
77
77
  opts.separator " -S /tmp/watchdog.sock"
78
78
  opts.separator " Sends the 'POST /shutdown.json' command to the watchdog listening at the"
79
79
  opts.separator " specific socket file /tmp/watchdog.sock. No POST data."
@@ -92,9 +92,9 @@ module PhusionPassenger
92
92
  end
93
93
  opts.on("-a", "--agent NAME", String, "The name of the socket to send the command#{nl}" +
94
94
  "to. This specifies which agent the request#{nl}" +
95
- "is sent to. Choices: watchdog,#{nl}" +
96
- "server_admin, logging_admin.#{nl}" +
97
- "Default: server_admin") do |val|
95
+ "is sent to. Choices: watchdog_api,#{nl}" +
96
+ "server_api, logging_api.#{nl}" +
97
+ "Default: server_api") do |val|
98
98
  options[:agent_name] = val
99
99
  end
100
100
  opts.on("-S", "--socket PATH", String, "Instead of inferring the socket path from#{nl}" +
@@ -162,7 +162,10 @@ module PhusionPassenger
162
162
  else
163
163
  select_passenger_instance
164
164
  @socket_path = "#{@instance.path}/agents.s/#{@options[:agent_name]}"
165
- @password = obtain_full_admin_password(@instance)
165
+ begin
166
+ @password = @instance.full_admin_password
167
+ rescue Errno::EACCES
168
+ end
166
169
  end
167
170
  end
168
171
 
@@ -1,5 +1,5 @@
1
1
  # Phusion Passenger - https://www.phusionpassenger.com/
2
- # Copyright (c) 2014 Phusion
2
+ # Copyright (c) 2014-2015 Phusion
3
3
  #
4
4
  # "Phusion Passenger" is a trademark of Hongli Lai & Ninh Bui.
5
5
  #
@@ -89,10 +89,10 @@ module PhusionPassenger
89
89
 
90
90
  def perform_detach
91
91
  request = Net::HTTP::Post.new("/pool/detach_process.json")
92
- request.basic_auth("admin", obtain_full_admin_password(@instance))
92
+ try_performing_full_admin_basic_auth(request, @instance)
93
93
  request.content_type = "application/json"
94
94
  request.body = PhusionPassenger::Utils::JSON.generate(:pid => @pid)
95
- response = @instance.http_request("agents.s/server_admin", request)
95
+ response = @instance.http_request("agents.s/server_api", request)
96
96
  if response.code.to_i / 100 == 2
97
97
  body = PhusionPassenger::Utils::JSON.parse(response.body)
98
98
  if body['detached']
@@ -102,6 +102,9 @@ module PhusionPassenger
102
102
  else
103
103
  abort "Could not detach process #{@pid}."
104
104
  end
105
+ elsif response.code.to_i == 401
106
+ print_full_admin_command_permission_error
107
+ abort
105
108
  else
106
109
  STDERR.puts "*** An error occured while communicating with the #{PROGRAM_NAME} server:"
107
110
  STDERR.puts response.body
@@ -1,5 +1,5 @@
1
1
  # Phusion Passenger - https://www.phusionpassenger.com/
2
- # Copyright (c) 2013-2014 Phusion
2
+ # Copyright (c) 2013-2015 Phusion
3
3
  #
4
4
  # "Phusion Passenger" is a trademark of Hongli Lai & Ninh Bui.
5
5
  #
@@ -32,7 +32,7 @@ module PhusionPassenger
32
32
  ["restart-app", "RestartAppCommand"],
33
33
  ["list-instances", "ListInstancesCommand"],
34
34
  ["reopen-logs", "ReopenLogsCommand"],
35
- ["admin-command", "AdminCommandCommand"],
35
+ ["api-call", "ApiCallCommand"],
36
36
  ["validate-install", "ValidateInstallCommand"],
37
37
  ["build-native-support", "BuildNativeSupportCommand"],
38
38
 
@@ -90,9 +90,7 @@ module PhusionPassenger
90
90
  puts " restart-app Restart an application"
91
91
  puts " reopen-logs Instruct #{PROGRAM_NAME} agents to reopen their log"
92
92
  puts " files"
93
- if all
94
- puts " admin-command Invoke an internal #{PROGRAM_NAME} admin command."
95
- end
93
+ puts " api-call Makes an API call to a #{PROGRAM_NAME} agent."
96
94
  puts
97
95
  puts "Informational commands:"
98
96
  puts " list-instances List running #{PROGRAM_NAME} instances"
@@ -68,20 +68,42 @@ module PhusionPassenger
68
68
  end
69
69
 
70
70
  def perform_reopen_logs
71
- password = obtain_full_admin_password(@instance)
72
- perform_reopen_logs_on("watchdog", "watchdog", password)
73
- perform_reopen_logs_on("server", "server_admin", password)
74
- perform_reopen_logs_on("logger", "logging_admin", password)
71
+ perform_reopen_logs_on("watchdog", "watchdog")
72
+ perform_reinherit_logs_on("server", "server_api")
73
+ perform_reinherit_logs_on("logger", "logging_api")
75
74
  puts "All done"
76
75
  end
77
76
 
78
- def perform_reopen_logs_on(name, socket_name, password)
77
+ def perform_reopen_logs_on(name, socket_name)
79
78
  puts "Reopening logs for #{AGENT_EXE} #{name}"
80
79
  request = Net::HTTP::Post.new("/reopen_logs.json")
81
- request.basic_auth("admin", password)
80
+ try_performing_full_admin_basic_auth(request, @instance)
82
81
  request.content_type = "application/json"
83
82
  response = @instance.http_request("agents.s/#{socket_name}", request)
84
- if response["content-type"] == "application/json"
83
+ if response.code.to_i == 401
84
+ print_full_admin_command_permission_error
85
+ abort
86
+ elsif response["content-type"] == "application/json"
87
+ if response.code.to_i / 100 != 2
88
+ handle_error(name, response)
89
+ end
90
+ else
91
+ STDERR.puts "*** An error occured while communicating with the #{AGENT_EXE} #{name} (code #{response.code}):"
92
+ STDERR.puts response.body
93
+ abort
94
+ end
95
+ end
96
+
97
+ def perform_reinherit_logs_on(name, socket_name)
98
+ puts "Reopen logs for #{AGENT_EXE} #{name} (through reinheritance)"
99
+ request = Net::HTTP::Post.new("/reinherit_logs.json")
100
+ try_performing_full_admin_basic_auth(request, @instance)
101
+ request.content_type = "application/json"
102
+ response = @instance.http_request("agents.s/#{socket_name}", request)
103
+ if response.code.to_i == 401
104
+ print_full_admin_command_permission_error
105
+ abort
106
+ elsif response["content-type"] == "application/json"
85
107
  if response.code.to_i / 100 != 2
86
108
  handle_error(name, response)
87
109
  end
@@ -173,6 +173,9 @@ module PhusionPassenger
173
173
  index, name = menu.query
174
174
  rescue Interrupt
175
175
  abort
176
+ ensure
177
+ STDOUT.write(colors.reset)
178
+ STDOUT.flush
176
179
  end
177
180
 
178
181
  if index == choices.size - 1
@@ -202,14 +205,17 @@ module PhusionPassenger
202
205
  group_name = group.elements["name"].text
203
206
  puts "Restarting #{group_name}"
204
207
  request = Net::HTTP::Post.new("/pool/restart_app_group.json")
205
- request.basic_auth("admin", obtain_full_admin_password(@instance))
208
+ try_performing_full_admin_basic_auth(request, @instance)
206
209
  request.content_type = "application/json"
207
210
  request.body = PhusionPassenger::Utils::JSON.generate(
208
211
  :name => group_name,
209
212
  :method => restart_method)
210
- response = @instance.http_request("agents.s/server_admin", request)
213
+ response = @instance.http_request("agents.s/server_api", request)
211
214
  if response.code.to_i / 100 == 2
212
215
  response.body
216
+ elsif response.code.to_i == 401
217
+ print_full_admin_command_permission_error
218
+ abort
213
219
  else
214
220
  STDERR.puts "*** An error occured while communicating with the #{PROGRAM_NAME} server:"
215
221
  STDERR.puts response.body
@@ -229,10 +235,13 @@ module PhusionPassenger
229
235
 
230
236
  def query_pool_xml
231
237
  request = Net::HTTP::Get.new("/pool.xml")
232
- request.basic_auth("ro_admin", obtain_read_only_admin_password(@instance))
233
- response = @instance.http_request("agents.s/server_admin", request)
238
+ try_performing_ro_admin_basic_auth(request, @instance)
239
+ response = @instance.http_request("agents.s/server_api", request)
234
240
  if response.code.to_i / 100 == 2
235
241
  REXML::Document.new(response.body)
242
+ elsif response.code.to_i == 401
243
+ print_instance_querying_permission_error
244
+ abort
236
245
  else
237
246
  STDERR.puts "*** An error occured while querying the #{PROGRAM_NAME} server:"
238
247
  STDERR.puts response.body
@@ -96,22 +96,22 @@ module PhusionPassenger
96
96
  end
97
97
  end
98
98
 
99
- def obtain_read_only_admin_password(instance)
99
+ def try_performing_ro_admin_basic_auth(request, instance)
100
100
  begin
101
- return instance.read_only_admin_password
101
+ password = instance.read_only_admin_password
102
102
  rescue Errno::EACCES
103
- print_instance_querying_permission_error
104
- abort
103
+ return
105
104
  end
105
+ request.basic_auth("ro_admin", password)
106
106
  end
107
107
 
108
- def obtain_full_admin_password(instance)
108
+ def try_performing_full_admin_basic_auth(request, instance)
109
109
  begin
110
- return instance.full_admin_password
110
+ password = instance.full_admin_password
111
111
  rescue Errno::EACCES
112
- print_instance_querying_permission_error
113
- abort
112
+ return
114
113
  end
114
+ request.basic_auth("admin", password)
115
115
  end
116
116
 
117
117
 
@@ -122,6 +122,13 @@ module PhusionPassenger
122
122
  "'#{PhusionPassenger::PlatformInfo.ruby_sudo_command}'."
123
123
  end
124
124
 
125
+ def print_full_admin_command_permission_error
126
+ PhusionPassenger.require_passenger_lib 'platform_info/ruby'
127
+ STDERR.puts "*** ERROR: You are not authorized to perform this particular " +
128
+ "administration command on this #{PROGRAM_NAME} instance. Please try again with " +
129
+ "'#{PhusionPassenger::PlatformInfo.ruby_sudo_command}'."
130
+ end
131
+
125
132
  def is_enterprise?
126
133
  return defined?(PhusionPassenger::PASSENGER_IS_ENTERPRISE) && PhusionPassenger::PASSENGER_IS_ENTERPRISE
127
134
  end
@@ -67,7 +67,7 @@ module PhusionPassenger
67
67
  DEFAULT_UNION_STATION_GATEWAY_PORT = 443
68
68
  DEFAULT_HTTP_SERVER_LISTEN_ADDRESS = "tcp://127.0.0.1:3000"
69
69
  DEFAULT_LOGGING_AGENT_LISTEN_ADDRESS = "tcp://127.0.0.1:9344"
70
- DEFAULT_LOGGING_AGENT_ADMIN_LISTEN_ADDRESS = "tcp://127.0.0.1:9345"
70
+ DEFAULT_LOGGING_AGENT_API_LISTEN_ADDRESS = "tcp://127.0.0.1:9345"
71
71
 
72
72
  # Size limits
73
73
  MESSAGE_SERVER_MAX_USERNAME_SIZE = 100
@@ -83,8 +83,12 @@ module PhusionPassenger
83
83
 
84
84
  # Versions
85
85
  PASSENGER_VERSION = PhusionPassenger::VERSION_STRING
86
+ PASSENGER_API_VERSION_MAJOR = 0
87
+ PASSENGER_API_VERSION_MINOR = 2
88
+ PASSENGER_API_VERSION = "#{PASSENGER_API_VERSION_MAJOR}.#{PASSENGER_API_VERSION_MINOR}"
86
89
  SERVER_INSTANCE_DIR_STRUCTURE_MAJOR_VERSION = 2
87
- SERVER_INSTANCE_DIR_STRUCTURE_MINOR_VERSION = 0
90
+ SERVER_INSTANCE_DIR_STRUCTURE_MINOR_VERSION = 1
91
+ SERVER_INSTANCE_DIR_STRUCTURE_MIN_SUPPORTED_MINOR_VERSION = 1
88
92
 
89
93
  # Misc
90
94
  FEEDBACK_FD = 3
@@ -106,6 +106,10 @@ module PhusionPassenger
106
106
  #
107
107
  # We used to run `httpd -V`, but on systems like Ubuntu it depends on various
108
108
  # environment variables or directories, wich apache2ctl loads or initializes.
109
+ #
110
+ # Because on some systems (mostly Ubuntu) `apache2ctl -V` attempts to parse
111
+ # and load the config file, this command can fail because of configuration file
112
+ # errors.
109
113
  def self.apache2ctl_V(options = nil)
110
114
  if options
111
115
  apache2ctl = options[:apache2ctl] || self.apache2ctl(options)
@@ -42,24 +42,37 @@ module PhusionPassenger
42
42
  class ApacheDetector
43
43
  class Result
44
44
  # These are required and are never nil.
45
- attr_accessor :apxs2, :httpd, :ctl, :version, :config_file
45
+ attr_accessor :apxs2, :httpd, :ctl, :version
46
46
  # These are optional and may be nil.
47
47
  attr_accessor :a2enmod, :a2dismod
48
+ # Ttis may be nil. It depends on whether 'apache2ctl -V' succeeds.
49
+ attr_accessor :config_file
48
50
  # This may be nil. It depends on how well we can infer information from the config file.
49
51
  attr_accessor :error_log
52
+ attr_writer :config_file_broken
50
53
 
51
54
  def initialize(detector)
52
55
  @detector = detector
53
56
  end
54
57
 
58
+ def config_file_broken?
59
+ @config_file_broken
60
+ end
61
+
55
62
  def report
56
63
  log " <b>* Found Apache #{version}!</b>"
57
64
  log " Information:"
58
65
  log " apxs2 : #{apxs2}"
59
66
  log " Main executable: #{httpd}"
60
67
  log " Control command: #{ctl}"
61
- log " Config file : #{config_file}"
68
+ log " Config file : #{config_file || 'unknown'}"
62
69
  log " Error log file : #{error_log || 'unknown'}"
70
+ if config_file_broken?
71
+ log ""
72
+ log " WARNING:"
73
+ log " <red>The configuration file seems to be broken! Please double-check it by running:</red>"
74
+ log " <red>#{ctl} -t</red>"
75
+ end
63
76
  log ""
64
77
  log " To install #{PROGRAM_NAME} against this specific Apache version:"
65
78
  log " #{PlatformInfo.ruby_command} #{PhusionPassenger.bin_dir}/passenger-install-apache2-module --apxs2-path='#{apxs2}'"
@@ -145,7 +158,6 @@ module PhusionPassenger
145
158
  log " --> #{result.config_file}"
146
159
  else
147
160
  log "<red> --> Cannot detect default config file location!</red>"
148
- result.httpd = nil
149
161
  end
150
162
  end
151
163
  if result.httpd
@@ -162,6 +174,9 @@ module PhusionPassenger
162
174
  result.a2enmod = PlatformInfo.a2enmod(:apxs2 => apxs2)
163
175
  result.a2dismod = PlatformInfo.a2dismod(:apxs2 => apxs2)
164
176
  end
177
+ if result.httpd
178
+ result.config_file_broken = PlatformInfo.apache2ctl_V(:apxs2 => apxs2).nil?
179
+ end
165
180
  if result.httpd
166
181
  log "<green>Found a usable Apache installation using #{apxs2}.</green>"
167
182
  true