[FIX] letsencrypt: Increase test coverage
parent
11623a869c
commit
192a46005b
|
@ -1,3 +1,4 @@
|
||||||
# Copyright 2018 Therp BV <http://therp.nl>
|
# Copyright 2018 Therp BV <http://therp.nl>
|
||||||
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
|
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
|
||||||
|
from . import test_http
|
||||||
from . import test_letsencrypt
|
from . import test_letsencrypt
|
||||||
|
|
|
@ -0,0 +1,26 @@
|
||||||
|
# Copyright 2020 Therp BV <http://therp.nl>
|
||||||
|
# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
|
||||||
|
|
||||||
|
import os
|
||||||
|
import shutil
|
||||||
|
|
||||||
|
from odoo.tests import HttpCase
|
||||||
|
|
||||||
|
from ..models.letsencrypt import _get_challenge_dir
|
||||||
|
|
||||||
|
|
||||||
|
class TestHTTP(HttpCase):
|
||||||
|
def test_query_existing(self):
|
||||||
|
with open(os.path.join(_get_challenge_dir(), "foobar"), "w") as file:
|
||||||
|
file.write("content")
|
||||||
|
res = self.url_open("/.well-known/acme-challenge/foobar")
|
||||||
|
self.assertEqual(res.status_code, 200)
|
||||||
|
self.assertEqual(res.text, "content")
|
||||||
|
|
||||||
|
def test_query_missing(self):
|
||||||
|
res = self.url_open("/.well-known/acme-challenge/foobar")
|
||||||
|
self.assertEqual(res.status_code, 404)
|
||||||
|
|
||||||
|
def tearDown(self):
|
||||||
|
super().tearDown()
|
||||||
|
shutil.rmtree(_get_challenge_dir(), ignore_errors=True)
|
|
@ -9,9 +9,14 @@ from os import path
|
||||||
|
|
||||||
import mock
|
import mock
|
||||||
|
|
||||||
from odoo.exceptions import UserError
|
from odoo.exceptions import UserError, ValidationError
|
||||||
from odoo.tests import SingleTransactionCase
|
from odoo.tests import SingleTransactionCase
|
||||||
|
|
||||||
|
try:
|
||||||
|
import dns.resolver
|
||||||
|
except ImportError:
|
||||||
|
pass
|
||||||
|
|
||||||
from ..models.letsencrypt import _get_data_dir, _get_challenge_dir
|
from ..models.letsencrypt import _get_data_dir, _get_challenge_dir
|
||||||
|
|
||||||
|
|
||||||
|
@ -35,7 +40,7 @@ class TestLetsencrypt(SingleTransactionCase):
|
||||||
'letsencrypt_dns_provider': 'shell',
|
'letsencrypt_dns_provider': 'shell',
|
||||||
'letsencrypt_dns_shell_script': 'touch /tmp/.letsencrypt_test',
|
'letsencrypt_dns_shell_script': 'touch /tmp/.letsencrypt_test',
|
||||||
'letsencrypt_altnames': '*.example.com',
|
'letsencrypt_altnames': '*.example.com',
|
||||||
'letsencrypt_reload_command': 'true', # i.e. /bin/true
|
'letsencrypt_reload_command': 'echo reloaded',
|
||||||
}
|
}
|
||||||
).set_values()
|
).set_values()
|
||||||
|
|
||||||
|
@ -47,13 +52,18 @@ class TestLetsencrypt(SingleTransactionCase):
|
||||||
'touch /tmp/.letsencrypt_test',
|
'touch /tmp/.letsencrypt_test',
|
||||||
)
|
)
|
||||||
self.assertEqual(setting_vals['letsencrypt_altnames'], '*.example.com')
|
self.assertEqual(setting_vals['letsencrypt_altnames'], '*.example.com')
|
||||||
self.assertEqual(setting_vals['letsencrypt_reload_command'], 'true')
|
self.assertEqual(setting_vals['letsencrypt_reload_command'], 'echo reloaded')
|
||||||
self.assertTrue(setting_vals['letsencrypt_needs_dns_provider'])
|
self.assertTrue(setting_vals['letsencrypt_needs_dns_provider'])
|
||||||
self.assertFalse(setting_vals['letsencrypt_prefer_dns'])
|
self.assertFalse(setting_vals['letsencrypt_prefer_dns'])
|
||||||
|
|
||||||
|
with self.assertRaises(ValidationError):
|
||||||
|
self.env["res.config.settings"].create(
|
||||||
|
{"letsencrypt_dns_shell_script": "# Empty script"}
|
||||||
|
).set_values()
|
||||||
|
|
||||||
@mock.patch('acme.client.ClientV2.answer_challenge')
|
@mock.patch('acme.client.ClientV2.answer_challenge')
|
||||||
@mock.patch('acme.client.ClientV2.poll_and_finalize', side_effect=_poll)
|
@mock.patch('acme.client.ClientV2.poll_and_finalize', side_effect=_poll)
|
||||||
def test_http_challenge(self, poll, answer_challenge):
|
def test_http_challenge(self, poll, _answer_challenge):
|
||||||
letsencrypt = self.env['letsencrypt']
|
letsencrypt = self.env['letsencrypt']
|
||||||
self.env['res.config.settings'].create(
|
self.env['res.config.settings'].create(
|
||||||
{'letsencrypt_altnames': 'test.example.com'}
|
{'letsencrypt_altnames': 'test.example.com'}
|
||||||
|
@ -74,10 +84,12 @@ class TestLetsencrypt(SingleTransactionCase):
|
||||||
@mock.patch('acme.client.ClientV2.poll_and_finalize', side_effect=_poll)
|
@mock.patch('acme.client.ClientV2.poll_and_finalize', side_effect=_poll)
|
||||||
def test_dns_challenge(self, poll, answer_challenge, sleep, query, dnsupd):
|
def test_dns_challenge(self, poll, answer_challenge, sleep, query, dnsupd):
|
||||||
|
|
||||||
|
record = None
|
||||||
|
|
||||||
def register_update(challenge, domain, token):
|
def register_update(challenge, domain, token):
|
||||||
|
nonlocal record
|
||||||
record = mock.Mock()
|
record = mock.Mock()
|
||||||
record.to_text.return_value = '"%s"' % token
|
record.to_text.return_value = '"%s"' % token
|
||||||
query.return_value = [record]
|
|
||||||
ret = mock.Mock()
|
ret = mock.Mock()
|
||||||
ret.challenge = challenge
|
ret.challenge = challenge
|
||||||
ret.domain = domain
|
ret.domain = domain
|
||||||
|
@ -86,10 +98,28 @@ class TestLetsencrypt(SingleTransactionCase):
|
||||||
|
|
||||||
dnsupd.side_effect = register_update
|
dnsupd.side_effect = register_update
|
||||||
|
|
||||||
|
ncalls = 0
|
||||||
|
|
||||||
|
def query_effect(domain, rectype):
|
||||||
|
nonlocal ncalls
|
||||||
|
self.assertEqual(domain, "_acme-challenge.example.com.")
|
||||||
|
self.assertEqual(rectype, "TXT")
|
||||||
|
ncalls += 1
|
||||||
|
if ncalls == 1:
|
||||||
|
raise dns.resolver.NXDOMAIN
|
||||||
|
elif ncalls == 2:
|
||||||
|
wrong_record = mock.Mock()
|
||||||
|
wrong_record.to_text.return_value = '"not right"'
|
||||||
|
return [wrong_record]
|
||||||
|
else:
|
||||||
|
return [record]
|
||||||
|
|
||||||
|
query.side_effect = query_effect
|
||||||
|
|
||||||
self.install_certificate(days_left=10)
|
self.install_certificate(days_left=10)
|
||||||
self.env['letsencrypt']._cron()
|
self.env['letsencrypt']._cron()
|
||||||
poll.assert_called()
|
poll.assert_called()
|
||||||
query.assert_called_with("_acme-challenge.example.com.", "TXT")
|
self.assertEqual(ncalls, 3)
|
||||||
self.assertTrue(path.isfile('/tmp/.letsencrypt_test'))
|
self.assertTrue(path.isfile('/tmp/.letsencrypt_test'))
|
||||||
self.assertTrue(
|
self.assertTrue(
|
||||||
path.isfile(path.join(_get_data_dir(), 'www.example.com.crt'))
|
path.isfile(path.join(_get_data_dir(), 'www.example.com.crt'))
|
||||||
|
|
Loading…
Reference in New Issue