-1

Facebookのサインアップで「オブジェクト以外のプロパティを取得しようとしています」という問題が発生しています。サーバーは access_token に関連するエラーを返します。

490 行目と 451 行目にエラーがあります。451 行目では解決に成功しましたが、490 行目からまだ 2 つのエラーがあります。

if ( $token->access_token ) を if ( $token['access_token'] ) に変更することで行が修正されました。問題は codeigniter によるものだと思います。

490行目は次のとおりです。

   private function _token_string()
    {
        return 'access_token='.$this->_get('token')->access_token;
    }

コード全体は次のとおりです。

class Facebook_Lib extends CI_Config
{

    private $_api_url;
    private $_api_key;
    private $_api_secret;
    private $_errors = array();
    private $_enable_debug = FALSE;

    function __construct()
    {
        $this->_obj =$CI =& get_instance();

        $this->_obj->load->library('session');
        $this->_obj->load->helper('url');
        $this->_obj->load->helper('facebook');

        $fb_api_id     = $CI->db->get_where('settings', array('code' => 'SITE_FB_API_ID'))->row()->string_value;
        $fb_api_secret = $CI->db->get_where('settings', array('code' => 'SITE_FB_API_SECRET'))->row()->string_value;

        $this->_api_url        = $this->_obj->config->item('facebook_api_url');
        $this->_api_key     = $fb_api_id;
        $this->_api_secret  = $fb_api_secret;

        $this->session = new facebookSession();
        $this->connection = new facebookConnection();
    }

    public function logged_in()
    {
        return $this->session->logged_in();
    }

    public function login($scope = NULL)
    {
        return $this->session->login($scope);
    }

    public function login_url($scope = NULL)
    {
        return $this->session->login_url($scope);
    }

    public function logout()
    {
        return $this->session->logout();
    }

    public function user()
    {
        return $this->session->get();
    }

    public function call($method, $uri, $data = array())
    {
        $response = FALSE;

        try
        {
            switch ( $method )
            {
                case 'get':
                    $response = $this->connection->get($this->append_token($this->_api_url.$uri));
                break;

                case 'post':
                    $response = $this->connection->post($this->append_token($this->_api_url.$uri), $data);
                break;
            }
        }
        catch (facebookException $e)
        {
            $this->_errors[] = $e;

            if ( $this->_enable_debug )
            {
                echo $e;
            }
        }

        return $response;
    }

    public function errors()
    {
        return $this->_errors;
    }

    public function last_error()
    {
        if ( count($this->_errors) == 0 ) return NULL;

        return $this->_errors[count($this->_errors) - 1];
    }

    public function append_token($url)
    {
        return $this->session->append_token($url);
    }

    public function set_callback($url)
    {
        return $this->session->set_callback($url);
    }

    public function enable_debug($debug = TRUE)
    {
        $this->_enable_debug = (bool) $debug;


    }
}

class facebookConnection {

    // Allow multi-threading.

    private $_mch = NULL;
    private $_properties = array();

    function __construct()
    {
        $this->_mch = curl_multi_init();

        $this->_properties = array(
            'code'      => CURLINFO_HTTP_CODE,
            'time'      => CURLINFO_TOTAL_TIME,
            'length'    => CURLINFO_CONTENT_LENGTH_DOWNLOAD,
            'type'      => CURLINFO_CONTENT_TYPE
        );
    }

    private function _initConnection($url)
    {
        $this->_ch = curl_init($url);
        curl_setopt($this->_ch, CURLOPT_RETURNTRANSFER, TRUE);
    }

    public function get($url, $params = array())
    {
        if ( count($params) > 0 )
        {
            $url .= '?';

            foreach( $params as $k => $v )
            {
                $url .= "{$k}={$v}&";
            }

            $url = substr($url, 0, -1);
        }

        $this->_initConnection($url);
        $response = $this->_addCurl($url, $params);

        return $response;
    }

    public function post($url, $params = array())
    {
        // Todo
        $post = '';

        foreach ( $params as $k => $v )
        {
            $post .= "{$k}={$v}&";
        }

        $post = substr($post, 0, -1);

        $this->_initConnection($url, $params);
        curl_setopt($this->_ch, CURLOPT_POST, 1);
        curl_setopt($this->_ch, CURLOPT_POSTFIELDS, $post);

        $response = $this->_addCurl($url, $params);

        return $response;
    }

    private function _addCurl($url, $params = array())
    {
        $ch = $this->_ch;

        $key = (string) $ch;
        $this->_requests[$key] = $ch;

        $response = curl_multi_add_handle($this->_mch, $ch);

        if ( $response === CURLM_OK || $response === CURLM_CALL_MULTI_PERFORM )
        {
            do {
                $mch = curl_multi_exec($this->_mch, $active);
            } while ( $mch === CURLM_CALL_MULTI_PERFORM );

            return $this->_getResponse($key);
        }
        else
        {
            return $response;
        }
    }

    private function _getResponse($key = NULL)
    {
        if ( $key == NULL ) return FALSE;

        if ( isset($this->_responses[$key]) )
        {
            return $this->_responses[$key];
        }

        $running = NULL;

        do
        {
            $response = curl_multi_exec($this->_mch, $running_curl);

            if ( $running !== NULL && $running_curl != $running )
            {
                $this->_setResponse($key);

                if ( isset($this->_responses[$key]) )
                {
                    $response = new facebookResponse( (object) $this->_responses[$key] );

                    if ( $response->__resp->code !== 200 )
                    {
                        $error = $response->__resp->code.' | Request Failed';

                        if ( isset($response->__resp->data->error->type) )
                        {
                            $error .= ' - '.$response->__resp->data->error->type.' - '.$response->__resp->data->error->message;
                        }

                        throw new facebookException($error);
                    }

                    return $response;
                }
            }

            $running = $running_curl;

        } while ( $running_curl > 0);

    }

    private function _setResponse($key)
    {
        while( $done = curl_multi_info_read($this->_mch) )
        {
            $key = (string) $done['handle'];
            $this->_responses[$key]['data'] = curl_multi_getcontent($done['handle']);

            foreach ( $this->_properties as $curl_key => $value )
            {
                $this->_responses[$key][$curl_key] = curl_getinfo($done['handle'], $value);

                curl_multi_remove_handle($this->_mch, $done['handle']);
            }
      }
    }
}

class facebookResponse {

    private $__construct;

    public function __construct($resp)
    {
        $this->__resp = $resp;

        $data = json_decode($this->__resp->data);

        if ( $data !== NULL )
        {
            $this->__resp->data = $data;
        }
    }

    public function __get($name)
    {
        if ($this->__resp->code < 200 || $this->__resp->code > 299) return FALSE;

        $result = array();

        if ( is_string($this->__resp->data ) )
        {
            parse_str($this->__resp->data, $result);
            $this->__resp->data = (object) $result;
        }

        if ( $name === '_result')
        {
            return $this->__resp->data;
        }

        return $this->__resp->data->$name;
    }
}

class facebookException extends Exception {

    function __construct($string)
    {
        parent::__construct($string);
    }

    public function __toString() {
        return "exception '".__CLASS__ ."' with message '".$this->getMessage()."' in ".$this->getFile().":".$this->getLine()."\nStack trace:\n".$this->getTraceAsString();
    }
}

class facebookSession {

    private $_api_key;
    private $_api_secret;
    private $_token_url     = 'oauth/access_token';
    private $_user_url      = 'me';
    private $_data          = array();

    function __construct()
    {
        $this->_obj =$CI =& get_instance();

        $fb_api_id     = $CI->db->get_where('settings', array('code' => 'SITE_FB_API_ID'))->row()->string_value;
        $fb_api_secret = $CI->db->get_where('settings', array('code' => 'SITE_FB_API_SECRET'))->row()->string_value;

        $this->_api_key     = $fb_api_id;
        $this->_api_secret  = $fb_api_secret;

        $this->_token_url   = $this->_obj->config->item('facebook_api_url').$this->_token_url;
        $this->_user_url    = $this->_obj->config->item('facebook_api_url').$this->_user_url;

        $this->_set('scope', $this->_obj->config->item('facebook_default_scope'));

        $this->connection = new facebookConnection();

        if ( !$this->logged_in() )
        {
             // Initializes the callback to this page URL.
            $this->set_callback();
        }

    }

    public function logged_in()
    {
        return ( $this->get() === NULL ) ? FALSE : TRUE;
    }

    public function logout()
    {
        $this->_unset('token');
        $this->_unset('user');
    }

    public function login_url($scope = NULL)
    {
        $url = "http://www.facebook.com/dialog/oauth?client_id=".$this->_api_key.'&redirect_uri='.urlencode($this->_get('callback'));

        if ( empty($scope) )
        {
            $scope = $this->_get('scope');
        }
        else
        {
            $this->_set('scope', $scope);
        }

        if ( !empty($scope) )
        {
            $url .= '&scope='.$scope;
        }

        return $url;
    }

    public function login($scope = NULL)
    {
        $this->logout();

        if ( !$this->_get('callback') ) $this->_set('callback', current_url());

        $url = $this->login_url($scope);

        return redirect($url);
    }

    public function get()
    {
        $token = $this->_find_token();
        if ( empty($token) ) return NULL;

        // $user = $this->_get('user');
        // if ( !empty($user) ) return $user;

        try 
        {
            $user = $this->connection->get($this->_user_url.'?'.$this->_token_string());
        }
        catch ( facebookException $e )
        {
            $this->logout();
            return NULL;
        }

        // $this->_set('user', $user);
        return $user;
    }

    private function _find_token()
    {
        $token = $this->_get('token');

        if ( !empty($token) )
        {
            if ( !empty($token->expires) && intval($token->expires) >= time() )
            {
                // Problem, token is expired!
                return $this->logout();
            }

            $this->_set('token', $token);
            return $this->_token_string();
        }

        if ( !isset($_GET['code']) )
        {
            return $this->logout();
        }

        if ( !$this->_get('callback') ) $this->_set('callback', current_url());
        $token_url = $this->_token_url.'?client_id='.$this->_api_key."&client_secret=".$this->_api_secret."&code=".$_GET['code'].'&redirect_uri='.urlencode($this->_get('callback'));

        try 
        {
            $token = $this->connection->get($token_url);
        }
        catch ( facebookException $e )
        {
            $this->logout();
            redirect($this->_strip_query());
            return NULL;
        }

        $this->_unset('callback');

        if ( $token['access_token'] )
        {
            if ( !empty($token->expires) )
            {
                $token->expires = strval(time() + intval($token->expires));
            }

            $this->_set('token', $token);
            redirect($this->_strip_query());
        }

        return $this->_token_string();
    }

    private function _get($key)
    {
        $key = '_facebook_'.$key;
        return $this->_obj->session->userdata($key);
    }

    private function _set($key, $data)
    {
        $key = '_facebook_'.$key;
        $this->_obj->session->set_userdata($key, $data);
    }

    private function _unset($key)
    {
        $key = '_facebook_'.$key;
        $this->_obj->session->unset_userdata($key);
    }

    public function set_callback($url = NULL)
    {
        $this->_set('callback', $this->_strip_query($url));
    }

    private function _token_string()
    {
        return 'access_token='.$this->_get('token')->access_token;
    }

    public function append_token($url)
    {
        if ( $this->_get('token') ) $url .= '?'.$this->_token_string();

        return $url;
    }

    private function _strip_query($url = NULL)
    {
        if ( $url === NULL )
        {
            $url = ( empty($_SERVER['HTTPS']) ) ? 'http' : 'https';
            $url .= '://'.$_SERVER['HTTP_HOST'].$_SERVER['REQUEST_URI'];
        }

        $parts = explode('?', $url);
        return $parts[0];
    }
}
4

1 に答える 1

0

このライブラリで何が起こっているのかわかりません。451 行目では、$token 配列で返された値を探しています。次に、CI セッションでそれを設定する非常に複雑な方法を経て、CI セッションから即座にコールバックします。

458 行目でトークンをセッションに設定し、462 でそれを返しますが、session->userdata('token') を返すメソッドを呼び出すメソッドを呼び出します。セッションデータで値を取得しますが、返された値の上に ->access_token のデータを見つけようとしますが、それが存在しないため、490 で失敗するのはそのためです。

行 462 の前に $token をダンプし、それがオブジェクトか配列かを確認します。それが ann 配列である場合、490 の ->access_token が機能しない理由が説明されます。それがオブジェクトの場合、462行目を次のように変更します

return 'access_token='.$token->access_token;

または $token のダンプがオブジェクトの値を示しているものは何でも (私はそれが access_token であると想定しています)、それが機能するかどうかを確認します。もしそうなら、なぜ彼らがこれらすべての余分なステップを書いたのか、そしてそれが何のために使われるのかを理解する必要があります. そうでない場合は、それを良いと呼びます。

Facebookには、githubで利用できるライブラリが書かれており、codeigniterのライブラリディレクトリにドロップするだけで問題なく動作します。使用しているこのクラスを削除して、Facebook が提供するものを使用することをお勧めします。このようにして、開発者サイトから直接 Facebook と統合する方法を学ぶことができます。API 呼び出しが変更された場合でも、コードを書き直す必要はありません。ライブラリ ディレクトリ内の 2 つのファイルを置き換えるだけです。

https://github.com/facebook/facebook-php-sdk/tree/master/src

お役に立てれば。

于 2012-11-07T22:27:50.180 に答える