2011-07-19 18 views
2

私はクラスを作成しました(OAuthの仕組みを知ることができました)。それは正常に動作しています。私はクラスでアクセストークンを取得できます。しかし、私がアップデートを投稿しようとすると、私は認証されていないと言います!私はここで間違って何をしていますか?OAuth - Twitterでのエラー(認証できませんでした)

// By Kevin Jacobs 
class OAuth { 

    private $url = null; 
    private $debug = false; 
    private $method = 'POST'; 
    private $oauthData = array(); 
    private $data = array(); 
    private $token = array('key' => '', 'secret' => ''); 
    private $consumer = array('key' => '', 'secret' => ''); 

    /** 
    * Encode a string in such a way you can use it for OAuth. 
    * @param string $oauthData Data to encode 
    * @return string $encData Encoded data 
    */ 
    public static function encode($oauthData) { 
     if (is_string($oauthData)) { 
      return str_ireplace(
       array('+', '%7E'), 
       array(' ', '~'), 
       rawurlencode($oauthData) 
      ); 
     } else { 
      return ''; 
     } 
    } 

    /** 
    * Generates a relative unique random string of a certain length. 
    * @param int $length Length of the string 
    * @return string $strRand A random string 
    */ 
    public static function generateString($length = 40) { 
     // Only strong cryptographic strings are allowed 
     while (!isset($bStrong) || $bStrong === false) { 
      $bytes = openssl_random_pseudo_bytes(floor($length/2), $bStrong); 
     } 
     $strRand = bin2hex($bytes); 
     return sha1($strRand); 
    } 

    /** 
    * Generate a token pair (key and secret). 
    * @return array $tokenPair 
    */ 
    public static function generateTokenPair() { 
     $tokenPair = array(); 
     $tokenPair['key'] = self::generateString(); 
     $tokenPair['secret'] = self::generateString(); 
     return $tokenPair; 
    } 

    /** 
    * Set the callback URL. 
    * @param string $callbackURL 
    */ 
    public function setCallback($callback = null) { 
     if ($callback === null) { 
      $callback = 'http'; 
      if ($_SERVER['SERVER_PORT'] == 443) $callback .= 's'; 
      $callback .= '://' . $_SERVER['SERVER_NAME']; 
      if ($_SERVER['SERVER_PORT'] != 80 && $_SERVER['SERVER_PORT'] != 443) { 
       $callback .= ':' . $_SERVER['SERVER_PORT']; 
      } 
      $callback .= $_SERVER['REQUEST_URI']; 
     } 
     $this->oauthData['oauth_callback'] = $callback; 
    } 

    /** 
    * Get the callback URL. 
    * @return string $callbackURL 
    */ 
    public function getCallback() { 
     return $this->oauthData['oauth_callback']; 
    } 

    /** 
    * Generate the nonce. 
    * @return string $nonce 
    */ 
    public function setNonce() { 
     $this->oauthData['oauth_nonce'] = md5(self::generateString(20) . mktime()); 
     return $this->oauthData['oauth_nonce']; 
    } 

    /** 
    * Set the timestamp. 
    * @return int $timestamp 
    */ 
    public function setTimestamp() { 
     $this->oauthData['oauth_timestamp'] = mktime(); 
     return $this->oauthData['oauth_timestamp']; 
    } 

    /** 
    * Set the OAuth version. 
    * @param string Version 
    */ 
    public function setVersion($version = '1.0') { 
     $this->oauthData['oauth_version'] = $version; 
    } 

    /** 
    * Set the HTTP method. 
    * @param string Method 
    */ 
    public function setMethod($method = 'POST') { 
     $this->method = trim(strtoupper($method)); 
    } 

    /** 
    * Get the HTTP method. 
    * @return string Method 
    */ 
    public function getMethod() { 
     return $this->method; 
    } 

    /** 
    * Get the URL to call. 
    * @return string URL 
    */ 
    public function getURL() { 
     return $this->url; 
    } 

    /** 
    * Set the URL to call. 
    * @param string URL 
    */ 
    public function setURL($URL) { 
     $this->url = $URL; 
    } 

    /** 
    * Get the token key and secret 
    * @return array $token Containing token key and secret 
    */ 
    public function getToken() { 
     return $this->token; 
    } 

    /** 
    * Set the token 
    * @param string $tokenKey Token key 
    * @param string $tokenSecret Token secret 
    */ 
    public function setToken($tokenKey, $tokenSecret = null) { 
     $this->token['key'] = $tokenKey; 
     $this->token['secret'] = $tokenSecret; 
     $this->oauthData['oauth_token'] = $tokenKey; 
     $this->oauthData['oauth_token_secret'] = $tokenSecret; 
    } 

    /** 
    * Get the consumer 
    * @return array $consumer Containing consumer key and secret 
    */ 
    public function getConsumer() { 
     return $this->consumer; 
    } 

    /** 
    * Set the consumer 
    * @param string $consumerKey Consumer key 
    * @param string $consumerSecret Consumer secret 
    */ 
    public function setConsumer($consumerKey, $consumerSecret) { 
     $this->oauthData['oauth_consumer_key'] = $consumerKey; 
     $this->consumer['key'] = $consumerKey; 
     $this->consumer['secret'] = $consumerSecret; 
    } 

    /** 
    * Generate the signature. 
    * @return array Signature properties 
    */ 
    public function setSignature() { 
     // Set the signature method 
     $this->oauthData['oauth_signature_method'] = 'HMAC-SHA1'; 
     // First, sort the OAuth data 
     $oauthData = $this->oauthData; 
     ksort($oauthData); 
     // Now combine them in a string 
     $query = http_build_query($oauthData); 
     // Make it URL proof 
     $query = rawurlencode($query); 
     // Fetch the method and URL 
     $method = $this->getMethod(); 
     $url = $this->getURL(); 
     // Make the URL URL proof 
     $url = rawurlencode($url); 
     // Now bind everything together 
     $baseString = $method . '&' . $url . '&' . $query; 
     // Retrieve the key 
     $consumer = $this->getConsumer(); 
     $token = $this->getToken(); 
     $key = self::encode($consumer['secret']) . '&' . self::encode($token['secret']); 
     // Encrypt the base string 
     $signature = hash_hmac('SHA1', $baseString, $key, true); 
     // And make it URL proof using base64_encode 
     $signature = base64_encode($signature); 
     $this->oauthData['oauth_signature'] = $signature; 
    } 

    public function setVerifier($verifier) { 
     $this->oauthData['oauth_verifier'] = $verifier; 
    } 

    public function debugOn() { 
     $this->debug = true; 
    } 

    public function debugOff() { 
     $this->debug = false; 
    } 

    public function setData($data) { 
     $this->data = $data; 
    } 

    public function call($url) { 
     $method = $this->getMethod(); 
     $this->setURL($url); 
     $this->setNonce(); 
     $this->setTimestamp(); 
     $this->setSignature(); 
     $oauthData = $this->oauthData; 
     $data = $this->data; 
     $data = array_merge($data, $oauthData); 

     if ($method == 'GET') { 
      $url = explode('#', $url); 
      $url = reset($url); 
      if (strpos($url, '?') !== false) { 
       $binder = '&'; 
      } else { 
       $binder = '?'; 
      } 
      $url .= $binder . http_build_query($oauthData); 
     } 
     $ch = curl_init(); 
     if (!empty($headers)) { 
      curl_setopt($ch, CURLOPT_HTTPHEADER, $headers); 
     } 
     curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); 
     curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false); 
     if ($method == 'POST') { 
      curl_setopt($ch, CURLOPT_POST, true); 
      curl_setopt($ch, CURLOPT_POSTFIELDS, $oauthData); 
     } 
     curl_setopt($ch, CURLOPT_URL, $url); 
     curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); 
     curl_setopt($ch, CURLOPT_HEADER, false); 
     curl_setopt($ch, CURLOPT_FAILONERROR, false); 
     curl_setopt($ch, CURLOPT_MAXREDIRS, 10); 
     curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); 
     curl_setopt($ch, CURLOPT_ENCODING, ''); 
     curl_setopt($ch, CURLOPT_HTTPHEADER, array('Expect:')); 
     $result = curl_exec($ch); 
     curl_close($ch); 
     return $result; 
    } 

} 

$x = new OAuth(); 
$x->debugOn(); 
$x->setVersion('1.0'); 
$x->setConsumer('consumerToken', 'consumerSecret'); 
$x->setToken('accessToken', 'accessSecret'); 
$x->setMethod('POST'); 
$x->setData(array('status' => 'Hello World!')); 
echo $x->call('http://api.twitter.com/1/statuses/update.json', true); 

次のコードが機能している(アクセストークンを取得する):私は一種のここに推測している

$x = new OAuth(); 
$x->debugOn(); 
$x->setVersion('1.0'); 
$x->setConsumer('consumerToken', 'consumerSecret'); 
$x->setToken('accessToken', 'accessSecret'); 
$x->setMethod('POST'); 
if (isset($_GET['oauth_verifier']) && isset($_GET['oauth_token'])) { 
    // Request token -> Access token 
    $verifier = $_GET['oauth_verifier']; 
    $token = $_GET['oauth_token']; 
    $x->setVerifier($verifier); 
    $x->setToken($token); 
    $x->setMethod('GET'); 
    $result = $x->call('https://api.twitter.com/oauth/access_token', true); 
    parse_str($result); 
    echo 'Access token: ' . $oauth_token . '<br />'; 
    echo 'Access token secret: ' . $oauth_token_secret; 
} else { 
    // Request token 
    $x->setCallback(); 
    $x->setMethod('GET'); 
    $result = $x->call('https://api.twitter.com/oauth/request_token'); 
    parse_str($result); 
    header('Location: http://api.twitter.com/oauth/authorize?oauth_token=' . $oauth_token); 
} 

答えて

1

が、あなたが唯一の「クラスを使用してアクセストークンを取得する」と話しているので、私はあなたが実際にTwitterのOAuth認証フロー全体に従っていないと思う。あなたが元に戻す最初のトークンは、更新を投稿するのに使うことができる本当のトークンを得るための出発点です。 jump through a bunch of hoopsにする必要があります。

私が間違っていて、実際にそれらのフープを通過した場合は、気にしないでください。 :)

+0

あなたの答えをありがとう。私はプロセスを知っています(リクエストトークンで始まり、次にアクセストークンを取得する)。最初の投稿にコードを投稿します。しかし、私はTwitter(認証されていない)のリソースに「到達」できません。 –

+0

よろしいですか。正直なところ、OAuthサポートライブラリのデバッグは、今日の私の場合よりもはるかに優れています。 (私はいくつかの怪しげなものを探しましたが、思ったことはすべてうまくいくように思えました)おそらくあなたが持っている最良の勧告は、https://github.com/abraham/twitteroauth(Twitter PHP OAuthライブラリ私は作品を検証しました)、それを使ってデモンストレーションされた機能的な事例が得られたら、あなたがしていることがどこから来ているのかを見てみましょう。おそらく、あなたはOAuthについて何が欠けているかを教えてくれるでしょう。 – chaos

関連する問題