Merge remote-tracking branch 'github/letsencrypt/master' into test-dirs-chmods

Conflicts:
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/foo.conf
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/nginx.conf
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/nginx.new.conf
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/server.conf
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/sites-enabled/default
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/sites-enabled/example.com
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/fastcgi_params
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/koi-utf
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/koi-win
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/mime.types
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi-ui.conf.1.4.1
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi.rules
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi_core.rules
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/nginx.conf
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/proxy_params
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/scgi_params
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/sites-available/default
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/sites-enabled/default
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/uwsgi_params
	letsencrypt/client/plugins/nginx/tests/testdata/etc_nginx/ubuntu_nginx_1_4_6/default_vhost/nginx/win-utf
	letsencrypt/client/plugins/nginx/tests/testdata/foo.conf
	letsencrypt/client/plugins/nginx/tests/testdata/nginx.conf
	letsencrypt/client/plugins/nginx/tests/testdata/nginx.new.conf
	letsencrypt/client/plugins/nginx/tests/testdata/server.conf
	letsencrypt/client/plugins/nginx/tests/testdata/sites-enabled/default
	letsencrypt/client/plugins/nginx/tests/testdata/sites-enabled/example.com
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/fastcgi_params
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/koi-utf
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/koi-win
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/mime.types
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi-ui.conf.1.4.1
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi.rules
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi_core.rules
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/nginx.conf
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/proxy_params
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/scgi_params
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/sites-available/default
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/sites-enabled/default
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/uwsgi_params
	letsencrypt/client/plugins/nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/win-utf
	letsencrypt_apache/tests/util.py
	letsencrypt_nginx/tests/testdata/foo.conf
	letsencrypt_nginx/tests/testdata/nginx.conf
	letsencrypt_nginx/tests/testdata/nginx.new.conf
	letsencrypt_nginx/tests/testdata/server.conf
	letsencrypt_nginx/tests/testdata/sites-enabled/default
	letsencrypt_nginx/tests/testdata/sites-enabled/example.com
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/fastcgi_params
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/koi-utf
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/koi-win
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/mime.types
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi-ui.conf.1.4.1
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi.rules
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/naxsi_core.rules
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/nginx.conf
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/proxy_params
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/scgi_params
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/sites-available/default
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/sites-enabled/default
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/uwsgi_params
	letsencrypt_nginx/tests/testdata/ubuntu_nginx_1_4_6/default_vhost/nginx/win-utf
	letsencrypt_nginx/tests/util.py
This commit is contained in:
Jakub Warmuz 2015-05-12 21:06:17 +00:00
commit bb94952830
No known key found for this signature in database
GPG key ID: 2A7BAD3A489B52EA
282 changed files with 3834 additions and 2526 deletions

2
.gitignore vendored
View file

@ -10,4 +10,4 @@ m3
*~
.vagrant
*.swp
\#*#
\#*#

View file

@ -3,6 +3,14 @@ include CHANGES.rst
include CONTRIBUTING.md
include linter_plugin.py
include letsencrypt/EULA
recursive-include letsencrypt *.json
recursive-include letsencrypt *.conf
recursive-include letsencrypt/client/tests/testdata *
recursive-include acme/schemata *.json
recursive-include acme/jose/testdata *
recursive-include letsencrypt_apache/tests/testdata *
include letsencrypt_apache/options-ssl.conf
recursive-include letsencrypt_nginx/tests/testdata *
include letsencrypt_nginx/options-ssl.conf

View file

@ -17,11 +17,15 @@ It's all automated:
* If domain control has been proven, a certificate will get issued and the tool
will automatically install it.
All you need to do is:
All you need to do is::
::
user@www:~$ sudo letsencrypt -d www.example.org auth
user@www:~$ sudo letsencrypt -d www.example.org
and if you have a compatbile web server (Apache or Nginx), Let's Encrypt can
not only get a new certificate, but also deploy it and configure your
server automatically!::
user@www:~$ sudo letsencrypt -d www.example.org run
**Encrypt ALL the things!**
@ -56,7 +60,8 @@ Current Features
* web servers supported:
- apache2.x (tested and working on Ubuntu Linux)
- apache/2.x (tested and working on Ubuntu Linux)
- nginx/0.8.48+ (tested and mostly working on Ubuntu Linux)
- standalone (runs its own webserver to prove you control the domain)
* the private key is generated locally on your system
@ -66,7 +71,7 @@ Current Features
* can revoke certificates
* adjustable RSA key bitlength (2048 (default), 4096, ...)
* optionally can install a http->https redirect, so your site effectively
runs https only
runs https only (Apache only)
* fully automated
* configuration changes are logged and can be reverted using the CLI
* text and ncurses UI

2
Vagrantfile vendored
View file

@ -10,7 +10,7 @@ cd /vagrant
sudo ./bootstrap/ubuntu.sh
if [ ! -d "venv" ]; then
virtualenv --no-site-packages -p python2 venv
./venv/bin/python setup.py dev
./venv/bin/pip install -r requirements.txt -e .[dev,docs,testing]
fi
SETUP_SCRIPT

View file

@ -5,8 +5,8 @@ import hashlib
import Crypto.Random
from letsencrypt.acme import jose
from letsencrypt.acme import other
from acme import jose
from acme import other
# pylint: disable=too-few-public-methods
@ -186,8 +186,8 @@ class ProofOfPossession(ContinuityChallenge):
class Hints(jose.JSONObjectWithFields):
"""Hints for "proofOfPossession" challenge.
:ivar jwk: JSON Web Key (:class:`letsencrypt.acme.jose.JWK`)
:ivar list certs: List of :class:`letsencrypt.acme.jose.ComparableX509`
:ivar jwk: JSON Web Key (:class:`acme.jose.JWK`)
:ivar list certs: List of :class:`acme.jose.ComparableX509`
certificates.
"""
@ -221,7 +221,7 @@ class ProofOfPossessionResponse(ChallengeResponse):
"""ACME "proofOfPossession" challenge response.
:ivar str nonce: Random data, **not** base64-encoded.
:ivar signature: :class:`~letsencrypt.acme.other.Signature` of this message.
:ivar signature: :class:`~acme.other.Signature` of this message.
"""
typ = "proofOfPossession"

View file

@ -1,4 +1,4 @@
"""Tests for letsencrypt.acme.challenges."""
"""Tests for acme.challenges."""
import os
import pkg_resources
import unittest
@ -6,23 +6,22 @@ import unittest
import Crypto.PublicKey.RSA
import M2Crypto
from letsencrypt.acme import jose
from letsencrypt.acme import other
from acme import jose
from acme import other
CERT = jose.ComparableX509(M2Crypto.X509.load_cert(
pkg_resources.resource_filename(
'letsencrypt.client.tests', os.path.join('testdata', 'cert.pem'))))
'letsencrypt.tests', os.path.join('testdata', 'cert.pem'))))
KEY = jose.HashableRSAKey(Crypto.PublicKey.RSA.importKey(
pkg_resources.resource_string(
'letsencrypt.acme.jose',
os.path.join('testdata', 'rsa512_key.pem'))))
'acme.jose', os.path.join('testdata', 'rsa512_key.pem'))))
class SimpleHTTPSTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import SimpleHTTPS
from acme.challenges import SimpleHTTPS
self.msg = SimpleHTTPS(
token='evaGxfADs6pSRb2LAv9IZf17Dt3juxGJ+PCt92wr+oA')
self.jmsg = {
@ -34,18 +33,18 @@ class SimpleHTTPSTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import SimpleHTTPS
from acme.challenges import SimpleHTTPS
self.assertEqual(self.msg, SimpleHTTPS.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import SimpleHTTPS
from acme.challenges import SimpleHTTPS
hash(SimpleHTTPS.from_json(self.jmsg))
class SimpleHTTPSResponseTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import SimpleHTTPSResponse
from acme.challenges import SimpleHTTPSResponse
self.msg = SimpleHTTPSResponse(path='6tbIMBC5Anhl5bOlWT5ZFA')
self.jmsg = {
'type': 'simpleHttps',
@ -60,19 +59,19 @@ class SimpleHTTPSResponseTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import SimpleHTTPSResponse
from acme.challenges import SimpleHTTPSResponse
self.assertEqual(
self.msg, SimpleHTTPSResponse.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import SimpleHTTPSResponse
from acme.challenges import SimpleHTTPSResponse
hash(SimpleHTTPSResponse.from_json(self.jmsg))
class DVSNITest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import DVSNI
from acme.challenges import DVSNI
self.msg = DVSNI(
r="O*\xb4-\xad\xec\x95>\xed\xa9\r0\x94\xe8\x97\x9c&6"
"\xbf'\xb3\xed\x9a9nX\x0f'\\m\xe7\x12",
@ -91,21 +90,21 @@ class DVSNITest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import DVSNI
from acme.challenges import DVSNI
self.assertEqual(self.msg, DVSNI.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import DVSNI
from acme.challenges import DVSNI
hash(DVSNI.from_json(self.jmsg))
def test_from_json_invalid_r_length(self):
from letsencrypt.acme.challenges import DVSNI
from acme.challenges import DVSNI
self.jmsg['r'] = 'abcd'
self.assertRaises(
jose.DeserializationError, DVSNI.from_json, self.jmsg)
def test_from_json_invalid_nonce_length(self):
from letsencrypt.acme.challenges import DVSNI
from acme.challenges import DVSNI
self.jmsg['nonce'] = 'abcd'
self.assertRaises(
jose.DeserializationError, DVSNI.from_json, self.jmsg)
@ -114,7 +113,7 @@ class DVSNITest(unittest.TestCase):
class DVSNIResponseTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import DVSNIResponse
from acme.challenges import DVSNIResponse
self.msg = DVSNIResponse(
s='\xf5\xd6\xe3\xb2]\xe0L\x0bN\x9cKJ\x14I\xa1K\xa3#\xf9\xa8'
'\xcd\x8c7\x0e\x99\x19)\xdc\xb7\xf3\x9bw')
@ -124,7 +123,7 @@ class DVSNIResponseTest(unittest.TestCase):
}
def test_z_and_domain(self):
from letsencrypt.acme.challenges import DVSNI
from acme.challenges import DVSNI
challenge = DVSNI(
r="O*\xb4-\xad\xec\x95>\xed\xa9\r0\x94\xe8\x97\x9c&6"
"\xbf'\xb3\xed\x9a9nX\x0f'\\m\xe7\x12",
@ -140,18 +139,18 @@ class DVSNIResponseTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import DVSNIResponse
from acme.challenges import DVSNIResponse
self.assertEqual(self.msg, DVSNIResponse.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import DVSNIResponse
from acme.challenges import DVSNIResponse
hash(DVSNIResponse.from_json(self.jmsg))
class RecoveryContactTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import RecoveryContact
from acme.challenges import RecoveryContact
self.msg = RecoveryContact(
activation_url='https://example.ca/sendrecovery/a5bd99383fb0',
success_url='https://example.ca/confirmrecovery/bb1b9928932',
@ -167,11 +166,11 @@ class RecoveryContactTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import RecoveryContact
from acme.challenges import RecoveryContact
self.assertEqual(self.msg, RecoveryContact.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import RecoveryContact
from acme.challenges import RecoveryContact
hash(RecoveryContact.from_json(self.jmsg))
def test_json_without_optionals(self):
@ -179,7 +178,7 @@ class RecoveryContactTest(unittest.TestCase):
del self.jmsg['successURL']
del self.jmsg['contact']
from letsencrypt.acme.challenges import RecoveryContact
from acme.challenges import RecoveryContact
msg = RecoveryContact.from_json(self.jmsg)
self.assertTrue(msg.activation_url is None)
@ -191,7 +190,7 @@ class RecoveryContactTest(unittest.TestCase):
class RecoveryContactResponseTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import RecoveryContactResponse
from acme.challenges import RecoveryContactResponse
self.msg = RecoveryContactResponse(token='23029d88d9e123e')
self.jmsg = {'type': 'recoveryContact', 'token': '23029d88d9e123e'}
@ -199,18 +198,18 @@ class RecoveryContactResponseTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import RecoveryContactResponse
from acme.challenges import RecoveryContactResponse
self.assertEqual(
self.msg, RecoveryContactResponse.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import RecoveryContactResponse
from acme.challenges import RecoveryContactResponse
hash(RecoveryContactResponse.from_json(self.jmsg))
def test_json_without_optionals(self):
del self.jmsg['token']
from letsencrypt.acme.challenges import RecoveryContactResponse
from acme.challenges import RecoveryContactResponse
msg = RecoveryContactResponse.from_json(self.jmsg)
self.assertTrue(msg.token is None)
@ -220,7 +219,7 @@ class RecoveryContactResponseTest(unittest.TestCase):
class RecoveryTokenTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import RecoveryToken
from acme.challenges import RecoveryToken
self.msg = RecoveryToken()
self.jmsg = {'type': 'recoveryToken'}
@ -228,18 +227,18 @@ class RecoveryTokenTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import RecoveryToken
from acme.challenges import RecoveryToken
self.assertEqual(self.msg, RecoveryToken.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import RecoveryToken
from acme.challenges import RecoveryToken
hash(RecoveryToken.from_json(self.jmsg))
class RecoveryTokenResponseTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import RecoveryTokenResponse
from acme.challenges import RecoveryTokenResponse
self.msg = RecoveryTokenResponse(token='23029d88d9e123e')
self.jmsg = {'type': 'recoveryToken', 'token': '23029d88d9e123e'}
@ -247,18 +246,18 @@ class RecoveryTokenResponseTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import RecoveryTokenResponse
from acme.challenges import RecoveryTokenResponse
self.assertEqual(
self.msg, RecoveryTokenResponse.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import RecoveryTokenResponse
from acme.challenges import RecoveryTokenResponse
hash(RecoveryTokenResponse.from_json(self.jmsg))
def test_json_without_optionals(self):
del self.jmsg['token']
from letsencrypt.acme.challenges import RecoveryTokenResponse
from acme.challenges import RecoveryTokenResponse
msg = RecoveryTokenResponse.from_json(self.jmsg)
self.assertTrue(msg.token is None)
@ -282,7 +281,7 @@ class ProofOfPossessionHintsTest(unittest.TestCase):
authorized_for = ('www.example.com', 'example.net')
serial_numbers = (34234239832, 23993939911, 17)
from letsencrypt.acme.challenges import ProofOfPossession
from acme.challenges import ProofOfPossession
self.msg = ProofOfPossession.Hints(
jwk=jwk, issuers=issuers, cert_fingerprints=cert_fingerprints,
certs=(CERT,), subject_key_identifiers=subject_key_identifiers,
@ -304,12 +303,12 @@ class ProofOfPossessionHintsTest(unittest.TestCase):
self.assertEqual(self.jmsg_to, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import ProofOfPossession
from acme.challenges import ProofOfPossession
self.assertEqual(
self.msg, ProofOfPossession.Hints.from_json(self.jmsg_from))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import ProofOfPossession
from acme.challenges import ProofOfPossession
hash(ProofOfPossession.Hints.from_json(self.jmsg_from))
def test_json_without_optionals(self):
@ -318,7 +317,7 @@ class ProofOfPossessionHintsTest(unittest.TestCase):
del self.jmsg_from[optional]
del self.jmsg_to[optional]
from letsencrypt.acme.challenges import ProofOfPossession
from acme.challenges import ProofOfPossession
msg = ProofOfPossession.Hints.from_json(self.jmsg_from)
self.assertEqual(msg.cert_fingerprints, ())
@ -334,7 +333,7 @@ class ProofOfPossessionHintsTest(unittest.TestCase):
class ProofOfPossessionTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import ProofOfPossession
from acme.challenges import ProofOfPossession
hints = ProofOfPossession.Hints(
jwk=jose.JWKRSA(key=KEY.publickey()), cert_fingerprints=(),
certs=(), serial_numbers=(), subject_key_identifiers=(),
@ -360,12 +359,12 @@ class ProofOfPossessionTest(unittest.TestCase):
self.assertEqual(self.jmsg_to, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import ProofOfPossession
from acme.challenges import ProofOfPossession
self.assertEqual(
self.msg, ProofOfPossession.from_json(self.jmsg_from))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import ProofOfPossession
from acme.challenges import ProofOfPossession
hash(ProofOfPossession.from_json(self.jmsg_from))
@ -384,7 +383,7 @@ class ProofOfPossessionResponseTest(unittest.TestCase):
nonce='\x99\xc7Q\xb3f2\xbc\xdci\xfe\xd6\x98k\xc67\xdf',
)
from letsencrypt.acme.challenges import ProofOfPossessionResponse
from acme.challenges import ProofOfPossessionResponse
self.msg = ProofOfPossessionResponse(
nonce='xD\xf9\xb9\xdbU\xed\xaa\x17\xf1y|\x81\x88\x99 ',
signature=signature)
@ -407,19 +406,19 @@ class ProofOfPossessionResponseTest(unittest.TestCase):
self.assertEqual(self.jmsg_to, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import ProofOfPossessionResponse
from acme.challenges import ProofOfPossessionResponse
self.assertEqual(
self.msg, ProofOfPossessionResponse.from_json(self.jmsg_from))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import ProofOfPossessionResponse
from acme.challenges import ProofOfPossessionResponse
hash(ProofOfPossessionResponse.from_json(self.jmsg_from))
class DNSTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import DNS
from acme.challenges import DNS
self.msg = DNS(token='17817c66b60ce2e4012dfad92657527a')
self.jmsg = {'type': 'dns', 'token': '17817c66b60ce2e4012dfad92657527a'}
@ -427,18 +426,18 @@ class DNSTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import DNS
from acme.challenges import DNS
self.assertEqual(self.msg, DNS.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import DNS
from acme.challenges import DNS
hash(DNS.from_json(self.jmsg))
class DNSResponseTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.challenges import DNSResponse
from acme.challenges import DNSResponse
self.msg = DNSResponse()
self.jmsg = {'type': 'dns'}
@ -446,13 +445,13 @@ class DNSResponseTest(unittest.TestCase):
self.assertEqual(self.jmsg, self.msg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.challenges import DNSResponse
from acme.challenges import DNSResponse
self.assertEqual(self.msg, DNSResponse.from_json(self.jmsg))
def test_from_json_hashable(self):
from letsencrypt.acme.challenges import DNSResponse
from acme.challenges import DNSResponse
hash(DNSResponse.from_json(self.jmsg))
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -1,5 +1,5 @@
"""ACME errors."""
from letsencrypt.acme.jose import errors as jose_errors
from acme.jose import errors as jose_errors
class Error(Exception):
"""Generic ACME error."""

View file

@ -1,7 +1,7 @@
"""ACME JSON fields."""
import pyrfc3339
from letsencrypt.acme import jose
from acme import jose
class RFC3339Field(jose.Field):

View file

@ -1,35 +1,39 @@
"""Tests for letsencrypt.acme.fields."""
"""Tests for acme.fields."""
import datetime
import unittest
import pytz
from letsencrypt.acme import jose
from acme import jose
class RFC3339FieldTest(unittest.TestCase):
"""Tests for letsencrypt.acme.fields.RFC3339Field."""
"""Tests for acme.fields.RFC3339Field."""
def setUp(self):
self.decoded = datetime.datetime(2015, 3, 27, tzinfo=pytz.utc)
self.encoded = '2015-03-27T00:00:00Z'
def test_default_encoder(self):
from letsencrypt.acme.fields import RFC3339Field
from acme.fields import RFC3339Field
self.assertEqual(
self.encoded, RFC3339Field.default_encoder(self.decoded))
def test_default_encoder_naive_fails(self):
from letsencrypt.acme.fields import RFC3339Field
from acme.fields import RFC3339Field
self.assertRaises(
ValueError, RFC3339Field.default_encoder, datetime.datetime.now())
def test_default_decoder(self):
from letsencrypt.acme.fields import RFC3339Field
from acme.fields import RFC3339Field
self.assertEqual(
self.decoded, RFC3339Field.default_decoder(self.encoded))
def test_default_decoder_raises_deserialization_error(self):
from letsencrypt.acme.fields import RFC3339Field
from acme.fields import RFC3339Field
self.assertRaises(
jose.DeserializationError, RFC3339Field.default_decoder, '')
if __name__ == '__main__':
unittest.main() # pragma: no cover

View file

@ -22,21 +22,21 @@ particular the following RFCs:
https://datatracker.ietf.org/doc/draft-ietf-jose-json-web-signature/
"""
from letsencrypt.acme.jose.b64 import (
from acme.jose.b64 import (
b64decode,
b64encode,
)
from letsencrypt.acme.jose.errors import (
from acme.jose.errors import (
DeserializationError,
SerializationError,
Error,
UnrecognizedTypeError,
)
from letsencrypt.acme.jose.interfaces import JSONDeSerializable
from acme.jose.interfaces import JSONDeSerializable
from letsencrypt.acme.jose.json_util import (
from acme.jose.json_util import (
Field,
JSONObjectWithFields,
TypedJSONObjectWithFields,
@ -48,7 +48,7 @@ from letsencrypt.acme.jose.json_util import (
encode_csr,
)
from letsencrypt.acme.jose.jwa import (
from acme.jose.jwa import (
HS256,
HS384,
HS512,
@ -61,14 +61,14 @@ from letsencrypt.acme.jose.jwa import (
RS512,
)
from letsencrypt.acme.jose.jwk import (
from acme.jose.jwk import (
JWK,
JWKRSA,
)
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
from letsencrypt.acme.jose.util import (
from acme.jose.util import (
ComparableX509,
HashableRSAKey,
ImmutableMap,

View file

@ -1,4 +1,4 @@
"""Tests for letsencrypt.acme.jose.b64."""
"""Tests for acme.jose.b64."""
import unittest
@ -19,11 +19,11 @@ B64_URL_UNSAFE_EXAMPLES = {
class B64EncodeTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.b64.b64encode."""
"""Tests for acme.jose.b64.b64encode."""
@classmethod
def _call(cls, data):
from letsencrypt.acme.jose.b64 import b64encode
from acme.jose.b64 import b64encode
return b64encode(data)
def test_unsafe_url(self):
@ -39,11 +39,11 @@ class B64EncodeTest(unittest.TestCase):
class B64DecodeTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.b64.b64decode."""
"""Tests for acme.jose.b64.b64decode."""
@classmethod
def _call(cls, data):
from letsencrypt.acme.jose.b64 import b64decode
from acme.jose.b64 import b64decode
return b64decode(data)
def test_unsafe_url(self):
@ -69,4 +69,4 @@ class B64DecodeTest(unittest.TestCase):
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -1,10 +1,10 @@
"""Tests for letsencrypt.acme.jose.errors."""
"""Tests for acme.jose.errors."""
import unittest
class UnrecognizedTypeErrorTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.jose.errors import UnrecognizedTypeError
from acme.jose.errors import UnrecognizedTypeError
self.error = UnrecognizedTypeError('foo', {'type': 'foo'})
def test_str(self):
@ -14,4 +14,4 @@ class UnrecognizedTypeErrorTest(unittest.TestCase):
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -3,7 +3,7 @@ import abc
import collections
import json
from letsencrypt.acme.jose import util
from acme.jose import util
# pylint: disable=no-self-argument,no-method-argument,no-init,inherit-non-class
# pylint: disable=too-few-public-methods
@ -110,7 +110,7 @@ class JSONDeSerializable(object):
# in particular...
assert Bar().to_partial_json() != ['foo', 'foo']
:raises letsencrypt.acme.jose.errors.SerializationError:
:raises acme.jose.errors.SerializationError:
in case of any serialization error.
:returns: Partially serializable object.
@ -125,7 +125,7 @@ class JSONDeSerializable(object):
assert Bar().to_json() == ['foo', 'foo']
:raises letsencrypt.acme.jose.errors.SerializationError:
:raises acme.jose.errors.SerializationError:
in case of any serialization error.
:returns: Fully serialized object.
@ -157,7 +157,7 @@ class JSONDeSerializable(object):
types, as decoded from JSON document. Not necessarily
:class:`dict` (as decoded from "JSON object" document).
:raises letsencrypt.acme.jose.errors.DeserializationError:
:raises acme.jose.errors.DeserializationError:
if decoding was unsuccessful, e.g. in case of unparseable
X509 certificate, or wrong padding in JOSE base64 encoded
string, etc.

View file

@ -1,4 +1,4 @@
"""Tests for letsencrypt.acme.jose.interfaces."""
"""Tests for acme.jose.interfaces."""
import unittest
@ -6,7 +6,7 @@ class JSONDeSerializableTest(unittest.TestCase):
# pylint: disable=too-many-instance-attributes
def setUp(self):
from letsencrypt.acme.jose.interfaces import JSONDeSerializable
from acme.jose.interfaces import JSONDeSerializable
# pylint: disable=missing-docstring,invalid-name
@ -44,8 +44,7 @@ class JSONDeSerializableTest(unittest.TestCase):
@classmethod
def from_json(cls, jobj):
return cls(Basic.from_json(jobj.keys()[0]),
Basic.from_json(jobj.values()[0]))
pass # pragma: no cover
self.basic1 = Basic('foo1')
self.basic2 = Basic('foo2')
@ -76,7 +75,7 @@ class JSONDeSerializableTest(unittest.TestCase):
self.assertEqual(self.tuple.to_json(), (('foo', )))
def test_from_json_not_implemented(self):
from letsencrypt.acme.jose.interfaces import JSONDeSerializable
from acme.jose.interfaces import JSONDeSerializable
self.assertRaises(TypeError, JSONDeSerializable.from_json, 'xxx')
def test_json_loads(self):
@ -95,7 +94,7 @@ class JSONDeSerializableTest(unittest.TestCase):
self.seq.json_dumps_pretty(), '[\n "foo1",\n "foo2"\n]')
def test_json_dump_default(self):
from letsencrypt.acme.jose.interfaces import JSONDeSerializable
from acme.jose.interfaces import JSONDeSerializable
self.assertEqual(
'foo1', JSONDeSerializable.json_dump_default(self.basic1))
@ -106,10 +105,10 @@ class JSONDeSerializableTest(unittest.TestCase):
self.assertTrue(jobj[1] is self.basic2)
def test_json_dump_default_type_error(self):
from letsencrypt.acme.jose.interfaces import JSONDeSerializable
from acme.jose.interfaces import JSONDeSerializable
self.assertRaises(
TypeError, JSONDeSerializable.json_dump_default, object())
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -12,10 +12,10 @@ import logging
import M2Crypto
from letsencrypt.acme.jose import b64
from letsencrypt.acme.jose import errors
from letsencrypt.acme.jose import interfaces
from letsencrypt.acme.jose import util
from acme.jose import b64
from acme.jose import errors
from acme.jose import interfaces
from acme.jose import util
class Field(object):
@ -27,8 +27,8 @@ class Field(object):
``encoder`` (``decoder``) is a callable that accepts a single
parameter, i.e. a value to be encoded (decoded), and returns the
serialized (deserialized) value. In case of errors it should raise
:class:`~letsencrypt.acme.jose.errors.SerializationError`
(:class:`~letsencrypt.acme.jose.errors.DeserializationError`).
:class:`~acme.jose.errors.SerializationError`
(:class:`~acme.jose.errors.DeserializationError`).
Note, that ``decoder`` should perform partial serialization only.
@ -96,7 +96,7 @@ class Field(object):
"""Default decoder.
Recursively deserialize into immutable types (
:class:`letsencrypt.acme.jose.util.frozendict` instead of
:class:`acme.jose.util.frozendict` instead of
:func:`dict`, :func:`tuple` instead of :func:`list`).
"""
@ -304,7 +304,7 @@ def encode_cert(cert):
"""Encode certificate as JOSE Base-64 DER.
:param cert: Certificate.
:type cert: :class:`letsencrypt.acme.jose.util.ComparableX509`
:type cert: :class:`acme.jose.util.ComparableX509`
"""
return b64.b64encode(cert.as_der())
@ -381,7 +381,7 @@ class TypedJSONObjectWithFields(JSONObjectWithFields):
:returns: Serializable JSON object representing ACME typed object.
:meth:`validate` will almost certainly not work, due to reasons
explained in :class:`letsencrypt.acme.interfaces.IJSONSerializable`.
explained in :class:`acme.interfaces.IJSONSerializable`.
:rtype: dict
"""
@ -393,7 +393,7 @@ class TypedJSONObjectWithFields(JSONObjectWithFields):
def from_json(cls, jobj):
"""Deserialize ACME object from valid JSON object.
:raises letsencrypt.acme.errors.UnrecognizedTypeError: if type
:raises acme.errors.UnrecognizedTypeError: if type
of the ACME object has not been registered.
"""

View file

@ -1,4 +1,4 @@
"""Tests for letsencrypt.acme.jose.json_util."""
"""Tests for acme.jose.json_util."""
import os
import pkg_resources
import unittest
@ -6,19 +6,19 @@ import unittest
import M2Crypto
import mock
from letsencrypt.acme.jose import errors
from letsencrypt.acme.jose import interfaces
from letsencrypt.acme.jose import util
from acme.jose import errors
from acme.jose import interfaces
from acme.jose import util
CERT = M2Crypto.X509.load_cert(pkg_resources.resource_filename(
'letsencrypt.client.tests', os.path.join('testdata', 'cert.pem')))
'letsencrypt.tests', os.path.join('testdata', 'cert.pem')))
CSR = M2Crypto.X509.load_request(pkg_resources.resource_filename(
'letsencrypt.client.tests', os.path.join('testdata', 'csr.pem')))
'letsencrypt.tests', os.path.join('testdata', 'csr.pem')))
class FieldTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.json_util.Field."""
"""Tests for acme.jose.json_util.Field."""
def test_descriptors(self):
mock_value = mock.MagicMock()
@ -31,7 +31,7 @@ class FieldTest(unittest.TestCase):
def encoder(unused_value):
return 'e'
from letsencrypt.acme.jose.json_util import Field
from acme.jose.json_util import Field
field = Field('foo')
field = field.encoder(encoder)
@ -45,45 +45,45 @@ class FieldTest(unittest.TestCase):
class MockField(interfaces.JSONDeSerializable):
# pylint: disable=missing-docstring
def to_partial_json(self):
return 'foo'
return 'foo' # pragma: no cover
@classmethod
def from_json(cls, jobj):
pass
pass # pragma: no cover
mock_field = MockField()
from letsencrypt.acme.jose.json_util import Field
from acme.jose.json_util import Field
self.assertTrue(Field.default_encoder(mock_field) is mock_field)
# in particular...
self.assertNotEqual('foo', Field.default_encoder(mock_field))
def test_default_encoder_passthrough(self):
mock_value = mock.MagicMock()
from letsencrypt.acme.jose.json_util import Field
from acme.jose.json_util import Field
self.assertTrue(Field.default_encoder(mock_value) is mock_value)
def test_default_decoder_list_to_tuple(self):
from letsencrypt.acme.jose.json_util import Field
from acme.jose.json_util import Field
self.assertEqual((1, 2, 3), Field.default_decoder([1, 2, 3]))
def test_default_decoder_dict_to_frozendict(self):
from letsencrypt.acme.jose.json_util import Field
from acme.jose.json_util import Field
obj = Field.default_decoder({'x': 2})
self.assertTrue(isinstance(obj, util.frozendict))
self.assertEqual(obj, util.frozendict(x=2))
def test_default_decoder_passthrough(self):
mock_value = mock.MagicMock()
from letsencrypt.acme.jose.json_util import Field
from acme.jose.json_util import Field
self.assertTrue(Field.default_decoder(mock_value) is mock_value)
class JSONObjectWithFieldsTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.json_util.JSONObjectWithFields."""
"""Tests for acme.jose.json_util.JSONObjectWithFields."""
# pylint: disable=protected-access
def setUp(self):
from letsencrypt.acme.jose.json_util import JSONObjectWithFields
from letsencrypt.acme.jose.json_util import Field
from acme.jose.json_util import JSONObjectWithFields
from acme.jose.json_util import Field
class MockJSONObjectWithFields(JSONObjectWithFields):
# pylint: disable=invalid-name,missing-docstring,no-self-argument
@ -185,11 +185,11 @@ class DeEncodersTest(unittest.TestCase):
)
def test_decode_b64_jose_padding_error(self):
from letsencrypt.acme.jose.json_util import decode_b64jose
from acme.jose.json_util import decode_b64jose
self.assertRaises(errors.DeserializationError, decode_b64jose, 'x')
def test_decode_b64_jose_size(self):
from letsencrypt.acme.jose.json_util import decode_b64jose
from acme.jose.json_util import decode_b64jose
self.assertEqual('foo', decode_b64jose('Zm9v', size=3))
self.assertRaises(
errors.DeserializationError, decode_b64jose, 'Zm9v', size=2)
@ -197,44 +197,44 @@ class DeEncodersTest(unittest.TestCase):
errors.DeserializationError, decode_b64jose, 'Zm9v', size=4)
def test_decode_b64_jose_minimum_size(self):
from letsencrypt.acme.jose.json_util import decode_b64jose
from acme.jose.json_util import decode_b64jose
self.assertEqual('foo', decode_b64jose('Zm9v', size=3, minimum=True))
self.assertEqual('foo', decode_b64jose('Zm9v', size=2, minimum=True))
self.assertRaises(errors.DeserializationError, decode_b64jose,
'Zm9v', size=4, minimum=True)
def test_decode_hex16(self):
from letsencrypt.acme.jose.json_util import decode_hex16
from acme.jose.json_util import decode_hex16
self.assertEqual('foo', decode_hex16('666f6f'))
def test_decode_hex16_minimum_size(self):
from letsencrypt.acme.jose.json_util import decode_hex16
from acme.jose.json_util import decode_hex16
self.assertEqual('foo', decode_hex16('666f6f', size=3, minimum=True))
self.assertEqual('foo', decode_hex16('666f6f', size=2, minimum=True))
self.assertRaises(errors.DeserializationError, decode_hex16,
'666f6f', size=4, minimum=True)
def test_decode_hex16_odd_length(self):
from letsencrypt.acme.jose.json_util import decode_hex16
from acme.jose.json_util import decode_hex16
self.assertRaises(errors.DeserializationError, decode_hex16, 'x')
def test_encode_cert(self):
from letsencrypt.acme.jose.json_util import encode_cert
from acme.jose.json_util import encode_cert
self.assertEqual(self.b64_cert, encode_cert(CERT))
def test_decode_cert(self):
from letsencrypt.acme.jose.json_util import decode_cert
from acme.jose.json_util import decode_cert
cert = decode_cert(self.b64_cert)
self.assertTrue(isinstance(cert, util.ComparableX509))
self.assertEqual(cert, CERT)
self.assertRaises(errors.DeserializationError, decode_cert, '')
def test_encode_csr(self):
from letsencrypt.acme.jose.json_util import encode_csr
from acme.jose.json_util import encode_csr
self.assertEqual(self.b64_cert, encode_csr(CERT))
def test_decode_csr(self):
from letsencrypt.acme.jose.json_util import decode_csr
from acme.jose.json_util import decode_csr
csr = decode_csr(self.b64_csr)
self.assertTrue(isinstance(csr, util.ComparableX509))
self.assertEqual(csr, CSR)
@ -244,7 +244,7 @@ class DeEncodersTest(unittest.TestCase):
class TypedJSONObjectWithFieldsTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.jose.json_util import TypedJSONObjectWithFields
from acme.jose.json_util import TypedJSONObjectWithFields
# pylint: disable=missing-docstring,abstract-method
# pylint: disable=too-few-public-methods
@ -294,4 +294,4 @@ class TypedJSONObjectWithFieldsTest(unittest.TestCase):
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -13,9 +13,9 @@ from Crypto.Hash import SHA512
from Crypto.Signature import PKCS1_PSS
from Crypto.Signature import PKCS1_v1_5
from letsencrypt.acme.jose import errors
from letsencrypt.acme.jose import interfaces
from letsencrypt.acme.jose import jwk
from acme.jose import errors
from acme.jose import interfaces
from acme.jose import jwk
class JWA(interfaces.JSONDeSerializable): # pylint: disable=abstract-method

View file

@ -1,11 +1,11 @@
"""Tests for letsencrypt.acme.jose.jwa."""
"""Tests for acme.jose.jwa."""
import os
import pkg_resources
import unittest
from Crypto.PublicKey import RSA
from letsencrypt.acme.jose import errors
from acme.jose import errors
RSA256_KEY = RSA.importKey(pkg_resources.resource_string(
@ -17,19 +17,19 @@ RSA1024_KEY = RSA.importKey(pkg_resources.resource_string(
class JWASignatureTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.jwa.JWASignature."""
"""Tests for acme.jose.jwa.JWASignature."""
def setUp(self):
from letsencrypt.acme.jose.jwa import JWASignature
from acme.jose.jwa import JWASignature
class MockSig(JWASignature):
# pylint: disable=missing-docstring,too-few-public-methods
# pylint: disable=abstract-class-not-used
def sign(self, key, msg):
raise NotImplementedError()
raise NotImplementedError() # pragma: no cover
def verify(self, key, msg, sig):
raise NotImplementedError()
raise NotImplementedError() # pragma: no cover
# pylint: disable=invalid-name
self.Sig1 = MockSig('Sig1')
@ -48,15 +48,15 @@ class JWASignatureTest(unittest.TestCase):
self.assertEqual(self.Sig2.to_partial_json(), 'Sig2')
def test_from_json(self):
from letsencrypt.acme.jose.jwa import JWASignature
from letsencrypt.acme.jose.jwa import RS256
from acme.jose.jwa import JWASignature
from acme.jose.jwa import RS256
self.assertTrue(JWASignature.from_json('RS256') is RS256)
class JWAHSTest(unittest.TestCase): # pylint: disable=too-few-public-methods
def test_it(self):
from letsencrypt.acme.jose.jwa import HS256
from acme.jose.jwa import HS256
sig = (
"\xceR\xea\xcd\x94\xab\xcf\xfb\xe0\xacA.:\x1a'\x08i\xe2\xc4"
"\r\x85+\x0e\x85\xaeUZ\xd4\xb3\x97zO"
@ -69,19 +69,19 @@ class JWAHSTest(unittest.TestCase): # pylint: disable=too-few-public-methods
class JWARSTest(unittest.TestCase):
def test_sign_no_private_part(self):
from letsencrypt.acme.jose.jwa import RS256
from acme.jose.jwa import RS256
self.assertRaises(
errors.Error, RS256.sign, RSA512_KEY.publickey(), 'foo')
def test_sign_key_too_small(self):
from letsencrypt.acme.jose.jwa import RS256
from letsencrypt.acme.jose.jwa import PS256
from acme.jose.jwa import RS256
from acme.jose.jwa import PS256
self.assertRaises(errors.Error, RS256.sign, RSA256_KEY, 'foo')
self.assertRaises(errors.Error, PS256.sign, RSA256_KEY, 'foo')
self.assertRaises(errors.Error, PS256.sign, RSA512_KEY, 'foo')
def test_rs(self):
from letsencrypt.acme.jose.jwa import RS256
from acme.jose.jwa import RS256
sig = (
'|\xc6\xb2\xa4\xab(\x87\x99\xfa*:\xea\xf8\xa0N&}\x9f\x0f\xc0O'
'\xc6t\xa3\xe6\xfa\xbb"\x15Y\x80Y\xe0\x81\xb8\x88)\xba\x0c\x9c'
@ -95,11 +95,11 @@ class JWARSTest(unittest.TestCase):
self.assertFalse(RS256.verify(RSA512_KEY, 'foo', sig + '!') is False)
def test_ps(self):
from letsencrypt.acme.jose.jwa import PS256
from acme.jose.jwa import PS256
sig = PS256.sign(RSA1024_KEY, 'foo')
self.assertTrue(PS256.verify(RSA1024_KEY, 'foo', sig) is True)
self.assertTrue(PS256.verify(RSA1024_KEY, 'foo', sig + '!') is False)
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -4,10 +4,10 @@ import binascii
import Crypto.PublicKey.RSA
from letsencrypt.acme.jose import b64
from letsencrypt.acme.jose import errors
from letsencrypt.acme.jose import json_util
from letsencrypt.acme.jose import util
from acme.jose import b64
from acme.jose import errors
from acme.jose import json_util
from acme.jose import util
class JWK(json_util.TypedJSONObjectWithFields):

View file

@ -1,12 +1,12 @@
"""Tests for letsencrypt.acme.jose.jwk."""
"""Tests for acme.jose.jwk."""
import os
import pkg_resources
import unittest
from Crypto.PublicKey import RSA
from letsencrypt.acme.jose import errors
from letsencrypt.acme.jose import util
from acme.jose import errors
from acme.jose import util
RSA256_KEY = util.HashableRSAKey(RSA.importKey(pkg_resources.resource_string(
@ -16,10 +16,10 @@ RSA512_KEY = util.HashableRSAKey(RSA.importKey(pkg_resources.resource_string(
class JWKOctTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.jwk.JWKOct."""
"""Tests for acme.jose.jwk.JWKOct."""
def setUp(self):
from letsencrypt.acme.jose.jwk import JWKOct
from acme.jose.jwk import JWKOct
self.jwk = JWKOct(key='foo')
self.jobj = {'kty': 'oct', 'k': 'foo'}
@ -27,15 +27,15 @@ class JWKOctTest(unittest.TestCase):
self.assertEqual(self.jwk.to_partial_json(), self.jobj)
def test_from_json(self):
from letsencrypt.acme.jose.jwk import JWKOct
from acme.jose.jwk import JWKOct
self.assertEqual(self.jwk, JWKOct.from_json(self.jobj))
def test_from_json_hashable(self):
from letsencrypt.acme.jose.jwk import JWKOct
from acme.jose.jwk import JWKOct
hash(JWKOct.from_json(self.jobj))
def test_load(self):
from letsencrypt.acme.jose.jwk import JWKOct
from acme.jose.jwk import JWKOct
self.assertEqual(self.jwk, JWKOct.load('foo'))
def test_public(self):
@ -43,10 +43,10 @@ class JWKOctTest(unittest.TestCase):
class JWKRSATest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.jwk.JWKRSA."""
"""Tests for acme.jose.jwk.JWKRSA."""
def setUp(self):
from letsencrypt.acme.jose.jwk import JWKRSA
from acme.jose.jwk import JWKRSA
self.jwk256 = JWKRSA(key=RSA256_KEY.publickey())
self.jwk256_private = JWKRSA(key=RSA256_KEY)
self.jwk256json = {
@ -71,7 +71,7 @@ class JWKRSATest(unittest.TestCase):
self.assertNotEqual(self.jwk512, self.jwk256)
def test_load(self):
from letsencrypt.acme.jose.jwk import JWKRSA
from acme.jose.jwk import JWKRSA
self.assertEqual(
JWKRSA(key=util.HashableRSAKey(RSA256_KEY)), JWKRSA.load(
pkg_resources.resource_string(
@ -85,18 +85,18 @@ class JWKRSATest(unittest.TestCase):
self.assertEqual(self.jwk512.to_partial_json(), self.jwk512json)
def test_from_json(self):
from letsencrypt.acme.jose.jwk import JWK
from acme.jose.jwk import JWK
self.assertEqual(self.jwk256, JWK.from_json(self.jwk256json))
# TODO: fix schemata to allow RSA512
#self.assertEqual(self.jwk512, JWK.from_json(self.jwk512json))
def test_from_json_hashable(self):
from letsencrypt.acme.jose.jwk import JWK
from acme.jose.jwk import JWK
hash(JWK.from_json(self.jwk256json))
def test_from_json_non_schema_errors(self):
# valid against schema, but still failing
from letsencrypt.acme.jose.jwk import JWK
from acme.jose.jwk import JWK
self.assertRaises(errors.DeserializationError, JWK.from_json,
{'kty': 'RSA', 'e': 'AQAB', 'n': ''})
self.assertRaises(errors.DeserializationError, JWK.from_json,
@ -104,4 +104,4 @@ class JWKRSATest(unittest.TestCase):
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -5,12 +5,12 @@ import sys
import M2Crypto
from letsencrypt.acme.jose import b64
from letsencrypt.acme.jose import errors
from letsencrypt.acme.jose import json_util
from letsencrypt.acme.jose import jwa
from letsencrypt.acme.jose import jwk
from letsencrypt.acme.jose import util
from acme.jose import b64
from acme.jose import errors
from acme.jose import json_util
from acme.jose import jwa
from acme.jose import jwk
from acme.jose import util
class MediaType(object):
@ -103,9 +103,9 @@ class Header(json_util.JSONObjectWithFields):
.. todo:: Supports only "jwk" header parameter lookup.
:returns: (Public) key found in the header.
:rtype: :class:`letsencrypt.acme.jose.jwk.JWK`
:rtype: :class:`acme.jose.jwk.JWK`
:raises letsencrypt.acme.jose.errors.Error: if key could not be found
:raises acme.jose.errors.Error: if key could not be found
"""
if self.jwk is None:
@ -180,7 +180,7 @@ class Signature(json_util.JSONObjectWithFields):
"""Verify.
:param key: Key used for verification.
:type key: :class:`letsencrypt.acme.jose.jwk.JWK`
:type key: :class:`acme.jose.jwk.JWK`
"""
key = self.combined.find_key() if key is None else key
@ -195,7 +195,7 @@ class Signature(json_util.JSONObjectWithFields):
"""Sign.
:param key: Key for signature.
:type key: :class:`letsencrypt.acme.jose.jwk.JWK`
:type key: :class:`acme.jose.jwk.JWK`
"""
assert isinstance(key, alg.kty)
@ -241,8 +241,6 @@ class Signature(json_util.JSONObjectWithFields):
class JWS(json_util.JSONObjectWithFields):
"""JSON Web Signature.
from letsencrypt.acme.jose import interfaces
:ivar str payload: JWS Payload.
:ivar str signaturea: JWS Signatures.

View file

@ -1,4 +1,4 @@
"""Tests for letsencrypt.acme.jose.jws."""
"""Tests for acme.jose.jws."""
import base64
import os
import pkg_resources
@ -8,49 +8,49 @@ import Crypto.PublicKey.RSA
import M2Crypto
import mock
from letsencrypt.acme.jose import b64
from letsencrypt.acme.jose import errors
from letsencrypt.acme.jose import jwa
from letsencrypt.acme.jose import jwk
from letsencrypt.acme.jose import util
from acme.jose import b64
from acme.jose import errors
from acme.jose import jwa
from acme.jose import jwk
from acme.jose import util
CERT = util.ComparableX509(M2Crypto.X509.load_cert(
pkg_resources.resource_filename(
'letsencrypt.client.tests', 'testdata/cert.pem')))
'letsencrypt.tests', 'testdata/cert.pem')))
RSA512_KEY = Crypto.PublicKey.RSA.importKey(pkg_resources.resource_string(
__name__, os.path.join('testdata', 'rsa512_key.pem')))
class MediaTypeTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.jws.MediaType."""
"""Tests for acme.jose.jws.MediaType."""
def test_decode(self):
from letsencrypt.acme.jose.jws import MediaType
from acme.jose.jws import MediaType
self.assertEqual('application/app', MediaType.decode('application/app'))
self.assertEqual('application/app', MediaType.decode('app'))
self.assertRaises(
errors.DeserializationError, MediaType.decode, 'app;foo')
def test_encode(self):
from letsencrypt.acme.jose.jws import MediaType
from acme.jose.jws import MediaType
self.assertEqual('app', MediaType.encode('application/app'))
self.assertEqual('application/app;foo',
MediaType.encode('application/app;foo'))
class HeaderTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.jws.Header."""
"""Tests for acme.jose.jws.Header."""
def setUp(self):
from letsencrypt.acme.jose.jws import Header
from acme.jose.jws import Header
self.header1 = Header(jwk='foo')
self.header2 = Header(jwk='bar')
self.crit = Header(crit=('a', 'b'))
self.empty = Header()
def test_add_non_empty(self):
from letsencrypt.acme.jose.jws import Header
from acme.jose.jws import Header
self.assertEqual(Header(jwk='foo', crit=('a', 'b')),
self.header1 + self.crit)
@ -65,12 +65,12 @@ class HeaderTest(unittest.TestCase):
self.assertRaises(TypeError, self.header1.__add__, 'xxx')
def test_crit_decode_always_errors(self):
from letsencrypt.acme.jose.jws import Header
from acme.jose.jws import Header
self.assertRaises(errors.DeserializationError, Header.from_json,
{'crit': ['a', 'b']})
def test_x5c_decoding(self):
from letsencrypt.acme.jose.jws import Header
from acme.jose.jws import Header
header = Header(x5c=(CERT, CERT))
jobj = header.to_partial_json()
cert_b64 = base64.b64encode(CERT.as_der())
@ -86,30 +86,30 @@ class HeaderTest(unittest.TestCase):
class SignatureTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.jws.Signature."""
"""Tests for acme.jose.jws.Signature."""
def test_from_json(self):
from letsencrypt.acme.jose.jws import Header
from letsencrypt.acme.jose.jws import Signature
from acme.jose.jws import Header
from acme.jose.jws import Signature
self.assertEqual(
Signature(signature='foo', header=Header(alg=jwa.RS256)),
Signature.from_json(
{'signature': 'Zm9v', 'header': {'alg': 'RS256'}}))
def test_from_json_no_alg_error(self):
from letsencrypt.acme.jose.jws import Signature
from acme.jose.jws import Signature
self.assertRaises(errors.DeserializationError,
Signature.from_json, {'signature': 'foo'})
class JWSTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.jws.JWS."""
"""Tests for acme.jose.jws.JWS."""
def setUp(self):
self.privkey = jwk.JWKRSA(key=RSA512_KEY)
self.pubkey = self.privkey.public()
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
self.unprotected = JWS.sign(
payload='foo', key=self.privkey, alg=jwa.RS256)
self.protected = JWS.sign(
@ -140,7 +140,7 @@ class JWSTest(unittest.TestCase):
'_893n1zQjpim_eLS5J1F61lkvrCrCDErTEJnBGOGesJ72M7b6Ve1cAJA',
compact)
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
mixed = JWS.from_compact(compact)
self.assertNotEqual(self.mixed, mixed)
@ -148,7 +148,7 @@ class JWSTest(unittest.TestCase):
set(['alg']), set(mixed.signature.combined.not_omitted()))
def test_from_compact_missing_components(self):
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
self.assertRaises(errors.DeserializationError, JWS.from_compact, '.')
def test_json_omitempty(self):
@ -160,7 +160,7 @@ class JWSTest(unittest.TestCase):
unprotected_jobj['header'] = unprotected_jobj['header'].to_json()
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
self.assertEqual(JWS.from_json(protected_jobj), self.protected)
self.assertEqual(JWS.from_json(unprotected_jobj), self.unprotected)
@ -175,7 +175,7 @@ class JWSTest(unittest.TestCase):
jobj_from['header'] = jobj_from['header'].to_json()
self.assertEqual(self.mixed.to_partial_json(flat=True), jobj_to)
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
self.assertEqual(self.mixed, JWS.from_json(jobj_from))
def test_json_not_flat(self):
@ -187,16 +187,16 @@ class JWSTest(unittest.TestCase):
jobj_from['signatures'] = [jobj_to['signatures'][0].to_json()]
self.assertEqual(self.mixed.to_partial_json(flat=False), jobj_to)
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
self.assertEqual(self.mixed, JWS.from_json(jobj_from))
def test_from_json_mixed_flat(self):
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
self.assertRaises(errors.DeserializationError, JWS.from_json,
{'signatures': (), 'signature': 'foo'})
def test_from_json_hashable(self):
from letsencrypt.acme.jose.jws import JWS
from acme.jose.jws import JWS
hash(JWS.from_json(self.mixed.to_json()))
@ -207,14 +207,14 @@ class CLITest(unittest.TestCase):
__name__, os.path.join('testdata', 'rsa512_key.pem'))
def test_unverified(self):
from letsencrypt.acme.jose.jws import CLI
from acme.jose.jws import CLI
with mock.patch('sys.stdin') as sin:
sin.read.return_value = '{"payload": "foo", "signature": "xxx"}'
with mock.patch('sys.stdout'):
self.assertEqual(-1, CLI.run(['verify']))
def test_json(self):
from letsencrypt.acme.jose.jws import CLI
from acme.jose.jws import CLI
with mock.patch('sys.stdin') as sin:
sin.read.return_value = 'foo'
@ -225,7 +225,7 @@ class CLITest(unittest.TestCase):
self.assertEqual(0, CLI.run(['verify']))
def test_compact(self):
from letsencrypt.acme.jose.jws import CLI
from acme.jose.jws import CLI
with mock.patch('sys.stdin') as sin:
sin.read.return_value = 'foo'
@ -238,4 +238,4 @@ class CLITest(unittest.TestCase):
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -4,7 +4,7 @@ The following command has been used to generate test keys:
and for the CSR:
python -c from 'letsencrypt.client.crypto_util import make_csr;
python -c from 'letsencrypt.crypto_util import make_csr;
import pkg_resources; open("csr2.pem",
"w").write(make_csr(pkg_resources.resource_string("letsencrypt.client.tests",
"w").write(make_csr(pkg_resources.resource_string("letsencrypt.tests",
"testdata/rsa512_key.pem"), ["example2.com"])[0])'

View file

@ -1,4 +1,4 @@
"""Tests for letsencrypt.acme.jose.util."""
"""Tests for acme.jose.util."""
import functools
import os
import pkg_resources
@ -8,10 +8,10 @@ import Crypto.PublicKey.RSA
class HashableRSAKeyTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.util.HashableRSAKey."""
"""Tests for acme.jose.util.HashableRSAKey."""
def setUp(self):
from letsencrypt.acme.jose.util import HashableRSAKey
from acme.jose.util import HashableRSAKey
self.key = HashableRSAKey(Crypto.PublicKey.RSA.importKey(
pkg_resources.resource_string(
__name__, os.path.join('testdata', 'rsa256_key.pem'))))
@ -28,17 +28,17 @@ class HashableRSAKeyTest(unittest.TestCase):
self.assertTrue(isinstance(hash(self.key), int))
def test_publickey(self):
from letsencrypt.acme.jose.util import HashableRSAKey
from acme.jose.util import HashableRSAKey
self.assertTrue(isinstance(self.key.publickey(), HashableRSAKey))
class ImmutableMapTest(unittest.TestCase):
"""Tests for letsencrypt.acme.jose.util.ImmutableMap."""
"""Tests for acme.jose.util.ImmutableMap."""
def setUp(self):
# pylint: disable=invalid-name,too-few-public-methods
# pylint: disable=missing-docstring
from letsencrypt.acme.jose.util import ImmutableMap
from acme.jose.util import ImmutableMap
class A(ImmutableMap):
__slots__ = ('x', 'y')
@ -101,18 +101,18 @@ class ImmutableMapTest(unittest.TestCase):
class frozendictTest(unittest.TestCase): # pylint: disable=invalid-name
"""Tests for letsencrypt.acme.jose.util.frozendict."""
"""Tests for acme.jose.util.frozendict."""
def setUp(self):
from letsencrypt.acme.jose.util import frozendict
from acme.jose.util import frozendict
self.fdict = frozendict(x=1, y='2')
def test_init_dict(self):
from letsencrypt.acme.jose.util import frozendict
from acme.jose.util import frozendict
self.assertEqual(self.fdict, frozendict({'x': 1, 'y': '2'}))
def test_init_other_raises_type_error(self):
from letsencrypt.acme.jose.util import frozendict
from acme.jose.util import frozendict
# specifically fail for generators...
self.assertRaises(TypeError, frozendict, {'a': 'b'}.iteritems())
@ -137,4 +137,4 @@ class frozendictTest(unittest.TestCase): # pylint: disable=invalid-name
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -22,11 +22,11 @@
"""
import jsonschema
from letsencrypt.acme import challenges
from letsencrypt.acme import errors
from letsencrypt.acme import jose
from letsencrypt.acme import other
from letsencrypt.acme import util
from acme import challenges
from acme import errors
from acme import jose
from acme import other
from acme import util
class Message(jose.TypedJSONObjectWithFields):
@ -41,7 +41,7 @@ class Message(jose.TypedJSONObjectWithFields):
Subclasses must overrride it with a value that is acceptable by
:func:`jsonschema.validate`, most probably using
:func:`letsencrypt.acme.util.load_schema`.
:func:`acme.util.load_schema`.
"""
@ -53,10 +53,10 @@ class Message(jose.TypedJSONObjectWithFields):
:param jobj: JSON object.
:raises letsencrypt.acme.errors.SchemaValidationError: if the input
:raises acme.errors.SchemaValidationError: if the input
JSON object could not be validated against JSON schema specified
in :attr:`schema`.
:raises letsencrypt.acme.jose.errors.DeserializationError: for any
:raises acme.jose.errors.DeserializationError: for any
other generic error in decoding.
:returns: instance of the class
@ -79,7 +79,7 @@ class Challenge(Message):
:ivar str nonce: Random data, **not** base64-encoded.
:ivar list challenges: List of
:class:`~letsencrypt.acme.challenges.Challenge` objects.
:class:`~acme.challenges.Challenge` objects.
.. todo::
1. can challenges contain two challenges of the same type?
@ -121,7 +121,7 @@ class ChallengeRequest(Message):
class Authorization(Message):
"""ACME "authorization" message.
:ivar jwk: :class:`letsencrypt.acme.jose.JWK`
:ivar jwk: :class:`acme.jose.JWK`
"""
typ = "authorization"
@ -139,8 +139,8 @@ class AuthorizationRequest(Message):
:ivar str nonce: Random data from the corresponding
:attr:`Challenge.nonce`, **not** base64-encoded.
:ivar list responses: List of completed challenges (
:class:`letsencrypt.acme.challenges.ChallengeResponse`).
:ivar signature: Signature (:class:`letsencrypt.acme.other.Signature`).
:class:`acme.challenges.ChallengeResponse`).
:ivar signature: Signature (:class:`acme.other.Signature`).
"""
typ = "authorizationRequest"
@ -184,7 +184,7 @@ class AuthorizationRequest(Message):
"""Verify signature.
.. warning:: Caller must check that the public key encoded in the
:attr:`signature`'s :class:`letsencrypt.acme.jose.JWK` object
:attr:`signature`'s :class:`acme.jose.JWK` object
is the correct key for a given context.
:param str name: Hostname
@ -202,10 +202,10 @@ class Certificate(Message):
"""ACME "certificate" message.
:ivar certificate: The certificate (:class:`M2Crypto.X509.X509`
wrapped in :class:`letsencrypt.acme.util.ComparableX509`).
wrapped in :class:`acme.util.ComparableX509`).
:ivar list chain: Chain of certificates (:class:`M2Crypto.X509.X509`
wrapped in :class:`letsencrypt.acme.util.ComparableX509` ).
wrapped in :class:`acme.util.ComparableX509` ).
"""
typ = "certificate"
@ -230,8 +230,8 @@ class CertificateRequest(Message):
"""ACME "certificateRequest" message.
:ivar csr: Certificate Signing Request (:class:`M2Crypto.X509.Request`
wrapped in :class:`letsencrypt.acme.util.ComparableX509`.
:ivar signature: Signature (:class:`letsencrypt.acme.other.Signature`).
wrapped in :class:`acme.util.ComparableX509`.
:ivar signature: Signature (:class:`acme.other.Signature`).
"""
typ = "certificateRequest"
@ -262,7 +262,7 @@ class CertificateRequest(Message):
"""Verify signature.
.. warning:: Caller must check that the public key encoded in the
:attr:`signature`'s :class:`letsencrypt.acme.jose.JWK` object
:attr:`signature`'s :class:`acme.jose.JWK` object
is the correct key for a given context.
:returns: True iff ``signature`` can be verified, False otherwise.
@ -316,8 +316,8 @@ class RevocationRequest(Message):
"""ACME "revocationRequest" message.
:ivar certificate: Certificate (:class:`M2Crypto.X509.X509`
wrapped in :class:`letsencrypt.acme.util.ComparableX509`).
:ivar signature: Signature (:class:`letsencrypt.acme.other.Signature`).
wrapped in :class:`acme.util.ComparableX509`).
:ivar signature: Signature (:class:`acme.other.Signature`).
"""
typ = "revocationRequest"
@ -348,7 +348,7 @@ class RevocationRequest(Message):
"""Verify signature.
.. warning:: Caller must check that the public key encoded in the
:attr:`signature`'s :class:`letsencrypt.acme.jose.JWK` object
:attr:`signature`'s :class:`acme.jose.JWK` object
is the correct key for a given context.
:returns: True iff ``signature`` can be verified, False otherwise.

View file

@ -1,7 +1,7 @@
"""ACME protocol messages."""
from letsencrypt.acme import challenges
from letsencrypt.acme import fields
from letsencrypt.acme import jose
from acme import challenges
from acme import fields
from acme import jose
class Error(jose.JSONObjectWithFields, Exception):
@ -46,6 +46,11 @@ class Error(jose.JSONObjectWithFields, Exception):
"""Hardcoded error description based on its type."""
return self.ERROR_TYPE_DESCRIPTIONS[self.typ]
def __str__(self):
if self.typ is not None:
return ' :: '.join([self.typ, self.description, self.detail])
else:
return str(self.detail)
class _Constant(jose.JSONDeSerializable):
"""ACME constant."""
@ -96,7 +101,7 @@ IDENTIFIER_FQDN = IdentifierType('dns') # IdentifierDNS in Boulder
class Identifier(jose.JSONObjectWithFields):
"""ACME identifier.
:ivar letsencrypt.acme.messages2.IdentifierType typ:
:ivar acme.messages2.IdentifierType typ:
"""
typ = jose.Field('type', decoder=IdentifierType.from_json)
@ -106,7 +111,7 @@ class Identifier(jose.JSONObjectWithFields):
class Resource(jose.ImmutableMap):
"""ACME Resource.
:ivar letsencrypt.acme.messages2.ResourceBody body: Resource body.
:ivar acme.messages2.ResourceBody body: Resource body.
:ivar str uri: Location of the resource.
"""
@ -120,7 +125,7 @@ class ResourceBody(jose.JSONObjectWithFields):
class RegistrationResource(Resource):
"""Registration Resource.
:ivar letsencrypt.acme.messages2.Registration body:
:ivar acme.messages2.Registration body:
:ivar str new_authzr_uri: URI found in the 'next' ``Link`` header
:ivar str terms_of_service: URL for the CA TOS.
@ -131,7 +136,7 @@ class RegistrationResource(Resource):
class Registration(ResourceBody):
"""Registration Resource Body.
:ivar letsencrypt.acme.jose.jwk.JWK key: Public key.
:ivar acme.jose.jwk.JWK key: Public key.
:ivar tuple contact: Contact information following ACME spec
"""
@ -146,7 +151,7 @@ class Registration(ResourceBody):
class ChallengeResource(Resource, jose.JSONObjectWithFields):
"""Challenge Resource.
:ivar letsencrypt.acme.messages2.ChallengeBody body:
:ivar acme.messages2.ChallengeBody body:
:ivar str authzr_uri: URI found in the 'up' ``Link`` header.
"""
@ -168,10 +173,10 @@ class ChallengeBody(ResourceBody):
such as ``challb`` to distinguish instances of this class from
``achall``.
:ivar letsencrypt.acme.challenges.Challenge: Wrapped challenge.
:ivar acme.challenges.Challenge: Wrapped challenge.
Conveniently, all challenge fields are proxied, i.e. you can
call ``challb.x`` to get ``challb.chall.x`` contents.
:ivar letsencrypt.acme.messages2.Status status:
:ivar acme.messages2.Status status:
:ivar datetime.datetime validated:
"""
@ -198,7 +203,7 @@ class ChallengeBody(ResourceBody):
class AuthorizationResource(Resource):
"""Authorization Resource.
:ivar letsencrypt.acme.messages2.Authorization body:
:ivar acme.messages2.Authorization body:
:ivar str new_cert_uri: URI found in the 'next' ``Link`` header
"""
@ -208,13 +213,13 @@ class AuthorizationResource(Resource):
class Authorization(ResourceBody):
"""Authorization Resource Body.
:ivar letsencrypt.acme.messages2.Identifier identifier:
:ivar acme.messages2.Identifier identifier:
:ivar list challenges: `list` of `.ChallengeBody`
:ivar tuple combinations: Challenge combinations (`tuple` of `tuple`
of `int`, as opposed to `list` of `list` from the spec).
:ivar letsencrypt.acme.jose.jwk.JWK key: Public key.
:ivar acme.jose.jwk.JWK key: Public key.
:ivar tuple contact:
:ivar letsencrypt.acme.messages2.Status status:
:ivar acme.messages2.Status status:
:ivar datetime.datetime expires:
"""
@ -247,7 +252,7 @@ class Authorization(ResourceBody):
class CertificateRequest(jose.JSONObjectWithFields):
"""ACME new-cert request.
:ivar letsencrypt.acme.jose.util.ComparableX509 csr:
:ivar acme.jose.util.ComparableX509 csr:
`M2Crypto.X509.Request` wrapped in `.ComparableX509`
:ivar tuple authorizations: `tuple` of URIs (`str`)
@ -259,7 +264,7 @@ class CertificateRequest(jose.JSONObjectWithFields):
class CertificateResource(Resource):
"""Certificate Resource.
:ivar letsencrypt.acme.jose.util.ComparableX509 body:
:ivar acme.jose.util.ComparableX509 body:
`M2Crypto.X509.X509` wrapped in `.ComparableX509`
:ivar str cert_chain_uri: URI found in the 'up' ``Link`` header
:ivar tuple authzrs: `tuple` of `AuthorizationResource`.

View file

@ -1,4 +1,4 @@
"""Tests for letsencrypt.acme.messages2."""
"""Tests for acme.messages2."""
import datetime
import os
import pkg_resources
@ -8,19 +8,19 @@ import mock
import pytz
from Crypto.PublicKey import RSA
from letsencrypt.acme import challenges
from letsencrypt.acme import jose
from acme import challenges
from acme import jose
KEY = jose.util.HashableRSAKey(RSA.importKey(pkg_resources.resource_string(
'letsencrypt.acme.jose', os.path.join('testdata', 'rsa512_key.pem'))))
'acme.jose', os.path.join('testdata', 'rsa512_key.pem'))))
class ErrorTest(unittest.TestCase):
"""Tests for letsencrypt.acme.messages2.Error."""
"""Tests for acme.messages2.Error."""
def setUp(self):
from letsencrypt.acme.messages2 import Error
from acme.messages2 import Error
self.error = Error(detail='foo', typ='malformed')
def test_typ_prefix(self):
@ -31,14 +31,14 @@ class ErrorTest(unittest.TestCase):
'malformed', self.error.from_json(self.error.to_partial_json()).typ)
def test_typ_decoder_missing_prefix(self):
from letsencrypt.acme.messages2 import Error
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'})
def test_typ_decoder_not_recognized(self):
from letsencrypt.acme.messages2 import Error
from acme.messages2 import Error
self.assertRaises(jose.DeserializationError, Error.from_json,
{'detail': 'foo', 'type': 'urn:acme:error:baz'})
@ -47,15 +47,21 @@ class ErrorTest(unittest.TestCase):
'The request message was malformed', self.error.description)
def test_from_json_hashable(self):
from letsencrypt.acme.messages2 import Error
from acme.messages2 import Error
hash(Error.from_json(self.error.to_json()))
def test_str(self):
self.assertEqual(
'malformed :: The request message was malformed :: foo',
str(self.error))
self.assertEqual('foo', str(self.error.update(typ=None)))
class ConstantTest(unittest.TestCase):
"""Tests for letsencrypt.acme.messages2._Constant."""
"""Tests for acme.messages2._Constant."""
def setUp(self):
from letsencrypt.acme.messages2 import _Constant
from acme.messages2 import _Constant
class MockConstant(_Constant): # pylint: disable=missing-docstring
POSSIBLE_NAMES = {}
@ -88,7 +94,7 @@ class ConstantTest(unittest.TestCase):
self.assertFalse(self.const_a != const_a_prime)
class RegistrationTest(unittest.TestCase):
"""Tests for letsencrypt.acme.messages2.Registration."""
"""Tests for acme.messages2.Registration."""
def setUp(self):
key = jose.jwk.JWKRSA(key=KEY.publickey())
@ -96,7 +102,7 @@ class RegistrationTest(unittest.TestCase):
recovery_token = 'XYZ'
agreement = 'https://letsencrypt.org/terms'
from letsencrypt.acme.messages2 import Registration
from acme.messages2 import Registration
self.reg = Registration(
key=key, contact=contact, recovery_token=recovery_token,
agreement=agreement)
@ -114,31 +120,31 @@ class RegistrationTest(unittest.TestCase):
self.assertEqual(self.jobj_to, self.reg.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.messages2 import Registration
from acme.messages2 import Registration
self.assertEqual(self.reg, Registration.from_json(self.jobj_from))
def test_from_json_hashable(self):
from letsencrypt.acme.messages2 import Registration
from acme.messages2 import Registration
hash(Registration.from_json(self.jobj_from))
class ChallengeResourceTest(unittest.TestCase):
"""Tests for letsencrypt.acme.messages2.ChallengeResource."""
"""Tests for acme.messages2.ChallengeResource."""
def test_uri(self):
from letsencrypt.acme.messages2 import ChallengeResource
from acme.messages2 import ChallengeResource
self.assertEqual('http://challb', ChallengeResource(body=mock.MagicMock(
uri='http://challb'), authzr_uri='http://authz').uri)
class ChallengeBodyTest(unittest.TestCase):
"""Tests for letsencrypt.acme.messages2.ChallengeBody."""
"""Tests for acme.messages2.ChallengeBody."""
def setUp(self):
self.chall = challenges.DNS(token='foo')
from letsencrypt.acme.messages2 import ChallengeBody
from letsencrypt.acme.messages2 import STATUS_VALID
from acme.messages2 import ChallengeBody
from acme.messages2 import STATUS_VALID
self.status = STATUS_VALID
self.challb = ChallengeBody(
uri='http://challb', chall=self.chall, status=self.status)
@ -156,20 +162,23 @@ class ChallengeBodyTest(unittest.TestCase):
self.assertEqual(self.jobj_to, self.challb.to_partial_json())
def test_from_json(self):
from letsencrypt.acme.messages2 import ChallengeBody
from acme.messages2 import ChallengeBody
self.assertEqual(self.challb, ChallengeBody.from_json(self.jobj_from))
def test_from_json_hashable(self):
from letsencrypt.acme.messages2 import ChallengeBody
from acme.messages2 import ChallengeBody
hash(ChallengeBody.from_json(self.jobj_from))
def test_proxy(self):
self.assertEqual('foo', self.challb.token)
class AuthorizationTest(unittest.TestCase):
"""Tests for letsencrypt.acme.messages2.Authorization."""
"""Tests for acme.messages2.Authorization."""
def setUp(self):
from letsencrypt.acme.messages2 import ChallengeBody
from letsencrypt.acme.messages2 import STATUS_VALID
from acme.messages2 import ChallengeBody
from acme.messages2 import STATUS_VALID
self.challbs = (
ChallengeBody(
uri='http://challb1', status=STATUS_VALID,
@ -181,9 +190,9 @@ class AuthorizationTest(unittest.TestCase):
)
combinations = ((0, 2), (1, 2))
from letsencrypt.acme.messages2 import Authorization
from letsencrypt.acme.messages2 import Identifier
from letsencrypt.acme.messages2 import IDENTIFIER_FQDN
from acme.messages2 import Authorization
from acme.messages2 import Identifier
from acme.messages2 import IDENTIFIER_FQDN
identifier = Identifier(typ=IDENTIFIER_FQDN, value='example.com')
self.authz = Authorization(
identifier=identifier, combinations=combinations,
@ -196,11 +205,11 @@ class AuthorizationTest(unittest.TestCase):
}
def test_from_json(self):
from letsencrypt.acme.messages2 import Authorization
from acme.messages2 import Authorization
Authorization.from_json(self.jobj_from)
def test_from_json_hashable(self):
from letsencrypt.acme.messages2 import Authorization
from acme.messages2 import Authorization
hash(Authorization.from_json(self.jobj_from))
def test_resolved_combinations(self):
@ -211,10 +220,10 @@ class AuthorizationTest(unittest.TestCase):
class RevocationTest(unittest.TestCase):
"""Tests for letsencrypt.acme.messages2.RevocationTest."""
"""Tests for acme.messages2.RevocationTest."""
def setUp(self):
from letsencrypt.acme.messages2 import Revocation
from acme.messages2 import Revocation
self.rev_now = Revocation(authorizations=(), revoke=Revocation.NOW)
self.rev_date = Revocation(authorizations=(), revoke=datetime.datetime(
2015, 3, 27, tzinfo=pytz.utc))
@ -223,7 +232,7 @@ class RevocationTest(unittest.TestCase):
'revoke': '2015-03-27T00:00:00Z'}
def test_revoke_decoder(self):
from letsencrypt.acme.messages2 import Revocation
from acme.messages2 import Revocation
self.assertEqual(self.rev_now, Revocation.from_json(self.jobj_now))
self.assertEqual(self.rev_date, Revocation.from_json(self.jobj_date))
@ -232,9 +241,9 @@ class RevocationTest(unittest.TestCase):
self.assertEqual(self.jobj_date, self.rev_date.to_partial_json())
def test_from_json_hashable(self):
from letsencrypt.acme.messages2 import Revocation
from acme.messages2 import Revocation
hash(Revocation.from_json(self.rev_now.to_json()))
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -1,4 +1,4 @@
"""Tests for letsencrypt.acme.messages."""
"""Tests for acme.messages."""
import os
import pkg_resources
import unittest
@ -6,32 +6,32 @@ import unittest
import Crypto.PublicKey.RSA
import M2Crypto
from letsencrypt.acme import challenges
from letsencrypt.acme import errors
from letsencrypt.acme import jose
from letsencrypt.acme import other
from acme import challenges
from acme import errors
from acme import jose
from acme import other
KEY = jose.HashableRSAKey(Crypto.PublicKey.RSA.importKey(
pkg_resources.resource_string(
'letsencrypt.acme.jose', os.path.join('testdata', 'rsa512_key.pem'))))
'acme.jose', os.path.join('testdata', 'rsa512_key.pem'))))
CERT = jose.ComparableX509(M2Crypto.X509.load_cert(
pkg_resources.resource_filename(
'letsencrypt.client.tests', os.path.join('testdata', 'cert.pem'))))
'letsencrypt.tests', os.path.join('testdata', 'cert.pem'))))
CSR = jose.ComparableX509(M2Crypto.X509.load_request(
pkg_resources.resource_filename(
'letsencrypt.client.tests', os.path.join('testdata', 'csr.pem'))))
'letsencrypt.tests', os.path.join('testdata', 'csr.pem'))))
CSR2 = jose.ComparableX509(M2Crypto.X509.load_request(
pkg_resources.resource_filename(
'letsencrypt.acme.jose', os.path.join('testdata', 'csr2.pem'))))
'acme.jose', os.path.join('testdata', 'csr2.pem'))))
class MessageTest(unittest.TestCase):
"""Tests for letsencrypt.acme.messages.Message."""
"""Tests for acme.messages.Message."""
def setUp(self):
# pylint: disable=missing-docstring,too-few-public-methods
from letsencrypt.acme.messages import Message
from acme.messages import Message
class MockParentMessage(Message):
# pylint: disable=abstract-method
@ -69,7 +69,7 @@ class ChallengeTest(unittest.TestCase):
)
combinations = ((0, 2), (1, 2))
from letsencrypt.acme.messages import Challenge
from acme.messages import Challenge
self.msg = Challenge(
session_id='aefoGaavieG9Wihuk2aufai3aeZ5EeW4',
nonce='\xec\xd6\xf2oYH\xeb\x13\xd5#q\xe0\xdd\xa2\x92\xa9',
@ -107,14 +107,14 @@ class ChallengeTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg_to)
def test_from_json(self):
from letsencrypt.acme.messages import Challenge
from acme.messages import Challenge
self.assertEqual(Challenge.from_json(self.jmsg_from), self.msg)
def test_json_without_optionals(self):
del self.jmsg_from['combinations']
del self.jmsg_to['combinations']
from letsencrypt.acme.messages import Challenge
from acme.messages import Challenge
msg = Challenge.from_json(self.jmsg_from)
self.assertEqual(msg.combinations, ())
@ -124,7 +124,7 @@ class ChallengeTest(unittest.TestCase):
class ChallengeRequestTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.messages import ChallengeRequest
from acme.messages import ChallengeRequest
self.msg = ChallengeRequest(identifier='example.com')
self.jmsg = {
@ -136,7 +136,7 @@ class ChallengeRequestTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg)
def test_from_json(self):
from letsencrypt.acme.messages import ChallengeRequest
from acme.messages import ChallengeRequest
self.assertEqual(ChallengeRequest.from_json(self.jmsg), self.msg)
@ -145,7 +145,7 @@ class AuthorizationTest(unittest.TestCase):
def setUp(self):
jwk = jose.JWKRSA(key=KEY.publickey())
from letsencrypt.acme.messages import Authorization
from acme.messages import Authorization
self.msg = Authorization(recovery_token='tok', jwk=jwk,
identifier='example.com')
@ -162,7 +162,7 @@ class AuthorizationTest(unittest.TestCase):
def test_from_json(self):
self.jmsg['jwk'] = self.jmsg['jwk'].to_partial_json()
from letsencrypt.acme.messages import Authorization
from acme.messages import Authorization
self.assertEqual(Authorization.from_json(self.jmsg), self.msg)
def test_json_without_optionals(self):
@ -170,7 +170,7 @@ class AuthorizationTest(unittest.TestCase):
del self.jmsg['identifier']
del self.jmsg['jwk']
from letsencrypt.acme.messages import Authorization
from acme.messages import Authorization
msg = Authorization.from_json(self.jmsg)
self.assertTrue(msg.recovery_token is None)
@ -196,7 +196,7 @@ class AuthorizationRequestTest(unittest.TestCase):
'\x92\xe9\x96\x11\xc2\xefx\x0bR',
nonce='\xab?\x08o\xe6\x81$\x9f\xa1\xc9\x025\x1c\x1b\xa5+')
from letsencrypt.acme.messages import AuthorizationRequest
from acme.messages import AuthorizationRequest
self.msg = AuthorizationRequest(
session_id='aefoGaavieG9Wihuk2aufai3aeZ5EeW4',
nonce='\xec\xd6\xf2oYH\xeb\x13\xd5#q\xe0\xdd\xa2\x92\xa9',
@ -226,7 +226,7 @@ class AuthorizationRequestTest(unittest.TestCase):
}
def test_create(self):
from letsencrypt.acme.messages import AuthorizationRequest
from acme.messages import AuthorizationRequest
self.assertEqual(self.msg, AuthorizationRequest.create(
name='example.com', key=KEY, responses=self.responses,
nonce='\xec\xd6\xf2oYH\xeb\x13\xd5#q\xe0\xdd\xa2\x92\xa9',
@ -241,7 +241,7 @@ class AuthorizationRequestTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg_to)
def test_from_json(self):
from letsencrypt.acme.messages import AuthorizationRequest
from acme.messages import AuthorizationRequest
self.assertEqual(
self.msg, AuthorizationRequest.from_json(self.jmsg_from))
@ -249,7 +249,7 @@ class AuthorizationRequestTest(unittest.TestCase):
del self.jmsg_from['contact']
del self.jmsg_to['contact']
from letsencrypt.acme.messages import AuthorizationRequest
from acme.messages import AuthorizationRequest
msg = AuthorizationRequest.from_json(self.jmsg_from)
self.assertEqual(msg.contact, ())
@ -261,7 +261,7 @@ class CertificateTest(unittest.TestCase):
def setUp(self):
refresh = 'https://example.com/refresh/Dr8eAwTVQfSS/'
from letsencrypt.acme.messages import Certificate
from acme.messages import Certificate
self.msg = Certificate(
certificate=CERT, chain=(CERT,), refresh=refresh)
@ -279,7 +279,7 @@ class CertificateTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg_to)
def test_from_json(self):
from letsencrypt.acme.messages import Certificate
from acme.messages import Certificate
self.assertEqual(Certificate.from_json(self.jmsg_from), self.msg)
def test_json_without_optionals(self):
@ -288,7 +288,7 @@ class CertificateTest(unittest.TestCase):
del self.jmsg_to['chain']
del self.jmsg_to['refresh']
from letsencrypt.acme.messages import Certificate
from acme.messages import Certificate
msg = Certificate.from_json(self.jmsg_from)
self.assertEqual(msg.chain, ())
@ -307,7 +307,7 @@ class CertificateRequestTest(unittest.TestCase):
'k\xfe\xee\xb4\xe4\xc8\x05\x9a\x08\xa7',
nonce='\xec\xd6\xf2oYH\xeb\x13\xd5#q\xe0\xdd\xa2\x92\xa9')
from letsencrypt.acme.messages import CertificateRequest
from acme.messages import CertificateRequest
self.msg = CertificateRequest(csr=CSR, signature=signature)
self.jmsg_to = {
@ -319,7 +319,7 @@ class CertificateRequestTest(unittest.TestCase):
self.jmsg_from['signature'] = self.jmsg_from['signature'].to_json()
def test_create(self):
from letsencrypt.acme.messages import CertificateRequest
from acme.messages import CertificateRequest
self.assertEqual(self.msg, CertificateRequest.create(
csr=CSR, key=KEY,
sig_nonce='\xec\xd6\xf2oYH\xeb\x13\xd5#q\xe0\xdd\xa2\x92\xa9'))
@ -331,14 +331,14 @@ class CertificateRequestTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg_to)
def test_from_json(self):
from letsencrypt.acme.messages import CertificateRequest
from acme.messages import CertificateRequest
self.assertEqual(self.msg, CertificateRequest.from_json(self.jmsg_from))
class DeferTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.messages import Defer
from acme.messages import Defer
self.msg = Defer(
token='O7-s9MNq1siZHlgrMzi9_A', interval=60,
message='Warming up the HSM')
@ -354,14 +354,14 @@ class DeferTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg)
def test_from_json(self):
from letsencrypt.acme.messages import Defer
from acme.messages import Defer
self.assertEqual(Defer.from_json(self.jmsg), self.msg)
def test_json_without_optionals(self):
del self.jmsg['interval']
del self.jmsg['message']
from letsencrypt.acme.messages import Defer
from acme.messages import Defer
msg = Defer.from_json(self.jmsg)
self.assertTrue(msg.interval is None)
@ -372,7 +372,7 @@ class DeferTest(unittest.TestCase):
class ErrorTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.messages import Error
from acme.messages import Error
self.msg = Error(
error='badCSR', message='RSA keys must be at least 2048 bits long',
more_info='https://ca.example.com/documentation/csr-requirements')
@ -388,14 +388,14 @@ class ErrorTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg)
def test_from_json(self):
from letsencrypt.acme.messages import Error
from acme.messages import Error
self.assertEqual(Error.from_json(self.jmsg), self.msg)
def test_json_without_optionals(self):
del self.jmsg['message']
del self.jmsg['moreInfo']
from letsencrypt.acme.messages import Error
from acme.messages import Error
msg = Error.from_json(self.jmsg)
self.assertTrue(msg.message is None)
@ -406,7 +406,7 @@ class ErrorTest(unittest.TestCase):
class RevocationTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.messages import Revocation
from acme.messages import Revocation
self.msg = Revocation()
self.jmsg = {'type': 'revocation'}
@ -414,7 +414,7 @@ class RevocationTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg)
def test_from_json(self):
from letsencrypt.acme.messages import Revocation
from acme.messages import Revocation
self.assertEqual(Revocation.from_json(self.jmsg), self.msg)
@ -431,7 +431,7 @@ class RevocationRequestTest(unittest.TestCase):
's\xd9\xd0\xe7',
nonce=self.sig_nonce)
from letsencrypt.acme.messages import RevocationRequest
from acme.messages import RevocationRequest
self.msg = RevocationRequest(certificate=CERT, signature=signature)
self.jmsg_to = {
@ -443,7 +443,7 @@ class RevocationRequestTest(unittest.TestCase):
self.jmsg_from['signature'] = self.jmsg_from['signature'].to_json()
def test_create(self):
from letsencrypt.acme.messages import RevocationRequest
from acme.messages import RevocationRequest
self.assertEqual(self.msg, RevocationRequest.create(
certificate=CERT, key=KEY, sig_nonce=self.sig_nonce))
@ -454,14 +454,14 @@ class RevocationRequestTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg_to)
def test_from_json(self):
from letsencrypt.acme.messages import RevocationRequest
from acme.messages import RevocationRequest
self.assertEqual(self.msg, RevocationRequest.from_json(self.jmsg_from))
class StatusRequestTest(unittest.TestCase):
def setUp(self):
from letsencrypt.acme.messages import StatusRequest
from acme.messages import StatusRequest
self.msg = StatusRequest(token=u'O7-s9MNq1siZHlgrMzi9_A')
self.jmsg = {
'type': 'statusRequest',
@ -472,9 +472,9 @@ class StatusRequestTest(unittest.TestCase):
self.assertEqual(self.msg.to_partial_json(), self.jmsg)
def test_from_json(self):
from letsencrypt.acme.messages import StatusRequest
from acme.messages import StatusRequest
self.assertEqual(StatusRequest.from_json(self.jmsg), self.msg)
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -5,7 +5,7 @@ import logging
import Crypto.Random
import Crypto.PublicKey.RSA
from letsencrypt.acme import jose
from acme import jose
class Signature(jose.JSONObjectWithFields):

View file

@ -1,21 +1,21 @@
"""Tests for letsencrypt.acme.sig."""
"""Tests for acme.sig."""
import os
import pkg_resources
import unittest
import Crypto.PublicKey.RSA
from letsencrypt.acme import jose
from acme import jose
KEY = jose.HashableRSAKey(Crypto.PublicKey.RSA.importKey(
pkg_resources.resource_string(
'letsencrypt.acme.jose', os.path.join('testdata', 'rsa512_key.pem'))))
'acme.jose', os.path.join('testdata', 'rsa512_key.pem'))))
class SignatureTest(unittest.TestCase):
# pylint: disable=too-many-instance-attributes
"""Tests for letsencrypt.acme.sig.Signature."""
"""Tests for acme.sig.Signature."""
def setUp(self):
self.msg = 'message'
@ -45,7 +45,7 @@ class SignatureTest(unittest.TestCase):
'sig': b64sig,
}
from letsencrypt.acme.other import Signature
from acme.other import Signature
self.signature = Signature(
alg=self.alg, sig=self.sig, nonce=self.nonce, jwk=self.jwk)
@ -63,7 +63,7 @@ class SignatureTest(unittest.TestCase):
@classmethod
def _from_msg(cls, *args, **kwargs):
from letsencrypt.acme.other import Signature
from acme.other import Signature
return Signature.from_msg(*args, **kwargs)
def test_create_from_msg(self):
@ -80,12 +80,12 @@ class SignatureTest(unittest.TestCase):
self.assertEqual(self.signature.to_partial_json(), self.jsig_to)
def test_from_json(self):
from letsencrypt.acme.other import Signature
from acme.other import Signature
self.assertEqual(
self.signature, Signature.from_json(self.jsig_from))
def test_from_json_non_schema_errors(self):
from letsencrypt.acme.other import Signature
from acme.other import Signature
jwk = self.jwk.to_partial_json()
self.assertRaises(
jose.DeserializationError, Signature.from_json, {
@ -96,4 +96,4 @@ class SignatureTest(unittest.TestCase):
if __name__ == '__main__':
unittest.main()
unittest.main() # pragma: no cover

View file

@ -15,7 +15,7 @@
"type": "string"
},
"jwk": {
"$ref": "file:letsencrypt/acme/schemata/jwk.json"
"$ref": "file:acme/schemata/jwk.json"
}
}
}

View file

@ -15,14 +15,14 @@
"type": "string"
},
"signature" : {
"$ref": "file:letsencrypt/acme/schemata/signature.json"
"$ref": "file:acme/schemata/signature.json"
},
"responses": {
"type": "array",
"minItems": 1,
"items": {
"anyOf": [
{ "$ref": "file:letsencrypt/acme/schemata/responseobject.json" },
{ "$ref": "file:acme/schemata/responseobject.json" },
{ "type": "null" }
]
}

View file

@ -13,7 +13,7 @@
"pattern": "^[-_=0-9A-Za-z]+$"
},
"signature" : {
"$ref": "file:letsencrypt/acme/schemata/signature.json"
"$ref": "file:acme/schemata/signature.json"
}
}
}

View file

@ -18,7 +18,7 @@
"type": "array",
"minItems": 1,
"items": {
"$ref": "file:letsencrypt/acme/schemata/challengeobject.json"
"$ref": "file:acme/schemata/challengeobject.json"
}
},
"combinations": {

View file

@ -59,7 +59,7 @@
"pattern": "^[-_=0-9A-Za-z]+$"
},
"signature": {
"$ref": "file:letsencrypt/acme/schemata/signature.json"
"$ref": "file:acme/schemata/signature.json"
}
}
},

View file

@ -12,7 +12,7 @@
"type" : "string"
},
"signature" : {
"$ref": "file:letsencrypt/acme/schemata/signature.json"
"$ref": "file:acme/schemata/signature.json"
}
}
}

5
docs/api/account.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.account`
--------------------------
.. automodule:: letsencrypt.account
:members:

5
docs/api/achallenges.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.achallenges`
------------------------------
.. automodule:: letsencrypt.achallenges
:members:

View file

@ -1,61 +0,0 @@
:mod:`letsencrypt.acme`
=======================
.. contents::
.. automodule:: letsencrypt.acme
:members:
Messages
--------
v00
~~~
.. automodule:: letsencrypt.acme.messages
:members:
v02
~~~
.. automodule:: letsencrypt.acme.messages2
:members:
Challenges
----------
.. automodule:: letsencrypt.acme.challenges
:members:
Other ACME objects
------------------
.. automodule:: letsencrypt.acme.other
:members:
Fields
------
.. automodule:: letsencrypt.acme.fields
:members:
Errors
------
.. automodule:: letsencrypt.acme.errors
:members:
:members:
Utilities
---------
.. automodule:: letsencrypt.acme.util
:members:

View file

@ -1,67 +0,0 @@
:mod:`letsencrypt.acme.jose`
============================
.. contents::
.. automodule:: letsencrypt.acme.jose
:members:
JSON Web Algorithms
-------------------
.. automodule:: letsencrypt.acme.jose.jwa
:members:
JSON Web Key
------------
.. automodule:: letsencrypt.acme.jose.jwk
:members:
JSON Web Signature
------------------
.. automodule:: letsencrypt.acme.jose.jws
:members:
Implementation details
----------------------
Interfaces
~~~~~~~~~~
.. automodule:: letsencrypt.acme.jose.interfaces
:members:
Errors
~~~~~~
.. automodule:: letsencrypt.acme.jose.errors
:members:
JSON utilities
~~~~~~~~~~~~~~
.. automodule:: letsencrypt.acme.jose.json_util
:members:
JOSE Base64
~~~~~~~~~~~
.. automodule:: letsencrypt.acme.jose.b64
:members:
Utilities
~~~~~~~~~
.. automodule:: letsencrypt.acme.jose.util
:members:

View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.augeas_configurator`
--------------------------------------
.. automodule:: letsencrypt.augeas_configurator
:members:

View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.auth_handler`
-------------------------------
.. automodule:: letsencrypt.auth_handler
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.account`
---------------------------------
.. automodule:: letsencrypt.client.account
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.achallenges`
-------------------------------------
.. automodule:: letsencrypt.client.achallenges
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.augeas_configurator`
---------------------------------------------
.. automodule:: letsencrypt.client.augeas_configurator
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.auth_handler`
--------------------------------------
.. automodule:: letsencrypt.client.auth_handler
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.client`
--------------------------------
.. automodule:: letsencrypt.client.client
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.configuration`
---------------------------------------
.. automodule:: letsencrypt.client.configuration
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.constants`
-----------------------------------
.. automodule:: letsencrypt.client.constants
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.continuity_auth`
-----------------------------------------
.. automodule:: letsencrypt.client.continuity_auth
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.crypto_util`
-------------------------------------
.. automodule:: letsencrypt.client.crypto_util
:members:

View file

@ -1,29 +0,0 @@
:mod:`letsencrypt.client.display`
---------------------------------
.. automodule:: letsencrypt.client.display
:members:
:mod:`letsencrypt.client.display.util`
======================================
.. automodule:: letsencrypt.client.display.util
:members:
:mod:`letsencrypt.client.display.ops`
=====================================
.. automodule:: letsencrypt.client.display.ops
:members:
:mod:`letsencrypt.client.display.enhancements`
==============================================
.. automodule:: letsencrypt.client.display.enhancements
:members:
:mod:`letsencrypt.client.display.revocation`
============================================
.. automodule:: letsencrypt.client.display.revocation
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.errors`
--------------------------------
.. automodule:: letsencrypt.client.errors
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.interfaces`
------------------------------------
.. automodule:: letsencrypt.client.interfaces
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.le_util`
---------------------------------
.. automodule:: letsencrypt.client.le_util
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.log`
-----------------------------
.. automodule:: letsencrypt.client.log
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.network`
---------------------------------
.. automodule:: letsencrypt.client.network
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.network2`
----------------------------------
.. automodule:: letsencrypt.client.network2
:members:

View file

@ -1,29 +0,0 @@
:mod:`letsencrypt.client.plugins.apache`
----------------------------------------
.. automodule:: letsencrypt.client.plugins.apache
:members:
:mod:`letsencrypt.client.plugins.apache.configurator`
=====================================================
.. automodule:: letsencrypt.client.plugins.apache.configurator
:members:
:mod:`letsencrypt.client.plugins.apache.dvsni`
==============================================
.. automodule:: letsencrypt.client.plugins.apache.dvsni
:members:
:mod:`letsencrypt.client.plugins.apache.obj`
============================================
.. automodule:: letsencrypt.client.plugins.apache.obj
:members:
:mod:`letsencrypt.client.plugins.apache.parser`
===============================================
.. automodule:: letsencrypt.client.plugins.apache.parser
:members:

View file

@ -1,35 +0,0 @@
:mod:`letsencrypt.client.plugins.nginx`
----------------------------------------
.. automodule:: letsencrypt.client.plugins.nginx
:members:
:mod:`letsencrypt.client.plugins.nginx.configurator`
=====================================================
.. automodule:: letsencrypt.client.plugins.nginx.configurator
:members:
:mod:`letsencrypt.client.plugins.nginx.dvsni`
==============================================
.. automodule:: letsencrypt.client.plugins.nginx.dvsni
:members:
:mod:`letsencrypt.client.plugins.nginx.obj`
============================================
.. automodule:: letsencrypt.client.plugins.nginx.obj
:members:
:mod:`letsencrypt.client.plugins.nginx.parser`
===============================================
.. automodule:: letsencrypt.client.plugins.nginx.parser
:members:
:mod:`letsencrypt.client.plugins.nginx.nginxparser`
====================================================
.. automodule:: letsencrypt.client.plugins.nginx.nginxparser
:members:

View file

@ -1,11 +0,0 @@
:mod:`letsencrypt.client.plugins.standalone`
--------------------------------------------
.. automodule:: letsencrypt.client.plugins.standalone
:members:
:mod:`letsencrypt.client.plugins.standalone.authenticator`
==========================================================
.. automodule:: letsencrypt.client.plugins.standalone.authenticator
:members:

View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.client.proof_of_possession`
--------------------------------------------------
.. automodule:: letsencrypt.client.proof_of_possession
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.recovery_token`
--------------------------------------------------
.. automodule:: letsencrypt.client.recovery_token
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.reverter`
----------------------------------
.. automodule:: letsencrypt.client.reverter
:members:

View file

@ -1,5 +0,0 @@
:mod:`letsencrypt.client.revoker`
---------------------------------
.. automodule:: letsencrypt.client.revoker
:members:

View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.configuration`
--------------------------------
.. automodule:: letsencrypt.configuration
:members:

5
docs/api/constants.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.constants`
-----------------------------------
.. automodule:: letsencrypt.constants
:members:

View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.continuity_auth`
----------------------------------
.. automodule:: letsencrypt.continuity_auth
:members:

5
docs/api/crypto_util.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.crypto_util`
------------------------------
.. automodule:: letsencrypt.crypto_util
:members:

29
docs/api/display.rst Normal file
View file

@ -0,0 +1,29 @@
:mod:`letsencrypt.display`
--------------------------
.. automodule:: letsencrypt.display
:members:
:mod:`letsencrypt.display.util`
===============================
.. automodule:: letsencrypt.display.util
:members:
:mod:`letsencrypt.display.ops`
==============================
.. automodule:: letsencrypt.display.ops
:members:
:mod:`letsencrypt.display.enhancements`
=======================================
.. automodule:: letsencrypt.display.enhancements
:members:
:mod:`letsencrypt.display.revocation`
=====================================
.. automodule:: letsencrypt.display.revocation
:members:

5
docs/api/errors.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.errors`
-------------------------
.. automodule:: letsencrypt.errors
:members:

5
docs/api/index.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt`
------------------
.. automodule:: letsencrypt
:members:

5
docs/api/interfaces.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.interfaces`
-----------------------------
.. automodule:: letsencrypt.interfaces
:members:

5
docs/api/le_util.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.le_util`
--------------------------
.. automodule:: letsencrypt.le_util
:members:

5
docs/api/log.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.log`
----------------------
.. automodule:: letsencrypt.log
:members:

5
docs/api/network.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.network`
--------------------------
.. automodule:: letsencrypt.network
:members:

5
docs/api/network2.rst Normal file
View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.network2`
---------------------------
.. automodule:: letsencrypt.network2
:members:

View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.plugins.common`
---------------------------------
.. automodule:: letsencrypt.plugins.common
:members:

View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.plugins.disco`
--------------------------------
.. automodule:: letsencrypt.plugins.disco
:members:

View file

@ -0,0 +1,11 @@
:mod:`letsencrypt.plugins.standalone`
-------------------------------------
.. automodule:: letsencrypt.plugins.standalone
:members:
:mod:`letsencrypt.plugins.standalone.authenticator`
===================================================
.. automodule:: letsencrypt.plugins.standalone.authenticator
:members:

View file

@ -0,0 +1,5 @@
:mod:`letsencrypt.recovery_token`
--------------------------------------------------
.. automodule:: letsencrypt.recovery_token
:members:

Some files were not shown because too many files have changed in this diff Show more