1
0
mirror of https://github.com/kevin1024/vcrpy.git synced 2025-12-10 01:25:34 +00:00

Merge pull request #389 from lamenezes/fix-proxy

Fix proxy
This commit is contained in:
Luiz Menezes
2018-09-18 11:32:53 -03:00
committed by GitHub
2 changed files with 72 additions and 3 deletions

View File

@@ -0,0 +1,60 @@
# -*- coding: utf-8 -*-
'''Test using a proxy.'''
# External imports
import multiprocessing
import pytest
from six.moves import socketserver, SimpleHTTPServer
from six.moves.urllib.request import urlopen
# Internal imports
import vcr
# Conditional imports
requests = pytest.importorskip("requests")
class Proxy(SimpleHTTPServer.SimpleHTTPRequestHandler):
'''
Simple proxy server.
(Inspired by: http://effbot.org/librarybook/simplehttpserver.htm).
'''
def do_GET(self):
upstream_response = urlopen(self.path)
try:
status = upstream_response.status
headers = upstream_response.headers.items()
except AttributeError:
# In Python 2 the response is an addinfourl instance.
status = upstream_response.code
headers = upstream_response.info().items()
self.send_response(status, upstream_response.msg)
for header in headers:
self.send_header(*header)
self.end_headers()
self.copyfile(upstream_response, self.wfile)
@pytest.yield_fixture(scope='session')
def proxy_server():
httpd = socketserver.ThreadingTCPServer(('', 0), Proxy)
proxy_process = multiprocessing.Process(
target=httpd.serve_forever,
)
proxy_process.start()
yield 'http://{0}:{1}'.format(*httpd.server_address)
proxy_process.terminate()
def test_use_proxy(tmpdir, httpbin, proxy_server):
'''Ensure that it works with a proxy.'''
with vcr.use_cassette(str(tmpdir.join('proxy.yaml'))):
response = requests.get(httpbin.url, proxies={'http': proxy_server})
with vcr.use_cassette(str(tmpdir.join('proxy.yaml'))) as cassette:
cassette_response = requests.get(httpbin.url, proxies={'http': proxy_server})
assert cassette_response.headers == response.headers
assert cassette.play_count == 1

View File

@@ -18,7 +18,7 @@ log = logging.getLogger(__name__)
class VCRFakeSocket(object): class VCRFakeSocket(object):
""" """
A socket that doesn't do anything! A socket that doesn't do anything!
Used when playing back casssettes, when there Used when playing back cassettes, when there
is no actual open socket. is no actual open socket.
""" """
@@ -136,7 +136,10 @@ class VCRConnection(object):
def _uri(self, url): def _uri(self, url):
"""Returns request absolute URI""" """Returns request absolute URI"""
uri = "{}://{}{}{}".format( if url and not url.startswith('/'):
# Then this must be a proxy request.
return url
uri = "{0}://{1}{2}{3}".format(
self._protocol, self._protocol,
self.real_connection.host, self.real_connection.host,
self._port_postfix(), self._port_postfix(),
@@ -168,6 +171,8 @@ class VCRConnection(object):
# allows me to compare the entire length of the response to see if it # allows me to compare the entire length of the response to see if it
# exists in the cassette. # exists in the cassette.
self._sock = VCRFakeSocket()
def putrequest(self, method, url, *args, **kwargs): def putrequest(self, method, url, *args, **kwargs):
""" """
httplib gives you more than one way to do it. This is a way httplib gives you more than one way to do it. This is a way
@@ -291,11 +296,13 @@ class VCRConnection(object):
with force_reset(): with force_reset():
return self.real_connection.connect(*args, **kwargs) return self.real_connection.connect(*args, **kwargs)
self._sock = VCRFakeSocket()
@property @property
def sock(self): def sock(self):
if self.real_connection.sock: if self.real_connection.sock:
return self.real_connection.sock return self.real_connection.sock
return VCRFakeSocket() return self._sock
@sock.setter @sock.setter
def sock(self, value): def sock(self, value):
@@ -313,6 +320,8 @@ class VCRConnection(object):
with force_reset(): with force_reset():
self.real_connection = self._baseclass(*args, **kwargs) self.real_connection = self._baseclass(*args, **kwargs)
self._sock = None
def __setattr__(self, name, value): def __setattr__(self, name, value):
""" """
We need to define this because any attributes that are set on the We need to define this because any attributes that are set on the