簡體   English   中英

具有CURL和身份驗證的PHP API調用

[英]PHP api call with CURL and authentication

我得到以下代碼:

    // service
    $url = 'https://services.daisycon.com/publishers/' . $publisher_id  . '/news';

    // initialize curl resource
    $ch = curl_init();

    // set the http request authentication headers
    $headers = array( 'Authorization: Basic ' . base64_encode( $username . ':' . $password ) );

    // set curl options
    curl_setopt($ch, CURLOPT_URL, $url);
    curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); 

    // execute curl
    $response = curl_exec($ch);

    // check http code
    $code = curl_getinfo($ch, CURLINFO_HTTP_CODE);

    // close curl resource
    curl_close($ch);

    if ($code == 200)
    {
        // json decode reponse
        $news = json_decode($response);

        // display response
        foreach ($news as $news_item)
        {
            echo 'id: ' . $news_item->id . "\n";
            echo 'name: ' . $news_item->title . "\n\n";
        }
    }

並使用了此文檔,並研究了此身份驗證 但是,當我回顯代碼顯示0時,我無法使其正常工作。我已經填寫了所有詳細信息。 有人可以告訴我我在做什么錯嗎?

編輯:當我在控制台中運行此:

curl https://services.daisycon.com/publishers/{id}/news -u {username}:{password}

然后工作正常。 那么,如何將該命令設置為PHP代碼呢?

也許使用curl_error()來檢查curl操作是否有錯誤,如果不是200 OK,您也應該檢查一下返回的HTTP代碼是什么,如果您肯定收到200 OK,那么可以返回var_dump( )您的響應變量,以檢查您是否收到了所需的數據以及您使用的屬性名稱正確

以下內容應可幫助您找出問題所在

// service
$url = 'https://services.daisycon.com/publishers/' . $publisher_id  . 
'/news';

// initialize curl resource
$ch = curl_init();

// set curl options
curl_setopt_array($curl, array(
CURLOPT_URL=> $url,
    CURLOPT_RETURNTRANSFER => true,
    CURLOPT_ENCODING => "",
    CURLOPT_MAXREDIRS => 10,
    CURLOPT_TIMEOUT => 30,
    CURLOPT_HTTP_VERSION => CURL_HTTP_VERSION_1_1,
    CURLOPT_CUSTOMREQUEST => "GET",
    CURLOPT_HTTPHEADER => array(
        "accept: application/json",
        "authorization: Basic ".base64_encode($username.":".$password),
        "cache-control: no-cache",
        "content-type: application/json",
    ),
));

// execute curl
$response = curl_exec($ch);
$err = curl_error($curl);

// check http code
$code = curl_getinfo($ch, CURLINFO_HTTP_CODE);

// close curl resource
curl_close($ch);
if ($err) {
    echo "cURL Error #:" . $err;
}
else{
    if ($code == 200)
    {
        // json decode reponse
        $news = json_decode($response);

        // display response
        foreach ($news as $news_item)
        {   
            //checks if both properties are set
            if(isset($news_item->id,$news_item->title)){ 
                echo 'id: ' . $news_item->id . "\n";
                echo 'name: ' . $news_item->title . "\n\n";
            }
            //if not set...
            else{
                echo "Id Or Title Not Set\n";
                var_dump($news);
                echo "\n\n";
            }       
        }
    }
    //if not a 200 OK
    else{
         echo "Did Not Receive 200 OK\n";
         echo "Received Code:".$code."\n\n";
    }
}

也許他們從http基本身份驗證切換到摘要(傳輸用戶名/密碼的更安全方法),或者curl支持的任何其他身份驗證方法。 但是curl https://services.daisycon.com/publishers/{id}/news -u {username}:{password}起作用的事實意味着它 curl本身支持的auth方法。 為什么要自己制作auth標頭? 這很困難且容易出錯,您應該告訴libcurl為您登錄,就像告訴curl(cli程序)為您登錄一樣。

$ch = curl_init();
if(!curl_setopt_array($ch,array(
CURLOPT_HTTPAUTH=>CURLAUTH_ANY,
CURLOPT_USERPWD=>'username:password'
))){throw new \RuntimeException('curl_setopt_array failed. errno:'.curl_errno($ch).'. error:'.curl_error($ch);}

並且在調試curl代碼時,設置CURLOPT_STDERR和CURLOPT_VERBOSE,例如

$debugh=tmpfile();
$debugf=stream_get_meta_data($debugh)['uri'];
curl_setopt_array($ch,array(CURLOPT_STDERR=>$debugh,CURLOPT_VERBOSE=>1));
...
//after curl_exec: 
$curldebugstr=file_get_contents($debugf);
var_dump($curldebugstr);

在curl cli程序中,使用-v參數。 那么您可以將php-libcurl發出的請求與curl命令行參數發出的請求進行比較,它們有什么區別? 可能是他們進行了有害的用戶代理檢測,在這種情況下,您可以使用CURLOPT_USERAGENT偽造curl cli的用戶代理。 同樣,如果curl_setopt(_array)失敗,它將返回bool(false),您應該創建一個包裝器函數,檢查它是否返回false,如果是,則拋出運行時異常,並設置失敗的參數以及curl_error()和curl_errno()報告,並使用這些包裝器。 -或至少每次使用原始函數時都要檢查返回值。

就像是

function _curl_setopt_array($ch,array $arr){foreach($arr as $option=>$val){_curl_setopt($ch,$option,$val);}}
    function _curl_setopt($ch,int $option,$value){
            $ret = curl_setopt ( $ch, $option, $value );
            if (! $ret) {
                throw new InvalidArgumentException ( 'curl_setopt failed. errno: ' . curl_errno ($ch) . '. error: ' . curl_error ($ch));
            }
    }

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM