Facebook JavaScript SDK over HTTPS loading non-secure items

paperclip picture paperclip · Mar 6, 2011 · Viewed 23.8k times · Source

I have a Facebook application that uses the Facebook Connect.js.

I am running my application over HTTPS. All content on the site is delivered from https:// with the exception of some content that must be included within Facebook's Connect.js

The problem is that I get warning messages saying that there are non-secure items within the page.

I've checked what scripts are being loaded using Chrome's Developer Tools / Network tab to see what files are being loaded and from where.

The only one I can see that is being loaded over HTTP and not over HTTPS is a file called http://static.ak.facebook.com/connect/canvas_proxy.php.

How can I force this file to use HTTPS?

Answer

Ralph Holzmann picture Ralph Holzmann · Aug 24, 2011

TL;DR

set FB._https to true before calling FB.init. Like so:

FB._https = true;
FB.init({
    /* your app id and stuff */
});

Explanation

If you unminify the Facebook JavaScript SDK, you'll see that its basically an object literal with a bunch of properties. One of these properties is _https, which is a boolean. This property determines which set of URLs to use (stored in FB._domain) when making API requests. It seems as though Facebook keeps two sets of URLs for each type of API request -- a secure URL and and non-secure URL -- then uses a switch function called getDomain() to determine which to use when making requests.

The reason the JavaScript SDK causes security warnings is due to the way the FB._https property is defined. This is how it's currently defined as of 2011-8-24:

_https: (window.name.indexOf('_fb_https') > -1)

Apparently Facebook thinks that if the window.name property has _fb_https in it, then it must be a secure app. This is obviously incorrect. The real test should be something similar to this:

_https: window.location.protocol == "https:"

Unfortunately, the SDK is not open source or even well documented, so I can't submit a pull request for this change :P. In the short term, setting FB._https to true manually before calling FB.init should do the trick.