[英]Facebook PHP SDK session lost, needs JS SDK refresh
真的很奇怪,使用PHP SDK(v 3.2.2)似乎丟失了Facebook會話($ user = 0)。 JS SDK需要重新加載我的頁面以恢復Facebook會話。 這個問題偶爾會發生,有時Facebook會話會丟失,有時它會正常工作。
session_start();
// Run Facebook API
$facebook = new Facebook(array(
'appId' => $config['facebook']['id'],
'secret' => $config['facebook']['secret']
));
// Fetch user
$user = $facebook->getUser();
if($user) {
try {
// Just to be sure, add access token to each request
$user['access_token'] = $facebook->getAccessToken();
// Fetch user details
$user = $facebook->api('/me?access_token='.$user['access_token']);
}
catch (FacebookApiException $e) {
error_log($e);
$user = null;
}
}
主要問題是$ user = $ facebook-> getUser(); 但是,當用戶實際連接時,JS SDK會檢測auth.login事件並重新加載頁面(另一個奇怪的事情是,我使用auth.login,因為auth.authResponseChange事件每秒都會被觸發)。 現在$ user = $ facebook-> getUser(); 返回用戶的uid。
window.fbAsyncInit = function() {
FB.init({
appId : appId,
channelUrl : '//domain.com/signon/channel.php',
status : true,
cookie : true,
xfbml : true
});
FB.Event.subscribe('auth.login', function(response) {
location.reload();
});
};
在Facebook Developer中,我定義了App Domain(domain.com)和Site Url( http://domain.com/ )。 已經嘗試使用/不帶斜杠的Site Url,沒有解決問題。
知道發生了什么,為什么Facebook PHP SDK沒有立即檢測到用戶的會話/不斷丟失用戶的會話並需要重新加載? 這個問題確實導致用戶體驗不好。
非常感謝!
知更鳥
我最近遇到了同樣的問題,似乎如果你在5分鍾左右的時間沒有進行重新加載,那么會話就不會持續存在。 有時候它有效,有時則不然。
我在上周一直在研究它,我能想到的唯一解決方案是使用JS SDK進行頁面重新加載:
FB.Event.subscribe('auth.login', function(response) {
window.location.reload();
});
但我同意,就UX而言,這不是一個非常優雅的解決方案。 您應該在PHP SDK中傳遞cookie
參數,在JS SDK中傳遞oauth參數,看看它是否有效(它不適合我):
$facebook = new Facebook(array(
'appId' => $config['facebook']['id'],
'secret' => $config['facebook']['secret'],
'cookie' => true
));
和
FB.init({
appId : appId,
channelUrl : '//domain.com/signon/channel.php',
status : true,
cookie : true,
xfbml : true,
oauth : true
});
甚至更奇怪的是,我從Github重新下載了最新的PHP SDK並將其上傳到沙箱環境(Apache,PHP 5.4)。 我運行示例(使用JS SDK)AS-IS,它有同樣的問題!
現在,如果以上只是沒有削減芥末,我還有一些建議。
改變SDK的位置
首先,通過
$facebook->getAccessToken();
如果$user
返回0,那對你沒有$user
但是,在對base_facebook.php
進行了一些挖掘base_facebook.php
,我注意到方法getCode()
實際上使用$_REQUEST
從查詢參數中檢索授權代碼。
從PHP手冊,$ _REQUEST是
一個關聯數組,默認情況下包含$ _GET,$ _POST和$ _COOKIE的內容。
但
它與$ _GET,$ _ POST或$ _COOKIE非常不同。
根據您的設置,這可能是一個bugger。 所以相反,在base_facebook.php
中找到如下所示的函數base_facebook.php
getCode()
:
protected function getCode() {
if (isset($_REQUEST['code'])) {
if ($this->state !== null &&
isset($_REQUEST['state']) &&
$this->state === $_REQUEST['state']) {
// CSRF state has done its job, so clear it
$this->state = null;
$this->clearPersistentData('state');
return $_REQUEST['code'];
} else {
self::errorLog('CSRF state token does not match one provided.');
return false;
}
}
return false;
}
並將查詢合並到一個新的數組/變量(讓我們稱之為$code_array
),使用array_merge()
包含$_GET
, $_POST
和$_COOKIE
數組,如下所示:
$code_array = array_merge($_GET,$_POST,$_COOKIE);
您最終得到的是一個包含來自相應請求的所有數據的數組。 只需繼續使用函數內的$code_array
替換$_REQUEST
,即
\\replace $_REQUEST with $code_array;
if (isset($code_array['code'])) {
if ($this->state !== null &&
isset($code_array['state']) &&
$this->state === $code_array['state']) { //...and so on for the rest
這應該很好地完成工作(希望如此)。
可選 - 延長您的訪問令牌生命周期
這是可選的,但無論如何我都包含了它。 大多數新應用程序已經擁有長期訪問令牌,但為了以防萬一,您可以使用$facebook->setExtendedAccessToken();
轉換現有訪問令牌的方法。
注意:您必須調用$facebook->setExtendedAccessToken();
在使用getAccessToken()
方法實際獲取訪問令牌之前。
現在,使用您的代碼
$user = $facebook->getUser();
if($user) {
try {
// Just to be sure, add access token to each request
$facebook->setExtendedAccessToken();
$access_token = $facebook->getAccessToken();
// Fetch user details
$user = $facebook->api('/me?access_token='.$access_token);
}
//and so on..
結論
將$ _REQUEST分解為$ _GET,$ _ POST和$ _COOKIE(即使它默認包含所有三個)似乎確保我們可以毫不費力地獲取SDK設置的cookie。 我說似乎是因為哎呀,我真的不是很自信。
我使用上面的方法讓它在我的情況下工作,所以我希望分享一些知識,因為我已經在這個問題上失去了太多的睡眠,並且找不到可行的解決方案。
希望這可以幫助!
編輯:我忘記提及,更改API請求
$user_profile = $facebook->api('/me');
至
$user_profile = $facebook->api('/'.$user.'?access_token='.$access_token);
這也是我也做過的事情,它起了作用。 :)
也許是因為Facebook PHP SDK不是ajax而且我們使用的是PHP頁面,而且我們的服務器加載速度比Facebook的認證過程更快,以回讀有效的會話。 Facebook PHP SDK需要的是從我們的應用程序刷新會話驗證的頁面,這應該內置到Facebook Javascript SDK,但它看起來不是。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.