Заголовки запроса не отправляются с Zend Http

Я делаю следующий запрос, используя Zend \ Http \ Request и Zend \ Http \ Client

        //Creating request and client objects
$request = new Request();
$client = new Client();

//Preparing Request Object
$request->setMethod('POST');
$request->setUri('https://my.api.address.com/apiendpointurl1234');
$request->getHeaders()->addHeaders(array(
'cache-control' => 'no-cache',
'content-type' => 'application/json',
'client_secret' => 'asdfasdfasdfasdfasdf',
'client_id' => 'asdfasdfasdfasdfasdf',
'accept' => 'application/json',
'authorization' => 'Basic MTIzNDoxMjM0',
));
$request->getPost()->set(json_encode(array(
'student_id' => '123456',
'short_description' => 'this is short description',
'description' => 'this is detailed description of the question',
)));

//Sending Request
$response = $client->send($request);

var_dump( $response->getBody() );

Однако ответ приходит с этой ошибкой:

«ошибка»: «заголовки: client_id обязательный»

Когда я высовываю API через Postman, он работает нормально. Но когда я вызываю его из приложения PHP, оказывается, что заголовки отправляются неправильно, что приводит к вышеуказанной ошибке. Кто-нибудь знает, почему заголовки не отправляются?

4

Решение

попробуй без метода addHeaders

// Setting multiple headers, overwriting any previous value
$client->setHeaders(array(
'Host' => 'www.example.com',
'Accept-encoding' => 'gzip,deflate',
'X-Powered-By' => 'Zend Framework'));

и, возможно, у вас есть некоторые путать с объектами клиента и запроса.

   $client = new Zend_Http_Client('http://example.org');
$client->setHeaders(array(
'Host' => 'www.example.com',
'Accept-encoding' => 'gzip,deflate',
'X-Powered-By' => 'Zend Framework'));
$response = $client->request();

и вы можете проверить свой запрос, например, в firebug и проверить, какие заголовки отправляются на сервер

1

Другие решения

Если вы хотите использовать Request объект, у вас есть использование setRequest а также dispatch методы:

use Zend\Http\Client;
use Zend\Http\Request;

$request = new Request();
$request->setUri('https://my.api.address.com/apiendpointurl1234');

// Performing a POST request
$request->setMethod(Request::METHOD_POST);
$request->getHeaders()->addHeaders(array(
'cache-control' => 'no-cache',
'content-type' => 'application/json',
'client_secret' => 'asdfasdfasdfasdfasdf',
'client_id' => 'asdfasdfasdfasdfasdf',
'accept' => 'application/json',
'authorization' => 'Basic MTIzNDoxMjM0',
));

$client = new Client();

$client->setRequest($request);
$response = $client->dispatch();
1

Могу поспорить, что вам нужно сохранить ссылку на объект Headers в переменной сразу после вас getHeadersманипулировать этим объектом, а затем использовать setHeaders обновить заголовки объекта запроса.

$headers = $request->getHeaders();
$headers->addHeaders([ ... ... ]);
$request->setHeaders($headers);
1

Если я правильно помню, это было давно, так как я использовал Zend Framework для запросов, но getHeaders Метод возвращает объект Headers, поэтому вам нужно использовать и установить.

Так твой код

 $request->getHeaders()->addHeaders(array(
'cache-control' => 'no-cache',
'content-type' => 'application/json',
'client_secret' => 'asdfasdfasdfasdfasdf',
'client_id' => 'asdfasdfasdfasdfasdf',
'accept' => 'application/json',
'authorization' => 'Basic MTIzNDoxMjM0',
));

Нужно будет стать

 $headers = $request->getHeaders();
$headers->addHeaders(array(
'cache-control' => 'no-cache',
'content-type' => 'application/json',
'client_secret' => 'asdfasdfasdfasdfasdf',
'client_id' => 'asdfasdfasdfasdfasdf',
'accept' => 'application/json',
'authorization' => 'Basic MTIzNDoxMjM0',
));
$request->setHeaders($headers);

Как сказано в одном из других ответов:

вам нужно будет установить URI и метод как Post, прежде чем вы сделаете это, так как вам понадобятся другие заголовки

$request->setUri('https://my.api.address.com/apiendpointurl1234');

// Performing a POST request
$request->setMethod(Request::METHOD_POST);

И, наконец, вам нужно будет установить свои данные поста, прежде чем вы сделаете это, так как это повлияет на ваши заголовки, так как заголовок Content-Length должен быть установлен, прежде чем вы начнете связываться с ними

$request->setContent(json_encode(array(
'student_id' => '123456',
'short_description' => 'this is short description',
'description' => 'this is detailed description of the question',
)));

Так что все вместе сценарий должен быть

//Creating request and client objects
$request = new Request();
$client = new Client();
$request->setUri('https://my.api.address.com/apiendpointurl1234');

// Performing a POST request
$request->setMethod(Request::METHOD_POST);
$client->setOptions(['strictredirects' => true]);

$request->setContent(json_encode(array(
'student_id' => '123456',
'short_description' => 'this is short description',
'description' => 'this is detailed description of the question',
)));
$headers = $request->getHeaders();
$headers->addHeaders(array(
'cache-control' => 'no-cache',
'content-type' => 'application/json',
'client_secret' => 'asdfasdfasdfasdfasdf',
'client_id' => 'asdfasdfasdfasdfasdf',
'accept' => 'application/json',
'authorization' => 'Basic MTIzNDoxMjM0',
));
$request->setHeaders($headers);
1

Вот что сработало для меня:

//Creating request and client objects
$request = new Request();
$client = new Client();

//Preparing Request Object
$request->setMethod('POST');
$request->setUri('https://my.api.address.com/apiendpointurl1234');
$request->getHeaders()->addHeaders(array(
'cache-control' => 'no-cache',
'content-type' => 'application/json',
'client_secret' => 'asdfasdfasdfasdfasdf',
'client_id' => 'asdfasdfasdfasdfasdf',
'accept' => 'application/json',
'authorization' => 'Basic MTIzNDoxMjM0'
));

$client->setOptions(['strictredirects' => true]);

$request->setContent(json_encode(array(
'student_id' => '123456',
'short_description' => 'this is short description',
'description' => 'this is detailed description of the question',
)));

//Sending Request
$response = $client->send($request);

echo ($response->getBody());

Я предполагаю, что существует перенаправление с вашего API на другой URL, и заголовки сбрасываются. Вы можете видеть это в строке 943 Client.php, где

$this->resetParameters(false, false);

называется.
Этого не происходит в Postman, поскольку Postman повторно использует те же заголовки для перенаправления.

На самом деле, вы можете проверить это, добавив просто добавив

$client->setOptions(['strictredirects' => true]);

который должен позволить заголовкам быть сохраненными между перенаправлениями.

PS: я попробовал приведенный выше код с последней стабильной версией zend http, и он выдал мне несколько ошибок в строке «$ request-> getPost () -> set».
Во всяком случае, это не источник проблемы.

РЕДАКТИРОВАТЬ:
Мое второе предположение заключается в том, что имя заголовка «client_id» запрашивается с учетом регистра API, что вызывает ошибку, поскольку запрос отправляется Zend \ Http \ Client, он использует «Zend \ Http \ Client \ Adapter \ Socket», который делает первый символ каждого заголовка заглавным (строка 361). Таким образом, «Client_id» действительно отправлено.
Отредактируйте строку 361 в Zend \ Http \ Client \ Adapter \ Socket «:

 $v = ucfirst($k) . ": $v";

в

  $v = $k . ": $v";

и проверьте, получен ли заголовок.

1

Получается что Zend\Http\Request а также Zend\Http\Client библиотеки преобразуют подчеркивания в дефис (-) во время вызова. Тем не менее, cURL ведет себя немного по-другому. Тем не менее, если вы предоставите массив заголовков в формате значения ключа, вы не сможете выполнить вызов, так как cURL преобразует client-id в client-id, Однако, если вы предоставите стандартный массив значений только путем объединения заголовков, вызов будет успешным. Итак, вот мой код замены, который работал:

    // Get cURL resource
$curl = curl_init();
// Set some options - we are passing in a useragent too here
curl_setopt_array($curl, [
CURLOPT_RETURNTRANSFER => 1,
CURLOPT_URL => 'https://my.api.address.com/apiendpointurl1234',
CURLOPT_POST => 1,
CURLOPT_HTTPHEADER => [
'client_id: ' . 'asdfasdfasdfasdf',
'client_secret: ' . 'asdfasdfasdfasdfasdf',
'Authorization: ' . 'Basic MTIzNDoxMjM0',
'Content-Type: ' . 'application/json',
],
CURLOPT_POSTFIELDS => [
'student_id' => '111',
'short_description' => 'this is the short description',
'description' => 'this is the long description this is the long description this is the long description'
],
]);
// Send the request & save response to $resp
$response = curl_exec($curl);
var_dump("Service call id is: " . $response);
// Close request to clear up some resources
curl_close($curl);

Надеюсь, это поможет.

0
По вопросам рекламы [email protected]