2016-01-17 55 views
1

我想使用SOAP證書流程ChannelAdvisor REST API集成。在PHP中使用ChannelAdvisor REST API - 請求不能在CURL中工作

根據他們的文檔,我有這樣的設置在PostMan(在Chrome瀏覽器中REST客戶端)如下:

enter image description here

enter image description here

當我做休息;在REST API服務器返回預期的響應:

enter image description here

於是,我試着用下面的類複製這一在PHP中:

<?php 

class ChannelAdvisorREST { 

    /** 
    * ChannelAdvisor constants & properties 
    */ 
    const BASE_URL = 'https://api.channeladvisor.com/v1'; 
    private $config; 

    /** 
    * Class constructor 
    */ 
    public function __construct() 
    { 
     $this->config = \Config::get('channeladvisor'); 
    } 

    // TEST 
    public function test($accountId) 
    { 
     // var_dump($this->config); 

     var_dump(self::getAccessToken($accountId)); 
    } 
    // TEST 

    /** 
    * Method to get access token from rest server. 
    * 
    * @param $accountId 
    * @return string 
    */ 
    private function getAccessToken($accountId) 
    { 
     return self::curlPOST('/oauth2/token', [ 
      'client_id' => $this->config['api_app_id'], 
      'grant_type' => 'soap', 
      'scope' => 'inventory', 
      'developer_key' => $this->config['api_developer_key'], 
      'password' => $this->config['api_password'], 
      'account_id' => $accountId 
     ]); 
    } 

    /** 
    * Method to generate a HTTP POST request 
    * 
    * @param $endpoint 
    * @param $fields 
    * @return string 
    */ 
    private function curlPOST($endpoint, $fields = array()) 
    { 
     // Open connection 
     $ch = curl_init(); 

     // Set the url, number of POST vars, POST data 
     curl_setopt($ch, CURLOPT_USERPWD, $this->config['api_app_id'] .':'. $this->config['api_shared_secret']); 
     curl_setopt($ch, CURLOPT_URL, self::BASE_URL . $endpoint); 
     curl_setopt($ch, CURLOPT_POST, count($fields)); 
     curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($fields, '', '&')); 
     curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); 
     curl_setopt($ch, CURLOPT_HTTPHEADER, array(
      'Content-Type: application/x-www-form-urlencoded' 
     )); 

     // Execute post request 
     $result = curl_exec($ch); 

     // Close connection 
     curl_close($ch); 

     // Finished 
     return $result; 
    } 
} 

當我執行測試($ ACCID)方法,我得到以下回應:

布爾值false

任何想法爲什麼它不像PostMan測試一樣工作?

P.S.我已經驗證了所有的配置/參數等...與我的PostMan測試是否正確相同。這個類是從我原來的代碼中刪除的版本(在Laravel 4.2中創建的,但這個問題與Laravel無關)。

回答

0

我已經找到了問題。這個問題是由於我的php沒有配置爲curl.cainfo

我發現這個通過添加以下調試代碼到我的curlPOST方法是這樣的:

private function curlPOST($endpoint, $fields = array()) 
{ 
    // Open connection 
    $ch = curl_init(); 

    // Set the url, number of POST vars, POST data 
    curl_setopt($ch, CURLOPT_USERPWD, $this->config['api_app_id'] .':'. $this->config['api_shared_secret']); 
    curl_setopt($ch, CURLOPT_URL, self::BASE_URL . $endpoint); 
    curl_setopt($ch, CURLOPT_POST, count($fields)); 
    curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($fields, '', '&')); 
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); 
    curl_setopt($ch, CURLOPT_HTTPHEADER, array(
     'Content-Type: application/x-www-form-urlencoded' 
    )); 
    curl_setopt($ch, CURLOPT_VERBOSE, true); 
    $verbose = fopen('php://temp', 'w+'); 
    curl_setopt($ch, CURLOPT_STDERR, $verbose); 

    // Execute post request 
    $result = curl_exec($ch); 

    // Debug error 
    if ($result === FALSE) { 
     printf("cUrl error (#%d): %s<br>\n", curl_errno($ch), htmlspecialchars(curl_error($ch))); 
     rewind($verbose); 
     $verboseLog = stream_get_contents($verbose); 
     echo "Verbose information:\n<pre>", htmlspecialchars($verboseLog), "</pre>\n"; 
    } 
    @fclose($verbose); 

    // Close connection 
    curl_close($ch); 

    // Finished 
    return $result; 
} 

此輸出以下錯誤消息:

cUrl error (#60): SSL certificate problem: unable to get local issuer certificate 
Verbose information: 
* Hostname was found in DNS cache 
* Hostname in DNS cache was stale, zapped 
* Trying 216.27.89.14... 
* Connected to api.channeladvisor.com (216.27.89.14) port 443 (#7) 
* SSL certificate problem: unable to get local issuer certificate 
* Closing connection 7 
boolean false 

這讓我跟蹤這個問題與我PHP。

0

兩件事情:

  1. 請確保您發送相同的標題爲您的瀏覽器發送。例如,我在代碼中看不到授權標頭,並且這對於在服務器端授權請求可能非常重要。對於您使用'庫存'而不是'訂單庫存'的範圍也是如此。在這個練習中非常嚴格。

  2. 測試後數據不在數組中,但寫下查詢字符串,因爲它應該根據自己,這樣你知道沒有一些問題由CURL試圖將你的數組轉換爲查詢 - 字符串(注意,兩者都可能用於CURL,數組和查詢字符串)。

所以最容易測試用:

client_id=1234&grant_type=soap&scope=order%20inventory...etc add other variables... 
+0

我的post man測試中的'Authorisation'標題是BASIC AUTH憑證,它使用'CURLOPT_USERPWD'在php中設置 - 這不一樣嗎? '範圍'字段接受'訂單庫存'以及'庫存'(我不認爲問題在這裏)。我已經測試了我的發佈數據,它是一個字符串。 – Latheesan

+0

忽略了CURLOPT_USERPWD,看起來不錯。如果您也將後數據作爲字符串進行測試,那麼我不會看到它在哪裏向南。然後,我會建議通過例如firebug或HTTP標頭來跟蹤http-stream,並檢查是否有例如一個或多個重定向,並且在這些重定向期間cookie將被設置爲具有特定值。這也是很常見的做法。如果瀏覽器出現這種情況,那麼也可以在你的php代碼中實現這個功能。 – PeterH

+0

我已經想通了。看到我的答案。 – Latheesan