Introduction

With the addition of Guzzle HTTP client library added to replace drupal_http_request().

An interesting issue has came up in regards to multidimensional associative arrays being passed to Guzzle as the query parameters.

In Drupal 7

$url = 'http://example.com';

$query = array(
  'user' => array(
    'name' => 'Bob Smith',
    'age'=>47,
  ),
);

drupal_http_request($url, array('query' => $query));

In Drupal 8

$url = 'http://example.com';

$query = array(
  'user' => array(
    'name' => 'Bob Smith',
    'age'=>47,
  ),
);

$client = \Drupal::httpClient();
$request = $client->get($url, array(), $query);
$response = json_decode($request->getBody(), true);

The above will fail.

Solution

The only work around I have is appending the parsed parameters onto the end of the url.

$url = 'http://example.com';

$query = array(
  'user' => array(
    'name' => 'Bob Smith',
    'age'=>47,
  ),
);

$query_str = UrlHelper::buildQuery($query);

$url = $url . '?' . $query_str;

$client = \Drupal::httpClient();
$request = $client->get($url);
$response = json_decode($request->getBody(), true);

The above we are using the UrlHelper that has replaced drupal_http_build_query: URL related functions got moved to a new UrlHelper component. Many of those url helpers were used in drupal_http_request().

https://github.com/guzzle/guzzle/issues/90 > https://github.com/ioseb/uri-template/issues/2

Issue

The use of drupal_http_request is used a lot of places in drupal 7. Views using this functionality a lot for example with multiple taxonomy terms filtering a view. Work around is ugly so documentation is needed.

Hopefully this helps someone, somewhere, some day.

Comments

dobe created an issue. See original summary.

dawehner’s picture

What about using something like this?

$url = new \GuzzleHttp\Psr7\Uri('http://example.com');
$url = \GuzzleHttp\Psr7\Uri::withQueryValue($url, 'user' => ['Bob Smith', 47]);

$client = \Drupal::httpClient();
$request = $client->get($url, array(), $query);
$response = json_decode($request->getBody(), true);
dobe’s picture

I will try this, thank you dawehner!

dawehner’s picture

@dobe
Is this issue fixed with my comment?

dobe’s picture

Well kind of. I modified what you provided

What I came up with is this... But it is less than ideal. As it would require to loop through everything to apply each parameter.

$url = \GuzzleHttp\Psr7\Uri::withQueryValue($url, 'user[name]', 'Bob Smith');
$url = \GuzzleHttp\Psr7\Uri::withQueryValue($url, 'user[age]', 47);

At that point just doing a http_build_query works out better.

Any other suggestions are much appreciated!

dawehner’s picture

Maybe you could add a new issue in the guzzle queue and ask about it. They maybe are able to help you better.

dobe’s picture

Status: Active » Closed (works as designed)

Its all good @dawehner thank you for helping me out! This is what guzzle queue said to me:

Maybe this(or similar) behaviour is implemented in another languages, these are not defined by IETF RFCs(do not confuse with PHP RFCs). URI Template extension implements IETF RFC-6570 that also depends on IETF RFC-3986. I do believe implementation should conform to these specs despite the fact that it is implemented for PHP.

http_build_query() I guess is the way to do it. Just seems weird to me.

dobe’s picture

Component: routing system » documentation
Category: Bug report » Task
Status: Closed (works as designed) » Active

I am going to reopen as I feel this should be something documented in the D8 Api docs.

dawehner’s picture

@dobe
That is a great idea. Let's document it.

dobe’s picture

Issue summary: View changes
jhodgdon’s picture

Status: Active » Postponed (maintainer needs more info)

Hm, where would we document this, and what would we document? We do not document in the Drupal 8 API docs how it is different from Drupal 7... we just document what Drupal 8 does. If something has changed between 7 and 8, we would make a change record to document it... what needs to be done?

dobe’s picture

Status: Postponed (maintainer needs more info) » Closed (won't fix)

Yeah I am not sure much more needs to be done here. I commented on the change record pages with links to this page. Not sure what else really can be done. We could probably close this issue now.