Php 用Guzzle下载文件

Php 用Guzzle下载文件,php,guzzle,Php,Guzzle,我正试图用Guzzle检索文件附件。文件不能直接通过端点访问,但下载是通过端点启动并下载到我的浏览器中的。我可以用Guzzle检索这个文件吗 我成功登录到该站点,但保存到我的文件中的是该站点的html,而不是下载。当我使用rest客户端发出请求时,文件内容似乎已经通过了,但Guzzle却没有 $client = new GuzzleHttp\Client(); $cookieJar = new \GuzzleHttp\Cookie\CookieJar(); $response = $clien

我正试图用Guzzle检索文件附件。文件不能直接通过端点访问,但下载是通过端点启动并下载到我的浏览器中的。我可以用Guzzle检索这个文件吗

我成功登录到该站点,但保存到我的文件中的是该站点的html,而不是下载。当我使用rest客户端发出请求时,文件内容似乎已经通过了,但Guzzle却没有

$client = new GuzzleHttp\Client();
$cookieJar = new \GuzzleHttp\Cookie\CookieJar();

$response = $client->post('https://test.com/login', [
    'form_params' => [
        'username' => $username,
        'password' => $password,
        'action' => 'login'
    ],
    'cookies' => $cookieJar
]);

$resource = fopen(__DIR__.'/../../feeds/test.xls', 'w');
$stream = GuzzleHttp\Psr7\stream_for($resource);
$response = $client->request('GET', 'https://test.com/download', ['sink' => $stream]);


您应该发送
Content Disposition
头,以指定客户端应接收文件下载作为响应。根据GET HTTP
请求
,该请求将内容捕获到
$stream
资源中,最后您可以使用
stream\u GET\u contents
将这些内容输出到浏览器

<?php 

// your 3rd party end-point authentication

...

header('Content-Type: application/vnd.ms-excel');
header('Content-Disposition: attachment; filename="test.xls"'); 

$resource = fopen(__DIR__.'/../../feeds/test.xls', 'w');
$stream = GuzzleHttp\Psr7\stream_for($resource);
$response = $client->request('GET', 'https://test.com/download', ['sink' => $stream]);

echo stream_get_contents($stream);

您应该发送
内容处置
头,以指定客户端应接收文件下载作为响应。根据GET HTTP
请求
,该请求将内容捕获到
$stream
资源中,最后您可以使用
stream\u GET\u contents
将这些内容输出到浏览器

<?php 

// your 3rd party end-point authentication

...

header('Content-Type: application/vnd.ms-excel');
header('Content-Disposition: attachment; filename="test.xls"'); 

$resource = fopen(__DIR__.'/../../feeds/test.xls', 'w');
$stream = GuzzleHttp\Psr7\stream_for($resource);
$response = $client->request('GET', 'https://test.com/download', ['sink' => $stream]);

echo stream_get_contents($stream);

如果要先执行身份验证步骤,然后执行下载步骤,则需要确保在两个请求之间持久保存cookie。现在,您只需将
$cookieJar
变量传递给第一个变量

这样做的明确方式是将其添加到第二个请求的选项中:

['sink' => $stream, 'cookies' => $cookieJar]
但利用客户端构造函数本身中的选项可能更容易:

$client = new GuzzleHttp\Client(['cookies' => true);

这意味着每个请求(与该客户机一起)都将自动使用一个共享cookie jar,您不必担心将其分别传递到每个请求中。

如果您希望执行身份验证步骤,然后执行下载步骤,则需要确保cookie在两个请求中都保持不变。现在,您只需将
$cookieJar
变量传递给第一个变量

这样做的明确方式是将其添加到第二个请求的选项中:

['sink' => $stream, 'cookies' => $cookieJar]
但利用客户端构造函数本身中的选项可能更容易:

$client = new GuzzleHttp\Client(['cookies' => true);

这意味着每个请求(与该客户端一起)都将自动使用一个共享cookie罐,您不必担心将其分别传递到每个请求。

请添加一些解释,说明您的答案如何解决原始问题。@G.Spirov感谢您的回答!但这并不完全是我想要的。请添加一些关于您的答案如何解决原始问题的解释。@G.Spirov谢谢您的答案!这不是我想要的。你不需要把你的饼干罐传回到第二个请求中吗?我认为它不会在客户端自动共享,除非您在客户端构造函数中使用
['cookies'=>true]
。哇!非常感谢。就这样。完全有道理。把你的答案贴出来,我会把它标记正确。你不需要把你的饼干罐传回到第二个请求中吗?我认为它不会在客户端自动共享,除非您在客户端构造函数中使用
['cookies'=>true]
。哇!非常感谢。就这样。完全有道理。把你的答案贴出来,我会把它标对的