WordPress.org

Make WordPress Core

Opened 5 years ago

Closed 5 years ago

Last modified 5 years ago

#37364 closed defect (bug) (invalid)

PHP Warning caused by \WP_Http::request, when body contains a JSON string

Reported by: sciamannikoo Owned by:
Milestone: Priority: normal
Severity: normal Version: 4.6
Component: HTTP API Keywords:
Focuses: Cc:

Description

This is happening with WP 4.6-beta3-38061.

Scenario:

A plugin needs to send requests to an external service, which is expecting to receive a JSON string in the request body.

<?php
$url = 'http://domain.tld/jobs.json?project_id=1234&accesskey=e2e65819764d93d94624b9e58ea931ea&state=any';

$context = array (
  'method' => 'GET',
  'body' => '{"project_id":1234,"accesskey":"e2e65819764d93d94624b9e58ea931ea","state":"any","api_version":1.1}',
  'sslverify' => false,
  'timeout' => 60,
  'headers' => 'Content-type: application/json',
);

Calling \WP_Http::request( $url, $context ) throws this warning:

PHP Warning:  http_build_query(): Parameter 1 expected to be Array or Object.  Incorrect value given in /.../wp-includes/Requests/Transport/cURL.php on line 505

The point is that \WP_Http::request set the "body" element (which in this case, again, is a JSON string) in $data.

Then \Requests::request (which expect $data to be either an array or null) is called.

However, \Requests_Transport_cURL::request (which is called by \Requests::request) expect $data to be either a string or an array.

Is worth noting that this issue does not happen with WP 4.5 and earlier versions.

Please let me know if you need more details.

Change History (8)

#1 @johnbillion
5 years ago

  • Milestone changed from Awaiting Review to 4.6

#2 @sciamannikoo
5 years ago

  • Summary changed from Exception thrown by \WP_Http::request when body contains a JSON string to PHP Warning caused by \WP_Http::request, when body contains a JSON string

#3 @ocean90
5 years ago

This seems to depend on the data_format option which is set here and used in cURL here.

@sciamannikoo: I'm actually not sure why body is set in your GET example, shouldn't this be a POST request?

@rmccue: Any thoughts on the different types? Looks like https://github.com/rmccue/Requests/blob/ae16e797f7dcc4439e540939d5bb31f920e5e87f/library/Requests.php#L557 supports a string too.

#4 @sciamannikoo
5 years ago

@ocean90 you nailed it!

This comes from some legacy code.

Apparently, the developer was too lazy to remove the "body" when the request type was using the GET method.

Removing it seems to have fixed the issue.

#5 follow-up: @rmccue
5 years ago

  • Milestone 4.6 deleted
  • Resolution set to invalid
  • Status changed from new to closed

GET doesn't support request bodies; technically speaking, clients, proxies, and servers are free to pretend it doesn't exist. It'd be nice if Requests didn't trigger a warning, but the usage is incorrect here.

We should probably sanity-check the value in Requests. Closing the ticket out here as it's not a WP thing, but rather something inside Requests itself.

#6 @ocean90
5 years ago

#37618 was marked as a duplicate.

#7 in reply to: ↑ 5 @ocean90
5 years ago

Replying to rmccue:

[…] It'd be nice if Requests didn't trigger a warning, but the usage is incorrect here.

We should probably sanity-check the value in Requests. Closing the ticket out here as it's not a WP thing, but rather something inside Requests itself.

See https://github.com/rmccue/Requests/issues/228.

#8 @johnbillion
5 years ago

#39043 was marked as a duplicate.

Note: See TracTickets for help on using tickets.