您可以使用Guzzle的Pool:batch()
方法并行执行http请求。它允许您在第三个参数中使用options
key为请求设置默认选项。
但是如果我需要为池中的不同请求提供不同的选项该怎么办?我希望使用池执行GET请求,并将每个响应流式传输到磁盘上的不同文件。有一个sink
选项。但是如何将该选项的不同值应用于请求呢?
Rastor的例子几乎是正确的,但是如果你想提供"options"到Pool()
构造函数
他忽略了这里提到的池选项数组的关键实现。
Guzzle文档说:
当迭代器生成函数时,提供该函数"request_options"数组,该数组应合并在任何该函数必须返回一个可等待对象承诺。
另外,如果你看一下我链接到的注释下面的Pool()
代码,你可以看到Guzzle's Pool调用了可调用对象,并给了它Pool的"选项";
请求选项>池选项>客户违约。
如果你不应用Pool()
对象的选项数组到你的请求对象,你将结束与严重的错误,如如果你试图使new Pool($client, $requests(100), ['options'=>['timeout'=>30.0]]);
。如果没有我更正的代码,您的池选项根本不会被应用,因为您不支持正确合并池选项,因此最终会丢弃它们。
Pool()
选项:
<?php
$client = new 'GuzzleHttp'Client();
$requests = function ($total) use ($client) {
for ($i = 0; $i < $total; $i++) {
$url = "domain.com/picture/{$i}.jpg";
$filepath = "/tmp/{$i}.jpg";
yield function($poolOpts) use ($client, $url, $filepath) {
/** Apply options as follows:
* Client() defaults are given the lowest priority
* (they're used for any values you don't specify on
* the request or the pool). The Pool() "options"
* override the Client defaults. And the per-request
* options ($reqOpts) override everything (both the
* Pool and the Client defaults).
* In short: Per-Request > Pool Defaults > Client Defaults.
*/
$reqOpts = [
'sink' => $filepath
];
if (is_array($poolOpts) && count($poolOpts) > 0) {
$reqOpts = array_merge($poolOpts, $reqOpts); // req > pool
}
return $client->getAsync($url, $reqOpts);
};
}
};
$pool = new Pool($client, $requests(100));
但是请注意,如果您知道永远不会向new Pool()
构造函数添加任何选项,则不必支持Pool()
选项。在这种情况下,您可以查看官方Guzzle文档中的示例。
官方示例如下:
// Using a closure that will return a promise once the pool calls the closure.
$client = new Client();
$requests = function ($total) use ($client) {
$uri = '127.0.0.1:8126/guzzle-server/perf';
for ($i = 0; $i < $total; $i++) {
yield function() use ($client, $uri) {
return $client->getAsync($uri);
};
}
};
$pool = new Pool($client, $requests(100));
For guzzle 6
$client = new 'GuzzleHttp'Client();
$requests = function ($total) use ($client) {
for ($i = 0; $i < $total; $i++) {
$url = "http://domain.com/picture/{$i}.jpg";
$filepath = "/tmp/{$i}.jpg";
yield function() use ($client, $url, $filepath) {
return $client->getAsync($url, [
'sink' => $filepath
]);
};
}
};
$pool = new Pool($client, $requests(100));
您可以在请求中单独指定所需的$options
。如果将它传递给客户端,它将仅适用于所有请求。以下是节选自Guzzle 6 doc:
在创建客户端时,可以将Headers作为默认选项添加。当头文件被用作默认选项,它们只在正在创建的请求尚未包含特定的标头。这包括在send()和sendAsync()方法和客户端创建的请求(例如,
看到http://guzzle.readthedocs.org/en/latest/request-options.html?highlight=default标题