web-dev-qa-db-ja.com

Guzzle PHPでSENTデータの本体を取得するにはどうすればよいですか?

PHPサーバーにPOSTリクエストを送信するためにGuzzle(v6.1.1)を使用しています。問題なく動作します。ログにログ機能を追加しています何が送受信され、Guzzleがサーバーに送信したデータを取得する方法がわかりません。応答は問題なく取得できますが、送信済みデータを取得するにはどうすればよいですか(どのJSON文字列になります。)

これが私のコードの関連部分です:

$client = new GuzzleHttp\Client(['base_uri' => $serviceUrlPayments ]);
    try {
       $response = $client->request('POST', 'Charge', [
            'auth' => [$securenetId, $secureKey],
            'json' => [     "amount" => $amount,
                            "paymentVaultToken" => array(
                                    "customerId" => $customerId,
                                    "paymentMethodId" => $token,
                                    "publicKey" => $publicKey
                                    ),
                            "extendedInformation" => array(
                                    "typeOfGoods" => $typeOfGoods,
                                    "userDefinedFields" => $udfs,
                                    "notes" => $Notes
                                    ),
                            'developerApplication'=> $developerApplication 
            ]
    ]);

    } catch (ServerErrorResponseException $e) {
        echo (string) $e->getResponse()->getBody();
    }


    echo $response->getBody(); // THIS CORRECTLY SHOWS THE SERVER RESPONSE
    echo $client->getBody();           // This doesn't work
    echo $client->request->getBody();  // nor does this

任意の助けいただければ幸いです。私はリクエストで動作するgetBody()に似た関数のGuzzleソースコードを調べようとしましたが、私はPHP=エキスパートではないため、役立つものを思い付きませんでした。私もGoogleをよく検索しましたが、サーバーから応答を返すことについて話している人だけが見つかりました。

18
ruhnet

ミドルウェア を作成することで、この作業を行うことができます。

use GuzzleHttp\Client;
use GuzzleHttp\HandlerStack;
use GuzzleHttp\Middleware;
use Psr\Http\Message\RequestInterface;

$stack = HandlerStack::create();
// my middleware
$stack->Push(Middleware::mapRequest(function (RequestInterface $request) {
    $contentsRequest = (string) $request->getBody();
    //var_dump($contentsRequest);

    return $request;
}));

$client = new Client([
    'base_uri' => 'http://www.example.com/api/',
    'handler' => $stack
]);

$response = $client->request('POST', 'itemupdate', [
    'auth' => [$username, $password],
    'json' => [
        "key" => "value",
        "key2" => "value",
    ]
]);

ただし、これは応答を受信する前にトリガーされます。あなたはこのようなことをしたいかもしれません:

$stack->Push(function (callable $handler) {
    return function (RequestInterface $request, array $options) use ($handler) {
        return $handler($request, $options)->then(
            function ($response) use ($request) {
                // work here
                $contentsRequest = (string) $request->getBody();
                //var_dump($contentsRequest);
                return $response;
            }
        );
    };
});
18
Federkun

Guzzle 6.2の使用。

過去2日間、さまざまなAPIとのHTTPインタラクションを監査するメソッドを構築しようとしている間も、私はこれに取り組んできました。私の場合の解決策は、単にリクエストの本文を巻き戻すことでした。

リクエストのボディは実際には stream として実装されます。したがって、リクエストが送信されると、Guzzleはストリームから読み取ります。完全なストリームを読み取ると、ストリームの内部ポインタが最後に移動します。したがって、リクエストが行われた後でgetContents()を呼び出すと、内部ポインタはすでにストリームの最後にあり、何も返しません。

ソリューション?ポインタを先頭に巻き戻して、ストリームを再度読み取ります。

<?php
// ...
$body = $request->getBody();
echo $body->getContents(); // -->nothing

// Rewind the stream
$body->rewind();
echo $body->getContents(); // -->The request body :)
11
DJ Sipe

次のようにして、リクエストによって作成されたデータ文字列を再現できます。

_$data = array(
    "key" => "value",
    "key2" => "value",
); 

$response = $client->request('POST', 'itemupdate', [
    'auth' => [$username, $password],
    'json' => $data,
]);

// ...

echo json_encode($data);
_

これにより、データがJSON文字列として出力されます。

http://php.net/manual/fr/function.json-encode.php にあるドキュメント

[〜#〜]編集[〜#〜]

GuzzleにはRequestクラスとResponseクラス(およびその他多数)があります。
Requestには、他のすべてのメンバーと同様に、dataをプライベートとして含むオブジェクトを返すgetQuery()メソッドが事実上あります。
また、アクセスできません。

これが手動でエンコードする方が簡単な解決策だと思う理由です。 Guzzleによって何が行われるかを知りたい場合は、データを変換してリクエストで送信するCollectionクラスもあります。

1
chalasr