user1704524
user1704524

Reputation: 458

Guzzle POST request always returns 400 Bad Request

I have been trying to make a simple POST request to an endpoint with a payload using Guzzle but I always get 400 Bad Request returned.

I can make the same request in Postman and it works. Also, If I make the request using cURL it works.

Can anyone tell from my code what I am doing wrong?

Here's the original cURL request:

curl "https://endpoint.com/" \
  -H "Authorization: ApiKey pp_test_*********" \
  --data '{
    "shipping_address": {
      "recipient_name": "Deon Botha",
      "address_line_1": "Eastcastle House",
    "address_line_2": "27-28 Eastcastle Street",
    "city": "London",
    "county_state": "Greater London",
    "postcode": "W1W 8DH",
    "country_code": "GBR"
    },
    "customer_email": "email£example.com",
    "customer_phone": "123455677",
    "customer_payment": {
      "amount": 29.99,
      "currency": "USD"
    },
    "jobs": [{
      "assets": ["http://psps.s3.amazonaws.com/sdk_static/1.jpg"],
    "template_id": "i6_case"
    }, {
      "assets": ["http://psps.s3.amazonaws.com/sdk_static/2.jpg"],
    "template_id": "a1_poster"
    }]
  }' 

And the Postman PHPHttp Request which works too.

<?php

$request = new HttpRequest();
$request->setUrl('https://endpoint.com/');
$request->setMethod(HTTP_METH_POST);

$request->setHeaders(array(
  'cache-control' => 'no-cache',
  'Connection' => 'keep-alive',
  'Content-Length' => '678',
  'Accept-Encoding' => 'gzip, deflate',
  'Host' => 'api.kite.ly',
  'Cache-Control' => 'no-cache',
  'Accept' => '*/*',
  'User-Agent' => 'PostmanRuntime/7.19.0',
  'Content-Type' => 'text/plain',
  'Authorization' => 'ApiKey pk_test_*******'
));

$request->setBody(' {
    "shipping_address": {
      "recipient_name": "Deon Botha",
      "address_line_1": "Eastcastle House",
    "address_line_2": "27-28 Eastcastle Street",
    "city": "London",
    "county_state": "Greater London",
    "postcode": "W1W 8DH",
    "country_code": "GBR"
    },
    "customer_email": "[email protected]",
    "customer_phone": "12345667",
    "customer_payment": {
      "amount": 29.99,
      "currency": "USD"
    },
    "jobs": [{
      "assets": ["http://psps.s3.amazonaws.com/sdk_static/1.jpg"],
    "template_id": "i6_case"
    }, {
      "assets": ["http://psps.s3.amazonaws.com/sdk_static/2.jpg"],
    "template_id": "a1_poster"
    }]
  }');

try {
  $response = $request->send();

  echo $response->getBody();
} catch (HttpException $ex) {
  echo $ex;
} 

But when I try to send make the same request with Guzzle it fails with 400 Bad Request and I can't understand why.


        $data = [
            "shipping_address" => [
                "recipient_name" => "Deon Botha",
                "address_line_1" => "Eastcastle House",
                "address_line_2" => "27-28 Eastcastle Street",
                "city" => "London",
                "county_state" => "Greater London",
                "postcode" => "W1W 8DH",
                "country_code" => "GBR"
            ],
            "customer_email" => "[email protected]",
            "customer_phone" => "+44 (0)784297 1234",
            "customer_payment" => [
                "amount" => 29.99,
                "currency" => "USD"
            ],
            "jobs" =>
                [
                    "assets" => ["http://psps.s3.amazonaws.com/sdk_static/1.jpg"],
                    "template_id" => "i6_case"
                ]

        ];

       $options = json_encode($data);

        $response = $client->request('POST', config('services.endpoint.com'),
            ['headers' => ["Authorization" => config('services.endpoint.com.public_key'),
              'Content-Type' => "application/json"], $options]);

If anyone can help me to debug this I'd be really grateful.

Upvotes: 2

Views: 1228

Answers (2)

Jason
Jason

Reputation: 3030

If you're using Guzzle 6 (and you probably should be), you're actually constructing in a more complex way than you need to, such that the endpoint is not receiving the expected JSON. Try this instead:

$client = new Client([
     'base_uri' => 'https://my.endpoint.com/api',
     'headers' => [
          'Accept' => 'application/json',
          ...other headers...
     ]
]);

$data = [...your big slab of data...];

$response = $client->post('/kitely/path', ['json' => $data]);

// a string containing the results, which will depend on the endpoint
// the Accept header says we will accept json if it is available
// then we can use json_decode on the result
$result = $response->getBody()->getContents();  

Upvotes: 1

I. Antonov
I. Antonov

Reputation: 707

I'm using Unirest to make any sort of HTTP requests. I tried using Guzzle, but was facing the same issue as you are.

So what I did was install Unirest in my project, all the process are given in details in their documentation. This works perfectly fine for me.

Upvotes: 0

Related Questions