Skip to content

Commit

Permalink
User-Agent support in acme (default: acme-python, fixes certbot#1351).
Browse files Browse the repository at this point in the history
In order to override the default (`acme-python`), clients (including
Let's Encrypt: certbot#858, certbot#1397) should create a custom
acme.clietn.ClientNetwork object and pass it to
acme.client.Client.__init__.
  • Loading branch information
kuba committed Nov 7, 2015
1 parent fc8af6b commit dc60cdb
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 4 deletions.
6 changes: 5 additions & 1 deletion acme/acme/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -481,11 +481,13 @@ class ClientNetwork(object):
JSON_ERROR_CONTENT_TYPE = 'application/problem+json'
REPLAY_NONCE_HEADER = 'Replay-Nonce'

def __init__(self, key, alg=jose.RS256, verify_ssl=True):
def __init__(self, key, alg=jose.RS256, verify_ssl=True,
user_agent='acme-python'):
self.key = key
self.alg = alg
self.verify_ssl = verify_ssl
self._nonces = set()
self.user_agent = user_agent

def _wrap_in_jws(self, obj, nonce):
"""Wrap `JSONDeSerializable` object in JWS.
Expand Down Expand Up @@ -578,6 +580,8 @@ def _send_request(self, method, url, *args, **kwargs):
logging.debug('Sending %s request to %s. args: %r, kwargs: %r',
method, url, args, kwargs)
kwargs['verify'] = self.verify_ssl
kwargs.setdefault('headers', {})
kwargs['headers'].setdefault('User-Agent', self.user_agent)
response = requests.request(method, url, *args, **kwargs)
logging.debug('Received %s. Headers: %s. Content: %r',
response, response.headers, response.content)
Expand Down
20 changes: 17 additions & 3 deletions acme/acme/client_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -396,7 +396,8 @@ def setUp(self):

from acme.client import ClientNetwork
self.net = ClientNetwork(
key=KEY, alg=jose.RS256, verify_ssl=self.verify_ssl)
key=KEY, alg=jose.RS256, verify_ssl=self.verify_ssl,
user_agent='acme-python-test')

self.response = mock.MagicMock(ok=True, status_code=http_client.OK)
self.response.headers = {}
Expand Down Expand Up @@ -479,7 +480,7 @@ def test_send_request(self, mock_requests):
self.assertEqual(self.response, self.net._send_request(
'HEAD', 'url', 'foo', bar='baz'))
mock_requests.request.assert_called_once_with(
'HEAD', 'url', 'foo', verify=mock.ANY, bar='baz')
'HEAD', 'url', 'foo', verify=mock.ANY, bar='baz', headers=mock.ANY)

@mock.patch('acme.client.requests')
def test_send_request_verify_ssl(self, mock_requests):
Expand All @@ -492,7 +493,20 @@ def test_send_request_verify_ssl(self, mock_requests):
self.assertEqual(
self.response, self.net._send_request('GET', 'url'))
mock_requests.request.assert_called_once_with(
'GET', 'url', verify=verify)
'GET', 'url', verify=verify, headers=mock.ANY)

@mock.patch('acme.client.requests')
def test_send_request_user_agent(self, mock_requests):
mock_requests.request.return_value = self.response
# pylint: disable=protected-access
self.net._send_request('GET', 'url', headers={'bar': 'baz'})
mock_requests.request.assert_called_once_with(
'GET', 'url', verify=mock.ANY,
headers={'User-Agent': 'acme-python-test', 'bar': 'baz'})

self.net._send_request('GET', 'url', headers={'User-Agent': 'foo2'})
mock_requests.request.assert_called_with(
'GET', 'url', verify=mock.ANY, headers={'User-Agent': 'foo2'})

@mock.patch('acme.client.requests')
def test_requests_error_passthrough(self, mock_requests):
Expand Down

0 comments on commit dc60cdb

Please sign in to comment.