Merge pull request #435 from kuba/boulder-compat

Spec and Boulder compatibility fixes
This commit is contained in:
schoen 2015-05-19 17:04:07 -07:00
commit 1681fbea3a
5 changed files with 26 additions and 27 deletions

View file

@ -18,11 +18,9 @@ class Error(jose.JSONObjectWithFields, Exception):
'badCSR': 'The CSR is unacceptable (e.g., due to a short key)',
}
# TODO: Boulder omits 'type' and 'instance', spec requires, boulder#128
typ = jose.Field('type', omitempty=True)
typ = jose.Field('type')
title = jose.Field('title', omitempty=True)
detail = jose.Field('detail')
instance = jose.Field('instance', omitempty=True)
@typ.encoder
def typ(value): # pylint: disable=missing-docstring,no-self-argument
@ -227,10 +225,6 @@ class Authorization(ResourceBody):
challenges = jose.Field('challenges', omitempty=True)
combinations = jose.Field('combinations', omitempty=True)
# TODO: acme-spec #92, #98
key = Registration._fields['key']
contact = Registration._fields['contact']
status = jose.Field('status', omitempty=True, decoder=Status.from_json)
# TODO: 'expires' is allowed for Authorization Resources in
# general, but for Key Authorization '[t]he "expires" field MUST

View file

@ -21,7 +21,8 @@ class ErrorTest(unittest.TestCase):
def setUp(self):
from acme.messages2 import Error
self.error = Error(detail='foo', typ='malformed')
self.error = Error(detail='foo', typ='malformed', title='title')
self.jobj = {'detail': 'foo', 'title': 'some title'}
def test_typ_prefix(self):
self.assertEqual('malformed', self.error.typ)
@ -32,15 +33,15 @@ class ErrorTest(unittest.TestCase):
def test_typ_decoder_missing_prefix(self):
from acme.messages2 import Error
self.assertRaises(jose.DeserializationError, Error.from_json,
{'detail': 'foo', 'type': 'malformed'})
self.assertRaises(jose.DeserializationError, Error.from_json,
{'detail': 'foo', 'type': 'not valid bare type'})
self.jobj['type'] = 'malfomed'
self.assertRaises(jose.DeserializationError, Error.from_json, self.jobj)
self.jobj['type'] = 'not balid bare type'
self.assertRaises(jose.DeserializationError, Error.from_json, self.jobj)
def test_typ_decoder_not_recognized(self):
from acme.messages2 import Error
self.assertRaises(jose.DeserializationError, Error.from_json,
{'detail': 'foo', 'type': 'urn:acme:error:baz'})
self.jobj['type'] = 'urn:acme:error:baz'
self.assertRaises(jose.DeserializationError, Error.from_json, self.jobj)
def test_description(self):
self.assertEqual(

View file

@ -115,6 +115,7 @@ class Network(object):
:rtype: `requests.Response`
"""
logging.debug('Sending GET request to %s', uri)
try:
response = requests.get(uri, **kwargs)
except requests.exceptions.RequestException as error:
@ -133,12 +134,12 @@ class Network(object):
:rtype: `requests.Response`
"""
logging.debug('Sending POST data: %s', data)
logging.debug('Sending POST data to %s: %s', uri, data)
try:
response = requests.post(uri, data=data, **kwargs)
except requests.exceptions.RequestException as error:
raise errors.NetworkError(error)
logging.debug('Received response %s: %s', response, response.text)
logging.debug('Received response %s: %r', response, response.text)
self._check_response(response, content_type=content_type)
return response
@ -247,6 +248,7 @@ class Network(object):
def _authzr_from_response(self, response, identifier,
uri=None, new_cert_uri=None):
# pylint: disable=no-self-use
if new_cert_uri is None:
try:
new_cert_uri = response.links['next']['url']
@ -257,8 +259,7 @@ class Network(object):
body=messages2.Authorization.from_json(response.json()),
uri=response.headers.get('Location', uri),
new_cert_uri=new_cert_uri)
if (authzr.body.key != self.key.public()
or authzr.body.identifier != identifier):
if authzr.body.identifier != identifier:
raise errors.UnexpectedUpdate(authzr)
return authzr

View file

@ -276,8 +276,6 @@ class PollChallengesTest(unittest.TestCase):
identifier=authzr.body.identifier,
challenges=new_challbs,
combinations=authzr.body.combinations,
key=authzr.body.key,
contact=authzr.body.contact,
status=status_,
),
)

View file

@ -72,7 +72,7 @@ class NetworkTest(unittest.TestCase):
self.authz = messages2.Authorization(
identifier=messages2.Identifier(
typ=messages2.IDENTIFIER_FQDN, value='example.com'),
challenges=(challb,), combinations=None, key=KEY.public())
challenges=(challb,), combinations=None)
self.authzr = messages2.AuthorizationResource(
body=self.authz, uri=authzr_uri,
new_cert_uri='https://www.letsencrypt-demo.org/acme/new-cert')
@ -114,7 +114,8 @@ class NetworkTest(unittest.TestCase):
def test_check_response_not_ok_jobj_error(self):
self.response.ok = False
self.response.json.return_value = messages2.Error(detail='foo')
self.response.json.return_value = messages2.Error(
detail='foo', typ='serverInternal', title='some title').to_json()
# pylint: disable=protected-access
self.assertRaises(
messages2.Error, self.net._check_response, self.response)
@ -258,11 +259,10 @@ class NetworkTest(unittest.TestCase):
# TODO: test POST call arguments
# TODO: split here and separate test
authz_wrong_key = self.authz.update(key=KEY2.public())
self.response.json.return_value = authz_wrong_key.to_json()
self.assertRaises(
errors.UnexpectedUpdate, self.net.request_challenges,
self.identifier, self.regr)
self.response.json.return_value = self.authz.update(
identifier=self.identifier.update(value='foo')).to_json()
self.assertRaises(errors.UnexpectedUpdate, self.net.request_challenges,
self.identifier, self.authzr.uri)
def test_request_challenges_missing_next(self):
self.response.status_code = httplib.CREATED
@ -336,6 +336,11 @@ class NetworkTest(unittest.TestCase):
self.assertEqual((self.authzr, self.response),
self.net.poll(self.authzr))
# TODO: split here and separate test
self.response.json.return_value = self.authz.update(
identifier=self.identifier.update(value='foo')).to_json()
self.assertRaises(errors.UnexpectedUpdate, self.net.poll, self.authzr)
def test_request_issuance(self):
self.response.content = CERT.as_der()
self.response.headers['Location'] = self.certr.uri