I'm new to cloud hosting...
I'm working on a PHP web app that's hosted on Heroku as a "Cedar" app. Heroku offers "piggy back" SSL to all their subdomains, so I can load https://myapp.herokuapp.com
just fine. But I can also load http://myapp.herokuapp.com
. I want to force SSL by redirecting http
requests to https
.
Normally, this would be easy. I would just use mod_rewrite as follows:
RewriteCond %{HTTPS} != on
RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
BUT THIS DOESNT WORK ON HEROKU!
It appears that SSL terminates upstream, before the traffic ever hits my app. So the %{HTTPS}
condition is never met, and the result is a redirect loop. I've also tried the following, which also didn't work:
RewriteCond %{SERVER_PORT} != 443 #<--also redirect loop
RewriteCond %{REQUEST_SCHEME} !https #<--also redirect loop
So my question is how can I detect/redirect-to HTTPS when it's terminated upstream?
I added one line to the great answer given above so it doesn't break my local dev environment which doesn't have SSL configured:
(Note RewriteRule is applied only if all preceeding RewriteCond's hold).
After spending all day on this, I figured it out!!
The issue is eloquently summarized here.
Bottom line: Heroku sets its own custom header to indicate the ORIGINAL scheme of the traffic (before SSL terminated at the load balancer).
So THIS works in an .htaccess file on Heroku
The secret sauce is the line with
HTTP:X-Forwarded-Proto
.Hope this helps someone else having the same issues! At the time of writing this there is ZERO documentation on this.
If heroku is not picking up your .htaccess file you might have to use a a custom application level Apache configuration as documented by heroku
Basically you'll need to add this to your profile:
web: vendor/bin/heroku-php-apache2 -C apache_app.conf