8

I'm getting started with Yelp API v3 (Fusion). I have created an app, got Client ID and Client Secret.

I understand that I need to get a token from Yelp API and then using business ID retrieve json data.

I've found the following PHP code:

$postData = "grant_type=client_credentials&".
            "client_id=YOURCLIENTID&".
            "client_secret=SECRET";
$ch = curl_init();

//set the url
curl_setopt($ch,CURLOPT_URL, "https://api.yelp.com/oauth2/token");
//tell curl we are doing a post
curl_setopt($ch,CURLOPT_POST, TRUE);
//set post fields
curl_setopt($ch,CURLOPT_POSTFIELDS, $postData);
//tell curl we want the returned data
curl_setopt($ch,CURLOPT_RETURNTRANSFER, TRUE);
$result = curl_exec($ch);

//close connection
curl_close($ch);

if($result){
   $data = json_decode($result);
   echo "Token: ".$data->access_token;
}

I've entered my ID and SECRET but got a blank page. What else am I missing?

ekad
  • 13,718
  • 26
  • 42
  • 44
santa
  • 13,148
  • 42
  • 144
  • 230
  • is `var_dump($result)` empty? – brianforan Jun 13 '17 at 20:10
  • @brianforan It outputs: bool(false) – santa Jun 13 '17 at 20:41
  • I'd test it on postman first and make sure the request itself is working, then when I'm sure of that I'd switch to php or whatever language I'm using to try it out. Unfortunately I'm not much help otherwise. – brianforan Jun 13 '17 at 20:45
  • https://stackoverflow.com/questions/21271140/curl-and-php-how-can-i-pass-a-json-through-curl-by-put-post-get maybe this will help, I think your `$postData` is formed oddly, but that could be normal – brianforan Jun 13 '17 at 20:46

2 Answers2

4

there's 3 versions of the API, you don't specify which version you're targeting, V1, V2, or Yelp Fusion (V3?) , but seeing as V2 is in the process of being retired (for example, they wont allow new programmers to sign up for an access token for V2), i guess you mean Fusion.

according to the docs, it all starts by making a request to https://api.yelp.com/oauth2/token , using your client_id and client_secret (that you get when registering a new app), and a hardcoded grant_type = client_credentials - and your code does do that, but it doesn't properly url encode the client_id and client_secret, that may be why you're getting a blank page (and that in itself means that you're not debugging using CURLOPT_VERBOSE - when debugging curl requests, always use CURLOPT_VERBOSE - we dont know if it connected and got a http 204 OK No Content, or a 500 Internal Server Error, or if your connection was outright blocked, but CURLOPT_VERBOSE would tell you.), when you get the access_token from the oauth2/token url, it comes encoded in JSON format, use json_decode to decode it.

when you got that token, for further API calls, set the http header Authorization: Bearer TOKEN for autentication.

here's my code, playing around with the API, logging in (getting an authorization_token), then getting business information on dentistry-for-kids-and-adults-canyon-country. unfortunately, the business search API seems broken, as it only returns 500 Internal Server Errors for everything i try. also i'm using the hhb_curl from https://github.com/divinity76/hhb_.inc.php/blob/master/hhb_.inc.php as a convenience wrapper around curl (takes care of CURLOPT_VERBOSE and giving it a file to put debug info in, setting CURLOPT_ENCODING for faster transfers, checking the return value of each curl_setopt, throwing an exception if any of the curl options could not be set and telling me exactly which option failed to be set, etc) - and if you want to testrun this code, make sure to replace client_id and client_secret, as the ones i posted here are fake (but have the same length and general structure, generated by this code https://gist.github.com/divinity76/c43e8ceb803969def0c0369b8ec6de4b )

<?php
declare(strict_types = 1);
// hhb_.inc.php from https://github.com/divinity76/hhb_.inc.php/blob/master/hhb_.inc.php
require_once ('hhb_.inc.php');
$hc = new hhb_curl ( 'https://api.yelp.com/oauth2/token', true );
$hc->setopt_array ( array (
        CURLOPT_POST => true,
        CURLOPT_POSTFIELDS => http_build_query ( array (
                'grant_type' => 'client_credentials', // << hardcoded
                'client_id' => 'Q3sE0uuprHlZx3UbjPlnXX',
                'client_secret' => 'Q3sE0uuprHlZx3UbjPlnXXQ3sE0uuprHlZx3UbjPlnXXQ3sE0uuprHlZx3UbjPln' 
        ) ) 
) );
$hc->exec ();
hhb_var_dump ( $hc->getStdErr (), $hc->getStdOut () );
$json = $hc->getResponseBody ();
$parsed = json_decode ( $json, true );
if (! isset ( $parsed ['access_token'] )) {
    throw new \RuntimeException ( 'failed to get access token!' );
}
$access_token = $parsed ['access_token'];
$hc->setopt_array ( array (
        CURLOPT_HTTPGET => true,
        CURLOPT_URL => 'https://api.yelp.com/v3/businesses/' . urlencode ( 'dentistry-for-kids-and-adults-canyon-country' ),
        CURLOPT_HTTPHEADER => array (
                'Authorization: Bearer ' . $access_token 
        ) 
) );
$hc->exec ();
hhb_var_dump ( $hc->getStdErr (), $hc->getStdOut () );
$json = $hc->getResponseBody ();
$parsed = json_decode ( $json, true );
hhb_var_dump ( $parsed );

/*
 * the business search api seems to be severly broken, giving me 500 Internal Server Errors all the time...
 * $hc->setopt_array ( array (
 * CURLOPT_POST => true,
 * CURLOPT_POSTFIELDS => http_build_query ( array (
 * //'location' => "375 Valencia St, San Francisco"
 * //somewhere in San Francisco.
 * 'latitude'=>'37.7670169511878',
 * 'longitude'=>'-122.42184275'
 *
 * ) ),
 * CURLOPT_URL => 'https://api.yelp.com/v3/businesses/search',
 * CURLOPT_HTTPHEADER => array (
 * 'Authorization: Bearer ' . $access_token
 * )
 * ) );
 * $hc->exec ();
 * hhb_var_dump ( $hc->getStdErr (), $hc->getStdOut () );
 * $json = $hc->getResponseBody ();
 * $parsed = json_decode ( $json, true );
 * hhb_var_dump ( $parsed );
 */

also be aware that the 2nd parameter for hhb_curl::__construct is called $insecureAndComfortableByDefault - which disables SSL certificate validation (), and enables compressed transfers (as for why that may be a problem, google "ssl crime vulnerability"), and is disabled by default (in an attempt to be "secure by default"), but i generally keep it on for ease of development

hanshenrik
  • 15,263
  • 3
  • 28
  • 61
  • Cool, thanks for this example. I'm getting a few errors. First it gives me Warning: Unsupported declare 'strict_types'... and after I comment it out it says: Parse error: syntax error, unexpected ':', expecting '{' in /mypath/hhb_.inc.php on line 4 My PHP Version 5.3.6 – santa Jun 16 '17 at 20:30
  • @santa this code is written in PHP7. there is a PHP5 version at https://github.com/divinity76/hhb_.inc.php/blob/master/hhb_.inc.php5.php , but anyone using 5.3 today is crazy. there's several known vulnerabilities in 5.3 that will never be fixed (off the top of my head, unserialize() has code execution vulnerabilities, and there's a DoS vulnerability by sending a lot of small POST parameters where php will hang for hours on 100% cpu), you really should upgrade to PHP 5.6. the backwards-compatibility issues are minimal (off the top of my head, need to replace the ereg/eregi functions) – hanshenrik Jun 17 '17 at 11:26
  • 5.6 is security supported until 31 December 2018, and there's plenty of performance improvements and syntactic sugar (like short array syntax [] , variadic functions, $v=function(){}; ) - and i haven't tested the php5 version on 5.3, just 5.5 – hanshenrik Jun 17 '17 at 11:31
0

Not sure why but I was getting different errors about hhb_.inc.php so I ended-up cobbling something together myself. It seems to work, in case there are other novices struggling out there. Just update client_id and client_secret with your own values. You get those when you register your app with Yelp as developer.

$postData = "grant_type=client_credentials&".
    "client_id=MyClientIDl94gqHAg&".
    "client_secret=SomEcoDehIW09e6BGuBi4NlJ43HnnHl4S7W5eoXUkB";


// GET TOKEN
$curl = curl_init();

//set the url
curl_setopt($curl,CURLOPT_URL, "https://api.yelp.com/oauth2/token");
//tell curl we are doing a post
curl_setopt($curl,CURLOPT_POST, TRUE);
//set post fields
curl_setopt($curl,CURLOPT_POSTFIELDS, $postData);
//tell curl we want the returned data
curl_setopt($curl,CURLOPT_RETURNTRANSFER, TRUE);
$result = curl_exec($curl);

if($result){
    $data = json_decode($result);
}

// GET RESTAURANT INFO
curl_setopt_array($curl, array(
    CURLOPT_URL => "https://api.yelp.com/v3/businesses/north-india-restaurant-san-francisco",
    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(
        "authorization: Bearer ".$data->access_token
    ),
));

$response = curl_exec($curl);
$err = curl_error($curl);

//close connection
curl_close($curl);

if ($err) {
    echo "cURL Error #:" . $err;
} else {
    echo $response;
}
santa
  • 13,148
  • 42
  • 144
  • 230