Битрикс: два способа отправить файл
В битриксе с некоторых пор есть встроенный функционал для работы HTTP запросами. Т.е. не обязательно напрямую дёргать curl или привлекать какой-нибудь Guzzle. Плюс это или минус - оставлю решать каждому самостоятельно. Тут покажу два варианта, как можно отправить файл встроенным битриксовым методом. Это нужно, например, при интеграции с каким-то API. Примеров не нашлось ни в официальной документации, ни в полезном разжёвывании.
Вариант в теле запроса через send()
Тут надо обратить внимание на заголовок: тип "multipart/form-data"; наличие вложения в виде файла "Content-Disposition". Сам файл отправляем в теле запроса через вызов содержимого файла $file->getContents().
$result = [];
// Проверяем существование файла на сервере
$file = new \Bitrix\Main\IO\File(
\Bitrix\Main\Application::getDocumentRoot() . '/upload/file.zip'
);
if ($file->isExists()) {
$httpClient = new HttpClient(
[
'redirect' => true, // true, если нужно выполнять редиректы
'redirectMax' => 3, // Максимальное количество редиректов
'waitResponse' => true, // true - ждать ответа, false - отключаться после запроса
'socketTimeout' => 30, // Таймаут соединения, сек
'streamTimeout' => 60, // Таймаут чтения ответа, сек, 0 - без таймаута
'version' => HttpClient::HTTP_1_1, // версия HTTP (HttpClient::HTTP_1_0 или HttpClient::HTTP_1_1)
'proxyHost' => '', // адрес
'proxyPort' => '', // порт
'proxyUser' => '', // имя
'proxyPassword' => '', // пароль
'compress' => false, // true - принимать gzip (Accept-Encoding: gzip)
'charset' => '', // Кодировка тела для POST и PUT
'disableSslVerification' => true // true - отключить проверку ssl
]
);
// Добавляем заголовки запроса
// Тут есть токен, который часто требуется в API:
// где-то в коде надо получить токен, тут просто считаем, что токен есть
$arHeader = [
'Content-Type' => 'multipart/form-data',
'Authorization' => 'Token ' . $obSomeClass->getToken(),
'Content-Disposition' => 'attachment; filename=' . $file->getName()
];
foreach ($arHeader as $name => $value) {
$httpClient->setHeader($name, $value, true);
}
// Отправляем запрос
$httpClient->query(
'POST',
'https://my-service.com/api/get-file/',
$file->getContents()
);
if (200 === intval($httpClient->getStatus())) {
$strResponse = $httpClient->getResult();
if (!empty($strResponse)) {
try {
$arResponse = \Bitrix\Main\Web\Json::decode(
$strResponse
);
} catch (\Exception $exception) {
echo 'Не удалось сформировать JSON: ' . $exception->getMessage();
}
if (!empty($arResponse)) {
$result = $arResponse;
}
}
}
}
print_r($result);
В программе Postman этот вид запроса настраивается так:Вариант как одно из полей запроса методом post()
Тут заголовки остаются такие же, как и в предыдущем примере. А вот тело запроса формируется по-другому. В этом примере файл отправляется в одном из полей ("zip_archive"), сам файл считываем функцией fopen(). И метод битриксового API тут нужен именно post(), а не query(), как было в предыдущем примере.
$result = [];
// Проверяем существование файла на сервере
$filePath = \Bitrix\Main\Application::getDocumentRoot() . '/upload/file.zip';
$file = new \Bitrix\Main\IO\File($filePath);
if ($file->isExists()) {
$httpClient = new HttpClient(
[
'redirect' => true, // true, если нужно выполнять редиректы
'redirectMax' => 3, // Максимальное количество редиректов
'waitResponse' => true, // true - ждать ответа, false - отключаться после запроса
'socketTimeout' => 30, // Таймаут соединения, сек
'streamTimeout' => 60, // Таймаут чтения ответа, сек, 0 - без таймаута
'version' => HttpClient::HTTP_1_1, // версия HTTP (HttpClient::HTTP_1_0 или HttpClient::HTTP_1_1)
'proxyHost' => '', // адрес
'proxyPort' => '', // порт
'proxyUser' => '', // имя
'proxyPassword' => '', // пароль
'compress' => false, // true - принимать gzip (Accept-Encoding: gzip)
'charset' => '', // Кодировка тела для POST и PUT
'disableSslVerification' => true // true - отключить проверку ssl
]
);
// Добавляем заголовки запроса
// Тут есть токен, который часто требуется в API:
// где-то в коде надо получить токен, тут просто считаем, что токен есть
$arHeader = [
'Content-Type' => 'multipart/form-data',
'Authorization' => 'Token ' . $obSomeClass->getToken(),
'Content-Disposition' => 'attachment; filename=' . $file->getName()
];
foreach ($arHeader as $name => $value) {
$httpClient->setHeader($name, $value, true);
}
// Отправляем запрос
$httpClient->post(
'POST',
'https://my-service.com/api/get-file/',
['zip_archive' => fopen($filePath, 'rb')]
);
if (200 === intval($httpClient->getStatus())) {
$strResponse = $httpClient->getResult();
if (!empty($strResponse)) {
try {
$arResponse = \Bitrix\Main\Web\Json::decode(
$strResponse
);
} catch (\Exception $exception) {
echo 'Не удалось сформировать JSON: ' . $exception->getMessage();
}
if (!empty($arResponse)) {
$result = $arResponse;
}
}
}
}
print_r($result);
В Postman это выглядит так:
Комментарии
Отправить комментарий