Drupal detects whether it's running through HTTPS by looking for $_SERVER['HTTPS']. This variable is not set to "YES" if Drupal runs in HTTP. If your Drupal site sits behind an reverse proxy that serves HTTPS, Drupal will set an incorrect $base_root. This causes various things to break -- most visibly, file uploads and lots of AJAX stuff.

Pound (http://www.apsis.ch/pound) sends an HTTP header, X_FORWARDED_PROTO, which is either "http" or "https". Detecting that solves this problem.

Here's a patch:

--- bootstrap.inc.orig  Thu Jul 26 15:16:45 2007
+++ bootstrap.inc       Sun Oct 14 11:22:12 2007
@@ -254,7 +254,7 @@
   }
   else {
     // Create base URL
-    $base_root = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on') ? 'https' : 'http';
+    $base_root = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on' || isset($_SERVER['HTTP_X_FORWARDED_PROTO']) && $_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https') ? 'https' : 'http';
 
     // As $_SERVER['HTTP_HOST'] is user input, ensure it only contains
     // characters allowed in hostnames.

I haven't been able to discover whether other HTTP reverse proxies use the same variable, but I've seen discussion by the Rails folks suggesting that people using Apache to proxy set RequestHeader set X_FORWARDED_PROTO "https" in their Apache configuration.

An alternative method for this might be:

--- bootstrap.inc.orig  Thu Jul 26 15:16:45 2007
+++ bootstrap.inc       Sun Oct 14 11:45:39 2007
@@ -254,7 +254,7 @@
   }
   else {
     // Create base URL
-    $base_root = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on') ? 'https' : 'http';
+    $base_root = isset($_SERVER['HTTP_X_FORWARDED_PROTO']) ? $_SERVER['HTTP_X_FORWARDED_PROTO'] : ((isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on') ? 'https' : 'http');
 
     // As $_SERVER['HTTP_HOST'] is user input, ensure it only contains
     // characters allowed in hostnames.

The former method is simpler to understand. The latter one may provide (very marginally) higher performance.

.

CommentFileSizeAuthor
#1 bootstrap.inc-183398.patch576 bytesghoti

Comments

ghoti’s picture

Version: 5.2 » 5.3
Status: Active » Needs review
StatusFileSize
new576 bytes

Patch for 5.3 attached.

ghoti’s picture

Status: Needs review » Closed (won't fix)

For the time being, the logic from this can be hacked into settings.php, since $base_root is never an issue if $base_url is already set.

bkonia’s picture

Here's a simpler solution:

Add the following line to the beginning of bootstrap.inc

if(isset($_SERVER['HTTP_X_FORWARDED_PROTO'])) $_SERVER['HTTPS'] = 'on';