Set proxy in Guzzle
Asked Answered
J

7

17

I have a problem with set proxy in guzzle that a blank page was shown while with curl everything works perfect. The code that I used in guzzle and curl came below. What is wrong with this code: Guzzle:

use GuzzleHttp\Client;
use GuzzleHttp\Exception\RequestException;

require_once "vendor/autoload.php";

try {
  $client = new Client();
  $request = new \GuzzleHttp\Psr7\Request('GET', 'http://httpbin.org');
  $response = $client->send($request, [
      'timeout'  => 30,
      'curl'  => [
          'CURLOPT_PROXY' => '*.*.*.*',
          'CURLOPT_PROXYPORT' => *,
          'CURLOPT_PROXYUSERPWD' => '*:*',
      ],

  ]);
  echo '</pre>';
  echo($response->getBody());
  exit;
} catch (RequestException $e) {
  echo $e->getRequest();
  if ($e->hasResponse()) {
      echo $e->getResponse();
  }
}

And The code with CURL:

$url = 'http://httpbin.org';
$ch = curl_init($url);
curl_setopt($ch,CURLOPT_USERAGENT,'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.13) Gecko/20080311 Firefox/2.0.0.13');
curl_setopt($ch, CURLOPT_PROXY, '*.*.*.*');
curl_setopt($ch, CURLOPT_PROXYPORT, *);
curl_setopt($ch, CURLOPT_PROXYUSERPWD, '*:*');
curl_setopt($ch, CURLOPT_HEADER, false);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, false);
curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
$page = curl_exec($ch);
echo $page;

Thanks.

Jala answered 1/9, 2015 at 6:26 Comment(0)
P
28

As for Guzzle 6.

Guzzle docs give info about setting proxy for a single request

$client->request('GET', '/', ['proxy' => 'tcp://localhost:8125']);

But you can set it to all requests when initializing client

    $client = new Client([
        'base_uri' => 'http://doma.in/',
        'timeout' => 10.0,
        'cookie' => true,
        'proxy' => 'tcp://12.34.56.78:3128',
    ]);

UPD. I don't know why, but I face a strange behaviour. One server with guzzle version 6.2.2 works great with config as above, and the other one with the same version receives 400 Bad Request HTTP error from a proxy. It is solved with another config structure (found in docs for guzzle 3)

$client = new Client([
    'base_uri' => 'http://doma.in/',
    'timeout' => 10.0,
    'cookie' => true,
    'request.options' => [
        'proxy' => 'tcp://12.34.56.78:3128',
    ],
]);
Ploce answered 3/2, 2017 at 23:29 Comment(0)
C
15

for a proxy, if you have the username and password, you can use:

$client = new GuzzleHttp\Client();

$res = $client->request("POST", "https://endpoint.com", [
    "proxy" => "http://username:[email protected]:10",
]);

this worked with guzzle in php.

Callaway answered 23/1, 2019 at 3:26 Comment(0)
T
5

For Guzzle6, I think the best way is to implement a middleware for setting proxy.

From Guzzle6 docs:

We can set proxy as below:

use Psr\Http\Message\RequestInterface;
use GuzzleHttp\HandlerStack;
use GuzzleHttp\Handler\CurlHandler;
use GuzzleHttp\Client;
use GuzzleHttp\Middleware;
use Util\Api;
function add_proxy_callback($proxy_callback) {
    return function (callable $handler) use ($proxy_callback) {
        return function (RequestInterface $request,$options) use ($handler,$proxy_callback) {
            $ip = $proxy_callback();
            $options['proxy'] = $ip;
            return $handler($request,$options);
        };
    };
} 
$stack = new HandlerStack();
$stack->setHandler(new CurlHandler());
$stack->push(add_proxy_callback(function() {
    return Api::getIp(); //function return a ip 
}));
$client = new Client(['handler'=>$stack]);
$response = $client->request('GET','http://httpbin.org/ip');
var_dump((string)$response->getBody());
Trictrac answered 6/12, 2017 at 10:51 Comment(0)
C
3

The procedure for psr-7 may be different, but if you're using the standard way to instantiate a client,

path\to\project\vendor\guzzlehttp\guzzle\src\Client.php, lines 164-170 includes code to read the environment variables to see if HTTP_PROXY and HTTPS_PROXY are set on the current machine, and if yes, Guzzle will use those values.

Additionally, I had to set my HTTPS_PROXY = http://ip:port (not https), because our workplace proxy seems to handle both https and http requests via the http protocol.

The advantage of this configuration is that you don't have to chnge proxy settings in your source code.

Crocked answered 13/1, 2016 at 6:28 Comment(2)
This no longer works due to the httpoxy vulnerability: github.com/guzzle/guzzle/issues/1534Ectoblast
@LarsNyström tested this with Laravel .env and it's still workingPaulownia
C
3

Had the same problem right now , and all i needed to do was use curl array keys as constants instead of strings ..

$response = $client->send($request, [
              'timeout'  => 30,
              'curl'  => [
                  CURLOPT_PROXY => '*.*.*.*',
                  CURLOPT_PROXYPORT => *,
                  CURLOPT_PROXYUSERPWD => '*:*',
             ],
         ]);

See CURL options Keys , they are not strings anymore.

Cattan answered 22/2, 2016 at 23:58 Comment(0)
H
1
$response = \Drupal::httpClient()->post($settings['base_url'] . 'api/search/', [
    'verify' => true,
    'body' => $post_data,
      'headers' => [
        'Content-type' => 'application/json',
      ],
    'curl' => [
        CURLOPT_SSLVERSION => CURL_SSLVERSION_TLSv1_2, 
        CURLOPT_PROXY => 'proxyip:58080'],
    ]
  )->getBody()->getContents();

Set proxy/https in Guzzle and SSL its work perfect.

Homologous answered 17/10, 2017 at 14:54 Comment(0)
N
0

To be able to use proxy with Guzzle 7.x you can try following settings:

$options = [
    'proxy' => [
        'http' => 'http://1.2.3.4:8080', // Use this proxy with "http"
        'https' => 'http://1.2.3.5:8080', // Use this proxy with "https",
        'no' => ['.mit.edu', 'foo.com']    // Don't use a proxy with these
    ]
];
    
$httpClient = new Client();
$response = $httpClient->get('http://wttr.in/Zagreb?0', $options);
$content = $response->getBody()->getContents();
echo $content;
Naker answered 4/12, 2023 at 11:59 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.