Script 'mail_helper' called by obssrc Hello community, here is the log from the commit of package python-certbot-dns-cloudflare for openSUSE:Factory checked in at 2023-06-07 23:08:24 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/python-certbot-dns-cloudflare (Old) and /work/SRC/openSUSE:Factory/.python-certbot-dns-cloudflare.new.15902 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-certbot-dns-cloudflare" Wed Jun 7 23:08:24 2023 rev:37 rq:1091324 version:2.6.0 Changes: -------- --- /work/SRC/openSUSE:Factory/python-certbot-dns-cloudflare/python-certbot-dns-cloudflare.changes 2022-10-27 13:55:13.116887725 +0200 +++ /work/SRC/openSUSE:Factory/.python-certbot-dns-cloudflare.new.15902/python-certbot-dns-cloudflare.changes 2023-06-07 23:08:58.459884190 +0200 @@ -1,0 +2,10 @@ +Wed Jun 7 16:05:05 UTC 2023 - Markéta Machová <mmach...@suse.com> + +- update to version 2.6.0 + * Support for Python 3.11 was added to Certbot and all of its components. + * All Certbot components now require pytest to run tests. + * Packaged tests for all Certbot components besides josepy were moved inside the _internal/tests module. + * There is now a new Other annotated challenge object to allow plugins to support entirely novel challenges. + * Certbot no longer depends on zope. + +------------------------------------------------------------------- Old: ---- certbot-dns-cloudflare-1.31.0.tar.gz New: ---- certbot-dns-cloudflare-2.6.0.tar.gz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ python-certbot-dns-cloudflare.spec ++++++ --- /var/tmp/diff_new_pack.qh4djz/_old 2023-06-07 23:08:59.007887372 +0200 +++ /var/tmp/diff_new_pack.qh4djz/_new 2023-06-07 23:08:59.015887419 +0200 @@ -1,7 +1,7 @@ # # spec file for package python-certbot-dns-cloudflare # -# Copyright (c) 2022 SUSE LLC +# Copyright (c) 2023 SUSE LLC # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed @@ -19,7 +19,7 @@ %{?!python_module:%define python_module() python-%{**} python3-%{**}} %define skip_python2 1 Name: python-certbot-dns-cloudflare -Version: 1.31.0 +Version: 2.6.0 Release: 0 Summary: Cloudflare Authenticator plugin for Certbot License: Apache-2.0 @@ -30,13 +30,11 @@ BuildRequires: %{python_module cloudflare >= 1.5.1} BuildRequires: %{python_module pytest} BuildRequires: %{python_module setuptools} -BuildRequires: %{python_module zope.interface} BuildRequires: fdupes BuildRequires: python-rpm-macros Requires: python-acme >= %{version} Requires: python-certbot >= %{version} Requires: python-cloudflare >= 1.5.1 -Requires: python-zope.interface BuildArch: noarch %python_subpackages ++++++ certbot-dns-cloudflare-1.31.0.tar.gz -> certbot-dns-cloudflare-2.6.0.tar.gz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/MANIFEST.in new/certbot-dns-cloudflare-2.6.0/MANIFEST.in --- old/certbot-dns-cloudflare-1.31.0/MANIFEST.in 2022-10-04 16:40:41.000000000 +0200 +++ new/certbot-dns-cloudflare-2.6.0/MANIFEST.in 2023-05-09 21:44:36.000000000 +0200 @@ -1,7 +1,6 @@ include LICENSE.txt include README.rst recursive-include docs * -recursive-include tests * include certbot_dns_cloudflare/py.typed global-exclude __pycache__ global-exclude *.py[cod] diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/PKG-INFO new/certbot-dns-cloudflare-2.6.0/PKG-INFO --- old/certbot-dns-cloudflare-1.31.0/PKG-INFO 2022-10-04 16:40:57.979791900 +0200 +++ new/certbot-dns-cloudflare-2.6.0/PKG-INFO 2023-05-09 21:44:45.862443400 +0200 @@ -1,6 +1,6 @@ Metadata-Version: 2.1 Name: certbot-dns-cloudflare -Version: 1.31.0 +Version: 2.6.0 Summary: Cloudflare DNS Authenticator plugin for Certbot Home-page: https://github.com/certbot/certbot Author: Certbot Project @@ -17,6 +17,7 @@ Classifier: Programming Language :: Python :: 3.8 Classifier: Programming Language :: Python :: 3.9 Classifier: Programming Language :: Python :: 3.10 +Classifier: Programming Language :: Python :: 3.11 Classifier: Topic :: Internet :: WWW/HTTP Classifier: Topic :: Security Classifier: Topic :: System :: Installation/Setup @@ -25,4 +26,5 @@ Classifier: Topic :: Utilities Requires-Python: >=3.7 Provides-Extra: docs +Provides-Extra: test License-File: LICENSE.txt diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare/_internal/tests/__init__.py new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare/_internal/tests/__init__.py --- old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare/_internal/tests/__init__.py 1970-01-01 01:00:00.000000000 +0100 +++ new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare/_internal/tests/__init__.py 2023-05-09 21:44:36.000000000 +0200 @@ -0,0 +1 @@ +"""certbot-dns-cloudflare tests""" diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare/_internal/tests/dns_cloudflare_test.py new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare/_internal/tests/dns_cloudflare_test.py --- old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare/_internal/tests/dns_cloudflare_test.py 1970-01-01 01:00:00.000000000 +0100 +++ new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare/_internal/tests/dns_cloudflare_test.py 2023-05-09 21:44:36.000000000 +0200 @@ -0,0 +1,230 @@ +"""Tests for certbot_dns_cloudflare._internal.dns_cloudflare.""" + +import sys +import unittest +from unittest import mock + +import CloudFlare +import pytest + +from certbot import errors +from certbot.compat import os +from certbot.plugins import dns_test_common +from certbot.plugins.dns_test_common import DOMAIN +from certbot.tests import util as test_util + +API_ERROR = CloudFlare.exceptions.CloudFlareAPIError(1000, '', '') + +API_TOKEN = 'an-api-token' + +API_KEY = 'an-api-key' +EMAIL = 'exam...@example.com' + + +class AuthenticatorTest(test_util.TempDirTestCase, dns_test_common.BaseAuthenticatorTest): + + def setUp(self): + from certbot_dns_cloudflare._internal.dns_cloudflare import Authenticator + + super().setUp() + + path = os.path.join(self.tempdir, 'file.ini') + dns_test_common.write({"cloudflare_email": EMAIL, "cloudflare_api_key": API_KEY}, path) + + self.config = mock.MagicMock(cloudflare_credentials=path, + cloudflare_propagation_seconds=0) # don't wait during tests + + self.auth = Authenticator(self.config, "cloudflare") + + self.mock_client = mock.MagicMock() + # _get_cloudflare_client | pylint: disable=protected-access + self.auth._get_cloudflare_client = mock.MagicMock(return_value=self.mock_client) + + @test_util.patch_display_util() + def test_perform(self, unused_mock_get_utility): + self.auth.perform([self.achall]) + + expected = [mock.call.add_txt_record(DOMAIN, '_acme-challenge.'+DOMAIN, mock.ANY, mock.ANY)] + assert expected == self.mock_client.mock_calls + + def test_cleanup(self): + # _attempt_cleanup | pylint: disable=protected-access + self.auth._attempt_cleanup = True + self.auth.cleanup([self.achall]) + + expected = [mock.call.del_txt_record(DOMAIN, '_acme-challenge.'+DOMAIN, mock.ANY)] + assert expected == self.mock_client.mock_calls + + @test_util.patch_display_util() + def test_api_token(self, unused_mock_get_utility): + dns_test_common.write({"cloudflare_api_token": API_TOKEN}, + self.config.cloudflare_credentials) + self.auth.perform([self.achall]) + + expected = [mock.call.add_txt_record(DOMAIN, '_acme-challenge.'+DOMAIN, mock.ANY, mock.ANY)] + assert expected == self.mock_client.mock_calls + + def test_no_creds(self): + dns_test_common.write({}, self.config.cloudflare_credentials) + with pytest.raises(errors.PluginError): + self.auth.perform([self.achall]) + + def test_missing_email_or_key(self): + dns_test_common.write({"cloudflare_api_key": API_KEY}, self.config.cloudflare_credentials) + with pytest.raises(errors.PluginError): + self.auth.perform([self.achall]) + + dns_test_common.write({"cloudflare_email": EMAIL}, self.config.cloudflare_credentials) + with pytest.raises(errors.PluginError): + self.auth.perform([self.achall]) + + def test_email_or_key_with_token(self): + dns_test_common.write({"cloudflare_api_token": API_TOKEN, "cloudflare_email": EMAIL}, + self.config.cloudflare_credentials) + with pytest.raises(errors.PluginError): + self.auth.perform([self.achall]) + + dns_test_common.write({"cloudflare_api_token": API_TOKEN, "cloudflare_api_key": API_KEY}, + self.config.cloudflare_credentials) + with pytest.raises(errors.PluginError): + self.auth.perform([self.achall]) + + dns_test_common.write({"cloudflare_api_token": API_TOKEN, "cloudflare_email": EMAIL, + "cloudflare_api_key": API_KEY}, self.config.cloudflare_credentials) + with pytest.raises(errors.PluginError): + self.auth.perform([self.achall]) + + +class CloudflareClientTest(unittest.TestCase): + record_name = "foo" + record_content = "bar" + record_ttl = 42 + zone_id = 1 + record_id = 2 + + def setUp(self): + from certbot_dns_cloudflare._internal.dns_cloudflare import _CloudflareClient + + self.cloudflare_client = _CloudflareClient(EMAIL, API_KEY) + + self.cf = mock.MagicMock() + self.cloudflare_client.cf = self.cf + + def test_add_txt_record(self): + self.cf.zones.get.return_value = [{'id': self.zone_id}] + + self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, + self.record_ttl) + + self.cf.zones.dns_records.post.assert_called_with(self.zone_id, data=mock.ANY) + + post_data = self.cf.zones.dns_records.post.call_args[1]['data'] + + assert 'TXT' == post_data['type'] + assert self.record_name == post_data['name'] + assert self.record_content == post_data['content'] + assert self.record_ttl == post_data['ttl'] + + def test_add_txt_record_error(self): + self.cf.zones.get.return_value = [{'id': self.zone_id}] + + self.cf.zones.dns_records.post.side_effect = CloudFlare.exceptions.CloudFlareAPIError(1009, '', '') + + with pytest.raises(errors.PluginError): + self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, self.record_ttl) + + def test_add_txt_record_error_during_zone_lookup(self): + self.cf.zones.get.side_effect = API_ERROR + + with pytest.raises(errors.PluginError): + self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, self.record_ttl) + + def test_add_txt_record_zone_not_found(self): + self.cf.zones.get.return_value = [] + + with pytest.raises(errors.PluginError): + self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, self.record_ttl) + + def test_add_txt_record_bad_creds(self): + self.cf.zones.get.side_effect = CloudFlare.exceptions.CloudFlareAPIError(6003, '', '') + with pytest.raises(errors.PluginError): + self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, self.record_ttl) + + self.cf.zones.get.side_effect = CloudFlare.exceptions.CloudFlareAPIError(9103, '', '') + with pytest.raises(errors.PluginError): + self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, self.record_ttl) + + self.cf.zones.get.side_effect = CloudFlare.exceptions.CloudFlareAPIError(9109, '', '') + with pytest.raises(errors.PluginError): + self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, self.record_ttl) + + self.cf.zones.get.side_effect = CloudFlare.exceptions.CloudFlareAPIError(0, 'com.cloudflare.api.account.zone.list', '') + with pytest.raises(errors.PluginError): + self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, self.record_ttl) + + def test_del_txt_record(self): + self.cf.zones.get.return_value = [{'id': self.zone_id}] + self.cf.zones.dns_records.get.return_value = [{'id': self.record_id}] + + self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) + + expected = [mock.call.zones.get(params=mock.ANY), + mock.call.zones.dns_records.get(self.zone_id, params=mock.ANY), + mock.call.zones.dns_records.delete(self.zone_id, self.record_id)] + + assert expected == self.cf.mock_calls + + get_data = self.cf.zones.dns_records.get.call_args[1]['params'] + + assert 'TXT' == get_data['type'] + assert self.record_name == get_data['name'] + assert self.record_content == get_data['content'] + + def test_del_txt_record_error_during_zone_lookup(self): + self.cf.zones.get.side_effect = API_ERROR + + self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) + + def test_del_txt_record_error_during_delete(self): + self.cf.zones.get.return_value = [{'id': self.zone_id}] + self.cf.zones.dns_records.get.return_value = [{'id': self.record_id}] + self.cf.zones.dns_records.delete.side_effect = API_ERROR + + self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) + expected = [mock.call.zones.get(params=mock.ANY), + mock.call.zones.dns_records.get(self.zone_id, params=mock.ANY), + mock.call.zones.dns_records.delete(self.zone_id, self.record_id)] + + assert expected == self.cf.mock_calls + + def test_del_txt_record_error_during_get(self): + self.cf.zones.get.return_value = [{'id': self.zone_id}] + self.cf.zones.dns_records.get.side_effect = API_ERROR + + self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) + expected = [mock.call.zones.get(params=mock.ANY), + mock.call.zones.dns_records.get(self.zone_id, params=mock.ANY)] + + assert expected == self.cf.mock_calls + + def test_del_txt_record_no_record(self): + self.cf.zones.get.return_value = [{'id': self.zone_id}] + self.cf.zones.dns_records.get.return_value = [] + + self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) + expected = [mock.call.zones.get(params=mock.ANY), + mock.call.zones.dns_records.get(self.zone_id, params=mock.ANY)] + + assert expected == self.cf.mock_calls + + def test_del_txt_record_no_zone(self): + self.cf.zones.get.return_value = [{'id': None}] + + self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) + expected = [mock.call.zones.get(params=mock.ANY)] + + assert expected == self.cf.mock_calls + + +if __name__ == "__main__": + sys.exit(pytest.main(sys.argv[1:] + [__file__])) # pragma: no cover diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare.egg-info/PKG-INFO new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare.egg-info/PKG-INFO --- old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare.egg-info/PKG-INFO 2022-10-04 16:40:57.000000000 +0200 +++ new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare.egg-info/PKG-INFO 2023-05-09 21:44:45.000000000 +0200 @@ -1,6 +1,6 @@ Metadata-Version: 2.1 Name: certbot-dns-cloudflare -Version: 1.31.0 +Version: 2.6.0 Summary: Cloudflare DNS Authenticator plugin for Certbot Home-page: https://github.com/certbot/certbot Author: Certbot Project @@ -17,6 +17,7 @@ Classifier: Programming Language :: Python :: 3.8 Classifier: Programming Language :: Python :: 3.9 Classifier: Programming Language :: Python :: 3.10 +Classifier: Programming Language :: Python :: 3.11 Classifier: Topic :: Internet :: WWW/HTTP Classifier: Topic :: Security Classifier: Topic :: System :: Installation/Setup @@ -25,4 +26,5 @@ Classifier: Topic :: Utilities Requires-Python: >=3.7 Provides-Extra: docs +Provides-Extra: test License-File: LICENSE.txt diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare.egg-info/SOURCES.txt new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare.egg-info/SOURCES.txt --- old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare.egg-info/SOURCES.txt 2022-10-04 16:40:57.000000000 +0200 +++ new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare.egg-info/SOURCES.txt 2023-05-09 21:44:45.000000000 +0200 @@ -12,10 +12,11 @@ certbot_dns_cloudflare.egg-info/top_level.txt certbot_dns_cloudflare/_internal/__init__.py certbot_dns_cloudflare/_internal/dns_cloudflare.py +certbot_dns_cloudflare/_internal/tests/__init__.py +certbot_dns_cloudflare/_internal/tests/dns_cloudflare_test.py docs/.gitignore docs/Makefile docs/api.rst docs/conf.py docs/index.rst -docs/make.bat -tests/dns_cloudflare_test.py \ No newline at end of file +docs/make.bat \ No newline at end of file diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare.egg-info/requires.txt new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare.egg-info/requires.txt --- old/certbot-dns-cloudflare-1.31.0/certbot_dns_cloudflare.egg-info/requires.txt 2022-10-04 16:40:57.000000000 +0200 +++ new/certbot-dns-cloudflare-2.6.0/certbot_dns_cloudflare.egg-info/requires.txt 2023-05-09 21:44:45.000000000 +0200 @@ -1,8 +1,11 @@ cloudflare>=1.5.1 setuptools>=41.6.0 -acme>=1.31.0 -certbot>=1.31.0 +acme>=2.6.0 +certbot>=2.6.0 [docs] Sphinx>=1.0 sphinx_rtd_theme + +[test] +pytest diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/setup.py new/certbot-dns-cloudflare-2.6.0/setup.py --- old/certbot-dns-cloudflare-1.31.0/setup.py 2022-10-04 16:40:42.000000000 +0200 +++ new/certbot-dns-cloudflare-2.6.0/setup.py 2023-05-09 21:44:37.000000000 +0200 @@ -4,7 +4,7 @@ from setuptools import find_packages from setuptools import setup -version = '1.31.0' +version = '2.6.0' install_requires = [ 'cloudflare>=1.5.1', @@ -30,6 +30,10 @@ 'sphinx_rtd_theme', ] +test_extras = [ + 'pytest', +] + setup( name='certbot-dns-cloudflare', version=version, @@ -51,6 +55,7 @@ 'Programming Language :: Python :: 3.8', 'Programming Language :: Python :: 3.9', 'Programming Language :: Python :: 3.10', + 'Programming Language :: Python :: 3.11', 'Topic :: Internet :: WWW/HTTP', 'Topic :: Security', 'Topic :: System :: Installation/Setup', @@ -64,6 +69,7 @@ install_requires=install_requires, extras_require={ 'docs': docs_extras, + 'test': test_extras, }, entry_points={ 'certbot.plugins': [ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/certbot-dns-cloudflare-1.31.0/tests/dns_cloudflare_test.py new/certbot-dns-cloudflare-2.6.0/tests/dns_cloudflare_test.py --- old/certbot-dns-cloudflare-1.31.0/tests/dns_cloudflare_test.py 2022-10-04 16:40:41.000000000 +0200 +++ new/certbot-dns-cloudflare-2.6.0/tests/dns_cloudflare_test.py 1970-01-01 01:00:00.000000000 +0100 @@ -1,251 +0,0 @@ -"""Tests for certbot_dns_cloudflare._internal.dns_cloudflare.""" - -import unittest - -import CloudFlare -try: - import mock -except ImportError: # pragma: no cover - from unittest import mock # type: ignore - -from certbot import errors -from certbot.compat import os -from certbot.plugins import dns_test_common -from certbot.plugins.dns_test_common import DOMAIN -from certbot.tests import util as test_util - -API_ERROR = CloudFlare.exceptions.CloudFlareAPIError(1000, '', '') - -API_TOKEN = 'an-api-token' - -API_KEY = 'an-api-key' -EMAIL = 'exam...@example.com' - - -class AuthenticatorTest(test_util.TempDirTestCase, dns_test_common.BaseAuthenticatorTest): - - def setUp(self): - from certbot_dns_cloudflare._internal.dns_cloudflare import Authenticator - - super().setUp() - - path = os.path.join(self.tempdir, 'file.ini') - dns_test_common.write({"cloudflare_email": EMAIL, "cloudflare_api_key": API_KEY}, path) - - self.config = mock.MagicMock(cloudflare_credentials=path, - cloudflare_propagation_seconds=0) # don't wait during tests - - self.auth = Authenticator(self.config, "cloudflare") - - self.mock_client = mock.MagicMock() - # _get_cloudflare_client | pylint: disable=protected-access - self.auth._get_cloudflare_client = mock.MagicMock(return_value=self.mock_client) - - @test_util.patch_display_util() - def test_perform(self, unused_mock_get_utility): - self.auth.perform([self.achall]) - - expected = [mock.call.add_txt_record(DOMAIN, '_acme-challenge.'+DOMAIN, mock.ANY, mock.ANY)] - self.assertEqual(expected, self.mock_client.mock_calls) - - def test_cleanup(self): - # _attempt_cleanup | pylint: disable=protected-access - self.auth._attempt_cleanup = True - self.auth.cleanup([self.achall]) - - expected = [mock.call.del_txt_record(DOMAIN, '_acme-challenge.'+DOMAIN, mock.ANY)] - self.assertEqual(expected, self.mock_client.mock_calls) - - @test_util.patch_display_util() - def test_api_token(self, unused_mock_get_utility): - dns_test_common.write({"cloudflare_api_token": API_TOKEN}, - self.config.cloudflare_credentials) - self.auth.perform([self.achall]) - - expected = [mock.call.add_txt_record(DOMAIN, '_acme-challenge.'+DOMAIN, mock.ANY, mock.ANY)] - self.assertEqual(expected, self.mock_client.mock_calls) - - def test_no_creds(self): - dns_test_common.write({}, self.config.cloudflare_credentials) - self.assertRaises(errors.PluginError, - self.auth.perform, - [self.achall]) - - def test_missing_email_or_key(self): - dns_test_common.write({"cloudflare_api_key": API_KEY}, self.config.cloudflare_credentials) - self.assertRaises(errors.PluginError, - self.auth.perform, - [self.achall]) - - dns_test_common.write({"cloudflare_email": EMAIL}, self.config.cloudflare_credentials) - self.assertRaises(errors.PluginError, - self.auth.perform, - [self.achall]) - - def test_email_or_key_with_token(self): - dns_test_common.write({"cloudflare_api_token": API_TOKEN, "cloudflare_email": EMAIL}, - self.config.cloudflare_credentials) - self.assertRaises(errors.PluginError, - self.auth.perform, - [self.achall]) - - dns_test_common.write({"cloudflare_api_token": API_TOKEN, "cloudflare_api_key": API_KEY}, - self.config.cloudflare_credentials) - self.assertRaises(errors.PluginError, - self.auth.perform, - [self.achall]) - - dns_test_common.write({"cloudflare_api_token": API_TOKEN, "cloudflare_email": EMAIL, - "cloudflare_api_key": API_KEY}, self.config.cloudflare_credentials) - self.assertRaises(errors.PluginError, - self.auth.perform, - [self.achall]) - - -class CloudflareClientTest(unittest.TestCase): - record_name = "foo" - record_content = "bar" - record_ttl = 42 - zone_id = 1 - record_id = 2 - - def setUp(self): - from certbot_dns_cloudflare._internal.dns_cloudflare import _CloudflareClient - - self.cloudflare_client = _CloudflareClient(EMAIL, API_KEY) - - self.cf = mock.MagicMock() - self.cloudflare_client.cf = self.cf - - def test_add_txt_record(self): - self.cf.zones.get.return_value = [{'id': self.zone_id}] - - self.cloudflare_client.add_txt_record(DOMAIN, self.record_name, self.record_content, - self.record_ttl) - - self.cf.zones.dns_records.post.assert_called_with(self.zone_id, data=mock.ANY) - - post_data = self.cf.zones.dns_records.post.call_args[1]['data'] - - self.assertEqual('TXT', post_data['type']) - self.assertEqual(self.record_name, post_data['name']) - self.assertEqual(self.record_content, post_data['content']) - self.assertEqual(self.record_ttl, post_data['ttl']) - - def test_add_txt_record_error(self): - self.cf.zones.get.return_value = [{'id': self.zone_id}] - - self.cf.zones.dns_records.post.side_effect = CloudFlare.exceptions.CloudFlareAPIError(1009, '', '') - - self.assertRaises( - errors.PluginError, - self.cloudflare_client.add_txt_record, - DOMAIN, self.record_name, self.record_content, self.record_ttl) - - def test_add_txt_record_error_during_zone_lookup(self): - self.cf.zones.get.side_effect = API_ERROR - - self.assertRaises( - errors.PluginError, - self.cloudflare_client.add_txt_record, - DOMAIN, self.record_name, self.record_content, self.record_ttl) - - def test_add_txt_record_zone_not_found(self): - self.cf.zones.get.return_value = [] - - self.assertRaises( - errors.PluginError, - self.cloudflare_client.add_txt_record, - DOMAIN, self.record_name, self.record_content, self.record_ttl) - - def test_add_txt_record_bad_creds(self): - self.cf.zones.get.side_effect = CloudFlare.exceptions.CloudFlareAPIError(6003, '', '') - self.assertRaises( - errors.PluginError, - self.cloudflare_client.add_txt_record, - DOMAIN, self.record_name, self.record_content, self.record_ttl) - - self.cf.zones.get.side_effect = CloudFlare.exceptions.CloudFlareAPIError(9103, '', '') - self.assertRaises( - errors.PluginError, - self.cloudflare_client.add_txt_record, - DOMAIN, self.record_name, self.record_content, self.record_ttl) - - self.cf.zones.get.side_effect = CloudFlare.exceptions.CloudFlareAPIError(9109, '', '') - self.assertRaises( - errors.PluginError, - self.cloudflare_client.add_txt_record, - DOMAIN, self.record_name, self.record_content, self.record_ttl) - - self.cf.zones.get.side_effect = CloudFlare.exceptions.CloudFlareAPIError(0, 'com.cloudflare.api.account.zone.list', '') - self.assertRaises( - errors.PluginError, - self.cloudflare_client.add_txt_record, - DOMAIN, self.record_name, self.record_content, self.record_ttl) - - def test_del_txt_record(self): - self.cf.zones.get.return_value = [{'id': self.zone_id}] - self.cf.zones.dns_records.get.return_value = [{'id': self.record_id}] - - self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) - - expected = [mock.call.zones.get(params=mock.ANY), - mock.call.zones.dns_records.get(self.zone_id, params=mock.ANY), - mock.call.zones.dns_records.delete(self.zone_id, self.record_id)] - - self.assertEqual(expected, self.cf.mock_calls) - - get_data = self.cf.zones.dns_records.get.call_args[1]['params'] - - self.assertEqual('TXT', get_data['type']) - self.assertEqual(self.record_name, get_data['name']) - self.assertEqual(self.record_content, get_data['content']) - - def test_del_txt_record_error_during_zone_lookup(self): - self.cf.zones.get.side_effect = API_ERROR - - self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) - - def test_del_txt_record_error_during_delete(self): - self.cf.zones.get.return_value = [{'id': self.zone_id}] - self.cf.zones.dns_records.get.return_value = [{'id': self.record_id}] - self.cf.zones.dns_records.delete.side_effect = API_ERROR - - self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) - expected = [mock.call.zones.get(params=mock.ANY), - mock.call.zones.dns_records.get(self.zone_id, params=mock.ANY), - mock.call.zones.dns_records.delete(self.zone_id, self.record_id)] - - self.assertEqual(expected, self.cf.mock_calls) - - def test_del_txt_record_error_during_get(self): - self.cf.zones.get.return_value = [{'id': self.zone_id}] - self.cf.zones.dns_records.get.side_effect = API_ERROR - - self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) - expected = [mock.call.zones.get(params=mock.ANY), - mock.call.zones.dns_records.get(self.zone_id, params=mock.ANY)] - - self.assertEqual(expected, self.cf.mock_calls) - - def test_del_txt_record_no_record(self): - self.cf.zones.get.return_value = [{'id': self.zone_id}] - self.cf.zones.dns_records.get.return_value = [] - - self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) - expected = [mock.call.zones.get(params=mock.ANY), - mock.call.zones.dns_records.get(self.zone_id, params=mock.ANY)] - - self.assertEqual(expected, self.cf.mock_calls) - - def test_del_txt_record_no_zone(self): - self.cf.zones.get.return_value = [{'id': None}] - - self.cloudflare_client.del_txt_record(DOMAIN, self.record_name, self.record_content) - expected = [mock.call.zones.get(params=mock.ANY)] - - self.assertEqual(expected, self.cf.mock_calls) - - -if __name__ == "__main__": - unittest.main() # pragma: no cover