简体   繁体   中英

Google Cloud Vision API on PHP AppEngine

I have been using the Google Cloud Vision api with a php app hosted on a private VPS for a while without issue. I'm migrating the app to Google AppEngine and am now running into issues.

I'm using a CURL post to the API, but it's failing on AppEngine. I have billing enabled and other curl requests work without issue. Someone mentioned that calls to googleapis.com won't work on AppEngine, that I need to access the API differently. I'm not able to find any resources online to confirm that.

Below is my code, CURL error #7 is returned, failed to connect to host.

$request_json = '{
            "requests": [
                {
                  "image": {
                    "source": {
                        "gcsImageUri":"gs://bucketname/image.jpg"
                    }
                  },
                  "features": [
                      {
                        "type": "LABEL_DETECTION",
                        "maxResults": 200
                      }
                  ]
                }
            ]
        }';
$curl = curl_init();
curl_setopt($curl, CURLOPT_URL, 'https://vision.googleapis.com/v1/images:annotate?key='.GOOGLE_CLOUD_VISION_KEY);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER, array('Content-type: application/json'));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $request_json);
$json_response = curl_exec($curl);
$status = curl_getinfo($curl, CURLINFO_HTTP_CODE);
if ($status != 200) {
    die("Error: $status, response $json_response, curl_error " . curl_error($curl) . ', curl_errno ' . curl_errno($curl));
}
curl_close($curl);
echo '<pre>';
echo $json_response;
echo '</pre>';

I switch my code to use URLFetch (file_get_contents) instead of CURL. Working great so far. I'm still unsure why CURL didn't work.

The curl request to a Google API fails in PHP because curl uses the Sockets API and Google IPs are blocked with sockets. This restriction is documented in Limitations and restrictions :

Private, broadcast, multicast, and Google IP ranges are blocked


To send the POST request you describe, you can use PHP's stream handlers, providing the necessary context to send the data along. I've adapted the example shown in Issuing HTTP(S) Requests to suit your request:

<!-- language: lang-php -->

$url = 'https://vision.googleapis.com/v1/images:annotate';
$url .= '?key=' . GOOGLE_CLOUD_VISION_KEY;

$data = [
    [
        'image' => [
            'source' => [
                'gcsImageUri' => 'gs://bucketname/image.jpg'
            ]
         ],
         'features' => [
             [
                 'type' => 'LABEL_DETECTION',
                 'maxResults' => 200
             ]
         ]
    ]
];

$headers = "accept: */*\r\nContent-Type: application/json\r\n";

$context = [
    'http' => [
        'method' => 'POST',
        'header' => $headers,
        'content' => json_encode($data),
    ]
];
$context = stream_context_create($context);
$result = file_get_contents($url, false, $context);

I also recommend reading Asserting identity to Google APIs should you decide to use means of authentication other than an API key like OAuth.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM