使用 Square Connect API 和 PHP 上传项目图片
Upload item image using Square Connect API and PHP
我查看了 Whosebug 上关于此问题的旧问题。
但是我没有找到 php 集成的任何示例。
这是我执行此操作的代码示例,但它失败了
$url = 'https://connect.squareup.com/v1/me/items/9999999/image';
$auth_bearer = 'Authorization: Bearer ' . $this->accessToken;
$image_data = base64_encode(file_get_contents('image.jpeg'));
$header = array(
$auth_bearer,
'Accept: application/json',
'Content-Type: multipart/form-data; boundary=BOUNDARY',
);
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
curl_setopt($ch, CURLOPT_POSTFIELDS, 'files=' . $image_data);
$head = curl_exec($ch);
curl_close($ch);
$response = json_decode($head);
echo "<pre>";
print_r($response);
echo "</pre>";
什么也没发生...有什么帮助吗?
谢谢
您需要 post 原始图像数据(非 base64 编码)与文件 object 的适当多部分 header。这是一个工作示例(替换 ACCESS_TOKEN
、ITEM_ID
和 IMAGE_FILE
)。
<?php
function uploadItemImage($url, $access_token, $image_file) {
$headers = ["Authorization: Bearer $access_token"];
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, ['image_data' => "@$image_file"]);
curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$data = curl_exec($ch);
$return_status = curl_getinfo($ch, CURLINFO_HTTP_CODE);
print "POST to $url with status $return_status\n";
curl_close($ch);
return $data ? json_decode($data) : false;
}
print_r(
uploadItemImage(
'https://connect.squareup.com/v1/me/items/ITEM_ID/image',
'ACCESS_TOKEN',
'IMAGE_FILE.jpg'
)
);
?>
这是我的 PHP 上传 PNG 图像的实现。有时不同的代码视图会有所帮助。
如@Troy 所述,图像要包含的重要字段是 'Content-Type: multipart/form-data'。我上传到 Square 的所有其他内容都使用 'Content-Type: application/json'.
$square_url = 'https://connect.squareup.com/v1/me/items/' . $square_item_id . '/image';
$cfile = new CURLFile($image_path_on_server, 'image/png', 'image_data');
$image_data = array('image_data' => $cfile);
$curl = curl_init();
curl_setopt($curl, CURLOPT_HTTPHEADER, array(
'Authorization: Bearer ' . $access_token,
'Content-Type: multipart/form-data',
'Accept: application/json'
));
curl_setopt($curl, CURLOPT_POSTFIELDS, $image_data);
curl_setopt($curl, CURLOPT_URL, $square_url);
curl_setopt($curl, CURLOPT_POST, TRUE);
curl_setopt($curl, CURLOPT_SAFE_UPLOAD, TRUE);
curl_setopt($curl, CURLOPT_BINARYTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, FALSE);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, FALSE);
curl_setopt($curl, CURLINFO_HEADER_OUT, TRUE);
curl_setopt($curl, CURLOPT_VERBOSE, TRUE);
$json = curl_exec($curl);
curl_close($curl);
严格来说 Square API 文档,他们的方法可以在记住一些事情的情况下实现。
-- 您的请求必须包含在边界内并包含内容配置、名称、文件名、内容类型,如下例所示。
--BOUNDARY
Content-Disposition: form-data; name="image_data"; filename="MyImage.png"
Content-Type: image/png
{BLANK LINE IS REQUIRED}
IMAGE BINARY DATA GOES HERE
--BOUNDARY--
本质上,请求的格式必须与示例中指定的格式完全相同。这包括 'boundary'、换行符、必要的 headers、headers 之间的空行(出于某种原因,如果该行不存在则没有任何作用),以及实际图像二进制数据。注意:边界可以是您选择的任何字符串,但必须始终如一地使用。在代码中,这看起来像这样:
$boundary = "---------------------" . md5(mt_rand() . microtime());
$imageToUpload = "--{$boundary}" . "\r\n" .
"Content-Disposition: form-data; name=\"image_data\"; filename=\"" . $full_path_to_image_file . "\"" . "\r\n" .
"Content-Type: image/jpeg" . "\r\n" .
"\r\n" . // <- empty line is required
(file_get_contents($full_path_to_image_file)) . "\r\n" .
"--{$boundary}--";
以上将产生如下所示的请求:
-----------------------51b62743876b1201aee47ff4b1910e49
Content-Disposition: form-data; name="image_data"; filename="/some/directory/image.jpg"
Content-Type: image/jpeg
����
-----------------------51b62743876b1201aee47ff4b1910e49--
-- 从技术上讲,请求中的 Content-Type 必须随您上传的图像类型而变化(image/jpeg 或 image/png)。您可以将内容类型设置为application/octet-stream以涵盖所有基础。
-----------------------51b62743876b1201aee47ff4b1910e49
Content-Disposition: form-data; name="image_data"; filename="/some/directory/image.jpg"
Content-Type: application/octet-stream
����
-----------------------51b62743876b1201aee47ff4b1910e49--
以上两个例子都会上传一张图片。
-- 'Image binary data' 可能会产生误导,因为我的每次搜索都表明图像二进制是通过使用 base64_encode 函数获得的。在我的实验中,base64_encoding 没有做任何事情。您只需要使用 file_get_contents.
打开文件
-- 在您的 cURL 请求中,必须将 header 的 Content-Type 设置为 multipart/form-data 并且具有与请求相同的边界。示例如下:
curl_setopt($curl, CURLOPT_HTTPHEADER, array('Authorization: Bearer ' . $personalAccessToken, 'Content-Type: multipart/form-data; boundary=' . $boundary ));
所以这增加了另一种解决方案。
Troy 使用@ 的解决方案已被弃用,我无法让它工作。 Byron 的解决方案适用于 CURLOPT_POST before CURLOPT_POSTFIELDS(请参阅 Mavooks 在 https://www.php.net/manual/en/function.curl-setopt.php 的评论)并从 header。这是因为如果 CURLOPTS_POSTFIELDS 是一个数组并且手动包含它似乎会覆盖它,但它会自动多部分,但它会丢失边界。
$square_url = 'https://connect.squareup.com/v1/me/items/' . $square_item_id . '/image';
$cfile = new CURLFile($image_path_on_server, 'image/png', 'image_data');
$image_data = array('image_data' => $cfile);
$curl = curl_init();
curl_setopt($curl, CURLOPT_HTTPHEADER, array(
'Authorization: Bearer ' . $access_token,
'Accept: application/json'
));
curl_setopt($curl, CURLOPT_POST, TRUE);
curl_setopt($curl, CURLOPT_POSTFIELDS, $image_data);
curl_setopt($curl, CURLOPT_URL, $square_url);
curl_setopt($curl, CURLOPT_SAFE_UPLOAD, TRUE);
curl_setopt($curl, CURLOPT_BINARYTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, FALSE);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, FALSE);
curl_setopt($curl, CURLINFO_HEADER_OUT, TRUE);
curl_setopt($curl, CURLOPT_VERBOSE, TRUE);
$json = curl_exec($curl);
curl_close($curl);
我查看了 Whosebug 上关于此问题的旧问题。 但是我没有找到 php 集成的任何示例。
这是我执行此操作的代码示例,但它失败了
$url = 'https://connect.squareup.com/v1/me/items/9999999/image';
$auth_bearer = 'Authorization: Bearer ' . $this->accessToken;
$image_data = base64_encode(file_get_contents('image.jpeg'));
$header = array(
$auth_bearer,
'Accept: application/json',
'Content-Type: multipart/form-data; boundary=BOUNDARY',
);
$ch = curl_init($url);
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
curl_setopt($ch, CURLOPT_POSTFIELDS, 'files=' . $image_data);
$head = curl_exec($ch);
curl_close($ch);
$response = json_decode($head);
echo "<pre>";
print_r($response);
echo "</pre>";
什么也没发生...有什么帮助吗?
谢谢
您需要 post 原始图像数据(非 base64 编码)与文件 object 的适当多部分 header。这是一个工作示例(替换 ACCESS_TOKEN
、ITEM_ID
和 IMAGE_FILE
)。
<?php
function uploadItemImage($url, $access_token, $image_file) {
$headers = ["Authorization: Bearer $access_token"];
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, ['image_data' => "@$image_file"]);
curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$data = curl_exec($ch);
$return_status = curl_getinfo($ch, CURLINFO_HTTP_CODE);
print "POST to $url with status $return_status\n";
curl_close($ch);
return $data ? json_decode($data) : false;
}
print_r(
uploadItemImage(
'https://connect.squareup.com/v1/me/items/ITEM_ID/image',
'ACCESS_TOKEN',
'IMAGE_FILE.jpg'
)
);
?>
这是我的 PHP 上传 PNG 图像的实现。有时不同的代码视图会有所帮助。
如@Troy 所述,图像要包含的重要字段是 'Content-Type: multipart/form-data'。我上传到 Square 的所有其他内容都使用 'Content-Type: application/json'.
$square_url = 'https://connect.squareup.com/v1/me/items/' . $square_item_id . '/image';
$cfile = new CURLFile($image_path_on_server, 'image/png', 'image_data');
$image_data = array('image_data' => $cfile);
$curl = curl_init();
curl_setopt($curl, CURLOPT_HTTPHEADER, array(
'Authorization: Bearer ' . $access_token,
'Content-Type: multipart/form-data',
'Accept: application/json'
));
curl_setopt($curl, CURLOPT_POSTFIELDS, $image_data);
curl_setopt($curl, CURLOPT_URL, $square_url);
curl_setopt($curl, CURLOPT_POST, TRUE);
curl_setopt($curl, CURLOPT_SAFE_UPLOAD, TRUE);
curl_setopt($curl, CURLOPT_BINARYTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, FALSE);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, FALSE);
curl_setopt($curl, CURLINFO_HEADER_OUT, TRUE);
curl_setopt($curl, CURLOPT_VERBOSE, TRUE);
$json = curl_exec($curl);
curl_close($curl);
严格来说 Square API 文档,他们的方法可以在记住一些事情的情况下实现。
-- 您的请求必须包含在边界内并包含内容配置、名称、文件名、内容类型,如下例所示。
--BOUNDARY
Content-Disposition: form-data; name="image_data"; filename="MyImage.png"
Content-Type: image/png
{BLANK LINE IS REQUIRED}
IMAGE BINARY DATA GOES HERE
--BOUNDARY--
本质上,请求的格式必须与示例中指定的格式完全相同。这包括 'boundary'、换行符、必要的 headers、headers 之间的空行(出于某种原因,如果该行不存在则没有任何作用),以及实际图像二进制数据。注意:边界可以是您选择的任何字符串,但必须始终如一地使用。在代码中,这看起来像这样:
$boundary = "---------------------" . md5(mt_rand() . microtime());
$imageToUpload = "--{$boundary}" . "\r\n" .
"Content-Disposition: form-data; name=\"image_data\"; filename=\"" . $full_path_to_image_file . "\"" . "\r\n" .
"Content-Type: image/jpeg" . "\r\n" .
"\r\n" . // <- empty line is required
(file_get_contents($full_path_to_image_file)) . "\r\n" .
"--{$boundary}--";
以上将产生如下所示的请求:
-----------------------51b62743876b1201aee47ff4b1910e49
Content-Disposition: form-data; name="image_data"; filename="/some/directory/image.jpg"
Content-Type: image/jpeg
����
-----------------------51b62743876b1201aee47ff4b1910e49--
-- 从技术上讲,请求中的 Content-Type 必须随您上传的图像类型而变化(image/jpeg 或 image/png)。您可以将内容类型设置为application/octet-stream以涵盖所有基础。
-----------------------51b62743876b1201aee47ff4b1910e49
Content-Disposition: form-data; name="image_data"; filename="/some/directory/image.jpg"
Content-Type: application/octet-stream
����
-----------------------51b62743876b1201aee47ff4b1910e49--
以上两个例子都会上传一张图片。
-- 'Image binary data' 可能会产生误导,因为我的每次搜索都表明图像二进制是通过使用 base64_encode 函数获得的。在我的实验中,base64_encoding 没有做任何事情。您只需要使用 file_get_contents.
打开文件-- 在您的 cURL 请求中,必须将 header 的 Content-Type 设置为 multipart/form-data 并且具有与请求相同的边界。示例如下:
curl_setopt($curl, CURLOPT_HTTPHEADER, array('Authorization: Bearer ' . $personalAccessToken, 'Content-Type: multipart/form-data; boundary=' . $boundary ));
所以这增加了另一种解决方案。
Troy 使用@ 的解决方案已被弃用,我无法让它工作。 Byron 的解决方案适用于 CURLOPT_POST before CURLOPT_POSTFIELDS(请参阅 Mavooks 在 https://www.php.net/manual/en/function.curl-setopt.php 的评论)并从 header。这是因为如果 CURLOPTS_POSTFIELDS 是一个数组并且手动包含它似乎会覆盖它,但它会自动多部分,但它会丢失边界。
$square_url = 'https://connect.squareup.com/v1/me/items/' . $square_item_id . '/image';
$cfile = new CURLFile($image_path_on_server, 'image/png', 'image_data');
$image_data = array('image_data' => $cfile);
$curl = curl_init();
curl_setopt($curl, CURLOPT_HTTPHEADER, array(
'Authorization: Bearer ' . $access_token,
'Accept: application/json'
));
curl_setopt($curl, CURLOPT_POST, TRUE);
curl_setopt($curl, CURLOPT_POSTFIELDS, $image_data);
curl_setopt($curl, CURLOPT_URL, $square_url);
curl_setopt($curl, CURLOPT_SAFE_UPLOAD, TRUE);
curl_setopt($curl, CURLOPT_BINARYTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, TRUE);
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, FALSE);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, FALSE);
curl_setopt($curl, CURLINFO_HEADER_OUT, TRUE);
curl_setopt($curl, CURLOPT_VERBOSE, TRUE);
$json = curl_exec($curl);
curl_close($curl);