Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Force cURL to use GET on proxy for HTTPs requests

I'm trying to use a forward proxy server (Apache Traffic Server or Squid) on my local machine, as a local HTTP cache for my cURL calls.

I've set up the proxy using:

curl_setopt($ch, CURLOPT_PROXY, 'http://localhost:8080');

When I query an HTTP website, cURL performs a standard HTTP GET proxy request, which can be cached properly:

GET http://example.com/ HTTP/1.1

However, when querying an HTTPs website, cURL performs a CONNECT instead, effectively using the proxy as a TCP tunnel, and preventing it from caching the response:

CONNECT example.com:80 HTTP/1.1

Is there a way to force cURL to perform a GET request even for HTTPs websites?

I can understand the rationale behind using a TCP tunnel for HTTPs requests over an HTTP proxy for security, but because my proxy server is on localhost, I don't care using an insecure HTTP connection to the proxy, and would like cURL to perform a GET request:

GET https://example.com/ HTTP/1.1

I tried using:

curl_setopt($ch, CURLOPT_HTTPPROXYTUNNEL, false);

But this didn't change anything.

like image 519
BenMorel Avatar asked Mar 20 '16 02:03

BenMorel


1 Answers

I don't believe this can be done using some common configuration setting on the client side as it would deny the whole purpose of HTTPS (that no one can eavesdrop your HTTPS traffic).

Your only option is thus to configure your proxy to basically create a man-in-the-middle attack to decrypt the HTTPS traffic going through it. Squid proxy should support this using their "SSL bump" feature. There is a nice intro for it on this wiki and more setup docs here.

What squid does in this regime is that it gets the address of the remote server from the client's CONNECT request and instead of creating just a blind tunnel to the server, it starts a new direct HTTPS request to the server by itself and saves the reply. Thus Squid has access to all the traffic and can cache it or do anything else Squid can do with it.

When sending replies back to the client, it itself needs to present a HTTPS certificate (the client expects HTTPS traffic), so in Squid there is a feature to automatically generate certificates for all proxied domains. To configure it you will essentially have to create a local Certificate Authority. Note that these auto-generated certificates will be simple self-signed certificates so, on the client side, this will look as untrusted certificates and you'll need to switch off peer verification (CURLOPT_SSL_VERIFYPEER = false).

I could not find any similar feature in Apache traffic server. They seem to support only SSL termination in the reverse proxy mode.

Last note: please bear in mind that this is still rather a hack and decrypting HTTPS may bring legal or ethical problems. Never do this without the clients consent!

like image 143
Matouš Borák Avatar answered Oct 11 '22 23:10

Matouš Borák