这个问题困扰了我好几天,我想我终于把它缩小了。我正在使用Facebook JS SDK进行客户端身份验证:
FB.login(function(response) {
if (response.authResponse) {
var url = "/auth/facebook/callback?redirect=";
url += '&' + $.param({ signed_request: response.authResponse.signedRequest });
window.location = url;
}
}, { scope:'email,publish_stream,publish_actions' })
请注意,我手动传入signedRequest。由于某些原因,当我不这样做时,我收到一个错误,抱怨必须有“代码”参数或签名请求(OmniAuth Strategies Facebook NoAuthorizationCodeError (must pass either a `code` parameter or a signed request (via `signed_request` parameter):)。这是omniauth-facebook gem版本1.4.0。如果我使用1.4.1的最新版本,我会收到其他人似乎都会收到的invalid_credentials问题。
当我尝试登录时,会发生一些奇怪的事情。我打开了Chrome调试器,切换到了“网络”标签。我看到两个网络请求,都是GET到
https://www.MYHOST.com/auth/facebook/callback?redirect=&signed_request=BIGSTRINGHERE
然而,有趣的是,第一个请求的状态为301,第二个请求的状态为302,下一个网络请求是/ auth / failure回调。为了让事情更令人费解,这不会在本地重现,只在生产中。在本地,它可以工作,只能执行一个请求,其http状态为302。
同样值得注意的是,在点击失败回调后,它会返回到我的网站主页,然后会触发自动登录功能,因为它检测到用户是FB用户并且在网站上有一个帐户。这段代码点击相同的回调网址并成功。
所以我的问题是为什么有第二个回调请求,如何摆脱它,大概是让登录正常工作?奖金问题是为什么我必须手动传递signedRequest,而教程似乎不必这样做(例如RailsCast#360)?
一些澄清和提供细节的说明:
我正在使用omniauth-facebook 1.4.0,omniauth 1.1.4和omniauth-oauth 1.0.3
我没有使用Devise。我似乎也不会多次初始化facebook omniauth。
此问题仅发生在本地,而不是使用相同的Facebook应用ID和密码进行生产。登录URL设置为生产域,我使用一些本地配置将生产域指向本地。
appID和秘密是正确的(自动登录工作,它在本地工作)。
Facebook应用程序未处于沙盒模式。
答案 0 :(得分:2)
原来问题是重定向到的回调是https。由于该页面在https中不可用,因此重定向到http,导致数据丢失或数据损坏。我没注意到第二个请求是http而不是https。为该回调操作启用ssl修复了该问题。