common.Plugin (with .conf(var), PluginEntryPoint, PluginRegistry

This commit is contained in:
Jakub Warmuz
2015-05-02 07:01:44 +00:00
parent 17e8ddcb5c
commit 19cff00835
13 changed files with 278 additions and 135 deletions
@@ -1,18 +1,27 @@
"""Example Let's Encrypt plugins."""
"""Example Let's Encrypt plugins.
For full examples, see `letsencrypt.client.plugins`.
"""
import zope.interface
from letsencrypt.client import interfaces
from letsencrypt.client.plugins import common
class Authenticator(object):
class Authenticator(common.Plugin):
zope.interface.implements(interfaces.IAuthenticator)
description = 'Example Authenticator plugin'
def __init__(self, config):
self.config = config
# Implement all methods from IAuthenticator, remembering to add
# "self" as first argument, e.g. def prepare(self)...
# For full examples, see letsencrypt.client.plugins
class Installer(common.Plugins):
zope.interface.implements(interfaces.IInstaller)
description = 'Example Installer plugin'
# Implement all methods from IInstaller, remembering to add
# "self" as first argument, e.g. def get_all_names(self)...
+2 -1
View File
@@ -10,7 +10,8 @@ setup(
],
entry_points={
'letsencrypt.plugins': [
'example = letsencrypt_example_plugins:Authenticator',
'example_authenticator = letsencrypt_example_plugins:Authenticator',
'example_installer = letsencrypt_example_plugins:Installer',
],
},
)
+5 -4
View File
@@ -4,9 +4,10 @@ import logging
import augeas
from letsencrypt.client import reverter
from letsencrypt.client.plugins import common
class AugeasConfigurator(object):
class AugeasConfigurator(common.Plugin):
"""Base Augeas Configurator class.
:ivar config: Configuration.
@@ -21,8 +22,8 @@ class AugeasConfigurator(object):
"""
def __init__(self, config):
self.config = config
def __init__(self, *args, **kwargs):
super(AugeasConfigurator, self).__init__(*args, **kwargs)
# Set Augeas flags to not save backup (we do it ourselves)
# Set Augeas to not load anything by default
@@ -34,7 +35,7 @@ class AugeasConfigurator(object):
# This needs to occur before VirtualHost objects are setup...
# because this will change the underlying configuration and potential
# vhosts
self.reverter = reverter.Reverter(config)
self.reverter = reverter.Reverter(self.config)
self.reverter.recovery_routine()
def check_parsing_errors(self, lens):
+28 -37
View File
@@ -171,48 +171,49 @@ def config_changes(args, config):
client.config_changes(config)
def _print_plugins(filtered, plugins, names):
if not filtered:
def _print_plugins(plugins):
# TODO: this functions should use IDisplay rather than printing
if not plugins:
print "No plugins found"
for plugin_cls, content in filtered.iteritems():
print "* {0}".format(names[plugin_cls])
print "Description: {0}".format(plugin_cls.description)
for plugin_ep in plugins.itervalues():
print "* {0}".format(plugin_ep.name)
print "Description: {0}".format(plugin_ep.plugin_cls.description)
print "Interfaces: {0}".format(", ".join(
iface.__name__ for iface in zope.interface.implementedBy(
plugin_cls)))
print "Entry points:"
for entry_point in plugins[plugin_cls]:
print "- {0.dist}: {0}".format(entry_point)
plugin_ep.plugin_cls)))
print "Entry point: {0}".format(plugin_ep.entry_point)
if plugin_ep.initialized:
print "Initialized: {0}".format(plugin_ep.init())
# if filtered == prepared:
if isinstance(content, tuple) and content[1] is not None:
print content[1] # error
print
#if isinstance(content, tuple) and content[1] is not None:
# print content[1] # error
print # whitespace between plugins
def plugins(args, config):
"""List plugins."""
plugins = plugins_disco.find_plugins()
plugins = plugins_disco.PluginRegistry.find_all()
logging.debug("Discovered plugins: %s", plugins)
names = plugins_disco.name_plugins(plugins)
ifaces = [] if args.ifaces is None else args.ifaces
filtered = plugins_disco.filter_plugins(
plugins, *((iface,) for iface in ifaces))
filtered = plugins.filter(*((iface,) for iface in ifaces))
logging.debug("Filtered plugins: %s", filtered)
if not args.init and not args.prepare:
return _print_plugins(filtered, plugins, names)
return _print_plugins(filtered)
initialized = dict((plugin_cls, plugin_cls(config))
for plugin_cls in filtered)
verified = plugins_disco.verify_plugins(initialized, ifaces)
logging.debug("Verified plugins: %s", initialized)
for plugin_ep in filtered.itervalues():
plugin_ep.init(config)
#verified = plugins_disco.verify_plugins(initialized, ifaces)
#logging.debug("Verified plugins: %s", initialized)
if not args.prepare:
return _print_plugins(initialized, plugins, names)
return _print_plugins(filtered)
prepared = plugins_disco.prepare_plugins(initialized)
logging.debug("Prepared plugins: %s", plugins)
@@ -327,12 +328,10 @@ def create_parser():
paths_parser(parser.add_argument_group("paths"))
# TODO: plugin_parser should be called for every detected plugin
plugin_parser(
parser.add_argument_group("apache"), prefix="apache",
plugin_cls=apache_configurator.ApacheConfigurator)
plugin_parser(
parser.add_argument_group("nginx"), prefix="nginx",
plugin_cls=nginx_configurator.NginxConfigurator)
for name, plugin_cls in [
("apache", apache_configurator.ApacheConfigurator),
("nginx", nginx_configurator.NginxConfigurator)]:
plugin_cls.inject_parser_options(parser.add_argument_group(name), name)
return parser
@@ -360,14 +359,6 @@ def paths_parser(parser):
return parser
def plugin_parser(parser, prefix, plugin_cls):
def add(arg_name_no_prefix, *args, **kwargs):
parser.add_argument(
"--{0}-{1}".format(prefix, arg_name_no_prefix), *args, **kwargs)
plugin_cls.add_parser_arguments(add)
return parser
def main(args=sys.argv[1:]):
"""Command line argument parsing and main script execution."""
# note: arg parser internally handles --help (and exits afterwards)
+42 -9
View File
@@ -6,30 +6,63 @@ import zope.interface
class IPluginFactory(zope.interface.Interface):
"""IPlugin factory.
def __call__(config):
Objects providing this interface will be called without satisfying
any entry point "extras" (extra dependencies) you might have defined
for your plugin, e.g (excerpt from ``setup.py`` script)::
setup(
...
entry_points={
'letsencrypt.plugins': [
'name=example_project.plugin[plugin_deps]',
],
},
extras_require={
'plugin_deps': ['dep1', 'dep2'],
}
)
Therefore, make sure such objects are importable and usable without
extras. This is necessary, because CLI does the following operations
(in order):
- loads an entry point,
- calls `inject_parser_options`,
- requires an entry point,
- creates plugin instance (`__call__`).
"""
description = zope.interface.Attribute("Short plugin description")
def __call__(config, name):
"""Create new `IPlugin`.
:param IConfig config: Configuration.
:param str name: Unique plugin name.
"""
def add_parser_arguments(add):
"""Add plugin arguments to the CLI argument parser.
def inject_parser_options(parser, name):
"""Inject argument parser options (flags).
:param callable add: Function that proxies calls to
`argparse.ArgumentParser.add_argument` prepending options
with unique plugin name prefix.
1. Be nice and prepend all options and destinations with
`~.option_namespace` and `~.dest_namespace`.
2. Inject options (flags) only. Positional arguments are not
allowed, as this would break the CLI.
:param ArgumentParser parser: (Almost) top-level CLI parser.
:param str name: Unique plugin name.
"""
# TODO: move to IPlugin?
class IPlugin(zope.interface.Interface):
"""Let's Encrypt plugin."""
description = zope.interface.Attribute("Short plugin description")
def prepare():
"""Prepare the plugin.
@@ -97,14 +97,15 @@ class ApacheConfigurator(augeas_configurator.AugeasConfigurator):
add("init-script", default=constants.DEFAULT_INIT_SCRIPT,
help="Path to the Apache init script (used for server reload/restart).")
def __init__(self, config, version=None):
def __init__(self, *args, **kwargs):
"""Initialize an Apache Configurator.
:param tup version: version of Apache as a tuple (2, 4, 7)
(used mostly for unittesting)
"""
super(ApacheConfigurator, self).__init__(config)
version = kwargs.pop('version', None)
super(ApacheConfigurator, self).__init__(*args, **kwargs)
# Verify that all directories and files exist with proper permissions
if os.geteuid() == 0:
@@ -124,8 +125,7 @@ class ApacheConfigurator(augeas_configurator.AugeasConfigurator):
def prepare(self):
"""Prepare the authenticator/installer."""
self.parser = parser.ApacheParser(
self.aug, self.config.apache_server_root,
self.config.apache_mod_ssl_conf)
self.aug, self.conf('server-root'), self.conf('mod-ssl-conf'))
# Check for errors in parsing files with Augeas
self.check_parsing_errors("httpd.aug")
@@ -143,7 +143,7 @@ class ApacheConfigurator(augeas_configurator.AugeasConfigurator):
# on initialization
self._prepare_server_https()
temp_install(self.config.apache_mod_ssl_conf)
temp_install(self.conf('mod-ssl-conf'))
def deploy_cert(self, domain, cert, key, cert_chain=None):
"""Deploys certificate to specified virtual host.
@@ -401,10 +401,10 @@ class ApacheConfigurator(augeas_configurator.AugeasConfigurator):
is appropriately listening on port 443.
"""
if not mod_loaded("ssl_module", self.config.apache_ctl):
if not mod_loaded("ssl_module", self.conf('ctl')):
logging.info("Loading mod_ssl into Apache Server")
enable_mod("ssl", self.config.apache_init_script,
self.config.apache_enmod)
enable_mod("ssl", self.conf('init-script'),
self.conf('enmod'))
# Check for Listen 443
# Note: This could be made to also look for ip:443 combo
@@ -587,9 +587,8 @@ class ApacheConfigurator(augeas_configurator.AugeasConfigurator):
:class:`~letsencrypt.client.plugins.apache.obj.VirtualHost`)
"""
if not mod_loaded("rewrite_module", self.config.apache_ctl):
enable_mod("rewrite", self.config.apache_init_script,
self.config.apache_enmod)
if not mod_loaded("rewrite_module", self.conf('ctl')):
enable_mod("rewrite", self.conf('init-script'), self.conf('enmod'))
general_v = self._general_vhost(ssl_vhost)
if general_v is None:
@@ -912,7 +911,7 @@ class ApacheConfigurator(augeas_configurator.AugeasConfigurator):
:rtype: bool
"""
return apache_restart(self.config.apache_init_script)
return apache_restart(self.conf('init-script'))
def config_test(self): # pylint: disable=no-self-use
"""Check the configuration of Apache for errors.
@@ -923,7 +922,7 @@ class ApacheConfigurator(augeas_configurator.AugeasConfigurator):
"""
try:
proc = subprocess.Popen(
["sudo", self.config.apache_ctl, "configtest"], # TODO: sudo?
["sudo", self.conf('ctl'), "configtest"], # TODO: sudo?
stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
stdout, stderr = proc.communicate()
@@ -970,13 +969,13 @@ class ApacheConfigurator(augeas_configurator.AugeasConfigurator):
"""
try:
proc = subprocess.Popen(
[self.config.apache_ctl, "-v"],
[self.conf('ctl'), "-v"],
stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
text = proc.communicate()[0]
except (OSError, ValueError):
raise errors.LetsEncryptConfiguratorError(
"Unable to run %s -v" % self.config.apache_ctl)
"Unable to run %s -v" % self.conf('ctl'))
regex = re.compile(r"Apache/([0-9\.]*)", re.IGNORECASE)
matches = regex.findall(text)
@@ -64,7 +64,7 @@ def get_apache_configurator(
# This just states that the ssl module is already loaded
mock_popen().communicate.return_value = ("ssl_module", "")
config = configurator.ApacheConfigurator(
mock.MagicMock(
config=mock.MagicMock(
apache_server_root=config_path,
apache_mod_ssl_conf=ssl_options,
le_vhost_ext="-le-ssl.conf",
@@ -73,7 +73,8 @@ def get_apache_configurator(
temp_checkpoint_dir=os.path.join(work_dir, "temp_checkpoints"),
in_progress_dir=os.path.join(backups, "IN_PROGRESS"),
work_dir=work_dir),
version)
name="apache",
version=version)
config.prepare()
+62
View File
@@ -0,0 +1,62 @@
"""Plugin common functions."""
import zope.interface
from letsencrypt.acme.jose import util as jose_util
from letsencrypt.client import interfaces
def option_namespace(name):
"""ArgumentParser options namespace (prefix of all options)."""
return name + '-'
def dest_namespace(name):
"""ArgumentParser dest namespace (prefix of all destinations)."""
return name + '_'
class Plugin(object):
"""Generic plugin."""
zope.interface.implements(interfaces.IPlugin)
zope.interface.classProvides(interfaces.IPluginFactory)
def __init__(self, config, name):
self.config = config
self.name = name
@property
def option_namespace(self):
return option_namespace(self.name)
@property
def dest_namespace(self):
return dest_namespace(self.name)
def dest(self, var):
"""Find a destination for given variable ``var``."""
# this should do exactly the same what ArgumentParser(arg),
# does to "arg" to compute "dest"
return self.dest_namespace + var.replace('-', '_')
def conf(self, var):
"""Find a configuration value for variable ``var``."""
return getattr(self.config, self.dest(var))
@classmethod
def inject_parser_options(cls, parser, name):
# dummy function, doesn't check if dest.startswith(self.dest_namespace)
def add(arg_name_no_prefix, *args, **kwargs):
return parser.add_argument(
"--{0}{1}".format(option_namespace(name), arg_name_no_prefix),
*args, **kwargs)
cls.add_parser_arguments(add)
@jose_util.abstractclassmethod
def add_parser_arguments(cls, add):
"""Add plugin arguments to the CLI argument parser.
:param callable add: Function that proxies calls to
`argparse.ArgumentParser.add_argument` prepending options
with unique plugin name prefix.
"""
+73 -28
View File
@@ -12,52 +12,97 @@ from letsencrypt.client import interfaces
from letsencrypt.client.display import ops as display_ops
def name_plugins(plugins):
# TODO: actually make it unambiguous...
names = {}
for plugin_cls, entry_points in plugins.iteritems():
entry_point = next(iter(entry_points)) # entry_points.peek()
names[plugin_cls] = entry_point.name
return names
class PluginEntryPoint(object):
"""Plugin entry point."""
PREFIX_FREE_DISTRIBUTIONS = ['letsencrypt']
"""Distributions for which prefix will be omitted."""
def __init__(self, entry_point):
self.name = self.entry_point_to_plugin_name(entry_point)
self.plugin_cls = entry_point.load()
self.entry_point = entry_point
self._initialized = None
@property
def initialized(self):
return self._initialized is not None
@classmethod
def entry_point_to_plugin_name(cls, entry_point):
if entry_point.dist.key in cls.PREFIX_FREE_DISTRIBUTIONS:
return entry_point.name
return entry_point.dist.key + ':' + entry_point.name
def init(self, config=None):
"""Memoized plugin inititialization."""
if not self.initialized:
self.entry_point.require() # fetch extras!
self._initialized = self.plugin_cls(config, self.name)
return self._initialized
def __repr__(self):
return 'PluginEntryPoint#{0}'.format(self.name)
def find_plugins():
"""Find plugins using setuptools entry points."""
plugins = collections.defaultdict(set)
for entry_point in pkg_resources.iter_entry_points(
constants.SETUPTOOLS_PLUGINS_ENTRY_POINT):
plugin_cls = entry_point.load()
plugins[plugin_cls].add(entry_point)
return plugins
class PluginRegistry(collections.Mapping):
"""Plugin registry."""
def __init__(self, plugins):
self.plugins = plugins
def filter_plugins(plugins, *ifaces_groups):
"""Filter plugins based on interfaces."""
return dict(
(plugin_cls, entry_points)
for plugin_cls, entry_points in plugins.iteritems()
if not ifaces_groups or any(
all(iface.implementedBy(plugin_cls) for iface in ifaces)
for ifaces in ifaces_groups))
@classmethod
def find_all(cls):
"""Find plugins using setuptools entry points."""
plugins = {}
for entry_point in pkg_resources.iter_entry_points(
constants.SETUPTOOLS_PLUGINS_ENTRY_POINT):
plugin_ep = PluginEntryPoint(entry_point)
assert plugin_ep.name not in plugins, (
'PREFIX_FREE_DISTRIBTIONS messed up')
plugins[plugin_ep.name] = plugin_ep
return cls(plugins)
def filter(self, *ifaces_groups):
"""Filter plugins based on interfaces."""
return type(self)(dict(
plugin_ep
for plugin_ep in self.plugins.iteritems()
if not ifaces_groups or any(
all(iface.implementedBy(plugin_ep.plugin_cls)
for iface in ifaces)
for ifaces in ifaces_groups)))
def __repr__(self):
return '{0}({1!r})'.format(self.__class__.__name__, self.plugins)
def __getitem__(self, name):
return self.plugins[name]
def __iter__(self):
return iter(self.plugins)
def __len__(self):
return len(self.plugins)
def verify_plugins(initialized, ifaces):
"""Verify plugin objects."""
verified = {}
for plugin_cls, plugin in initialized.iteritems():
for name, plugin_ep in initialized.iteritems():
verifies = True
for iface in ifaces: # zope.interface.providedBy(plugin)
try:
zope.interface.verify.verifyObject(iface, plugin)
zope.interface.verify.verifyObject(iface, plugin_ep.init())
except zope.interface.exceptions.BrokenImplementation:
if iface.implementedBy(plugin_cls):
if iface.implementedBy(plugin_ep.plugin_cls):
logging.debug(
"%s implements %s but object does "
"not verify", plugin_cls, iface.__name__)
"not verify", plugin_ep.plugin_cls, iface.__name__)
verifies = False
break
if verifies:
verified[plugin_cls] = plugin
verified[name] = plugin_ep
return verified
@@ -17,12 +17,14 @@ from letsencrypt.client import interfaces
from letsencrypt.client import le_util
from letsencrypt.client import reverter
from letsencrypt.client.plugins import common
from letsencrypt.client.plugins.nginx import constants
from letsencrypt.client.plugins.nginx import dvsni
from letsencrypt.client.plugins.nginx import parser
class NginxConfigurator(object):
class NginxConfigurator(common.Plugin):
# pylint: disable=too-many-instance-attributes,too-many-public-methods
"""Nginx configurator.
@@ -60,14 +62,15 @@ class NginxConfigurator(object):
"'nginx' binary, used for 'configtest' and retrieving nginx "
"version number.")
def __init__(self, config, version=None):
def __init__(self, *args, **kwargs):
"""Initialize an Nginx Configurator.
:param tup version: version of Nginx as a tuple (1, 4, 7)
(used mostly for unittesting)
"""
self.config = config
version = kwargs.pop("version", None)
super(NginxConfigurator, self).__init__(*args, **kwargs)
# Verify that all directories and files exist with proper permissions
if os.geteuid() == 0:
@@ -85,21 +88,21 @@ class NginxConfigurator(object):
self._enhance_func = {} # TODO: Support at least redirects
# Set up reverter
self.reverter = reverter.Reverter(config)
self.reverter = reverter.Reverter(self.config)
self.reverter.recovery_routine()
# This is called in determine_authenticator and determine_installer
def prepare(self):
"""Prepare the authenticator/installer."""
self.parser = parser.NginxParser(
self.config.nginx_server_root,
self.config.nginx_mod_ssl_conf)
self.conf('server-root'),
self.conf('mod-ssl-conf'))
# Set Version
if self.version is None:
self.version = self.get_version()
temp_install(self.config.nginx_mod_ssl_conf)
temp_install(self.conf('mod-ssl-conf'))
# Entry point in main.py for installing cert
def deploy_cert(self, domain, cert, key, cert_chain=None):
@@ -323,7 +326,7 @@ class NginxConfigurator(object):
:rtype: bool
"""
return nginx_restart(self.config.nginx_ctl)
return nginx_restart(self.conf('ctl'))
def config_test(self): # pylint: disable=no-self-use
"""Check the configuration of Nginx for errors.
@@ -334,7 +337,7 @@ class NginxConfigurator(object):
"""
try:
proc = subprocess.Popen(
[self.config.nginx_ctl, "-t"],
[self.conf('ctl'), "-t"],
stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
stdout, stderr = proc.communicate()
@@ -381,13 +384,13 @@ class NginxConfigurator(object):
"""
try:
proc = subprocess.Popen(
[self.config.nginx_ctl, "-V"],
[self.conf('ctl'), "-V"],
stdout=subprocess.PIPE,
stderr=subprocess.PIPE)
text = proc.communicate()[1] # nginx prints output to stderr
except (OSError, ValueError):
raise errors.LetsEncryptConfiguratorError(
"Unable to run %s -V" % self.config.nginx_ctl)
"Unable to run %s -V" % self.conf('ctl'))
version_regex = re.compile(r"nginx/([0-9\.]*)", re.IGNORECASE)
version_matches = version_regex.findall(text)
@@ -65,12 +65,13 @@ def get_nginx_configurator(
backups = os.path.join(work_dir, "backups")
config = configurator.NginxConfigurator(
mock.MagicMock(
config=mock.MagicMock(
nginx_server_root=config_path, nginx_mod_ssl_conf=ssl_options,
le_vhost_ext="-le-ssl.conf", backup_dir=backups,
config_dir=config_dir, work_dir=work_dir,
temp_checkpoint_dir=os.path.join(work_dir, "temp_checkpoints"),
in_progress_dir=os.path.join(backups, "IN_PROGRESS")),
version)
name="nginx",
version=version)
config.prepare()
return config
@@ -17,8 +17,10 @@ from letsencrypt.acme import challenges
from letsencrypt.client import achallenges
from letsencrypt.client import interfaces
from letsencrypt.client.plugins import common
class StandaloneAuthenticator(object):
class StandaloneAuthenticator(common.Plugin):
# pylint: disable=too-many-instance-attributes
"""Standalone authenticator.
@@ -29,15 +31,10 @@ class StandaloneAuthenticator(object):
"""
zope.interface.implements(interfaces.IAuthenticator)
zope.interface.classProvides(interfaces.IPluginFactory)
description = "Standalone Authenticator"
@classmethod
def add_parser_arguments(cls, add):
pass
def __init__(self, unused_config):
def __init__(self, *args, **kwargs):
super(StandaloneAuthenticator, self).__init__(*args, **kwargs)
self.child_pid = None
self.parent_pid = os.getpid()
self.subproc_state = None
@@ -53,7 +53,7 @@ class ChallPrefTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
def test_chall_pref(self):
self.assertEqual(self.authenticator.get_chall_pref("example.com"),
@@ -65,7 +65,7 @@ class SNICallbackTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
test_key = pkg_resources.resource_string(
"letsencrypt.client.tests", "testdata/rsa256_key.pem")
key = le_util.Key("foo", test_key)
@@ -108,7 +108,7 @@ class ClientSignalHandlerTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
self.authenticator.tasks = {"foononce.acme.invalid": "stuff"}
self.authenticator.child_pid = 12345
@@ -137,7 +137,7 @@ class SubprocSignalHandlerTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
self.authenticator.tasks = {"foononce.acme.invalid": "stuff"}
self.authenticator.child_pid = 12345
self.authenticator.parent_pid = 23456
@@ -189,7 +189,7 @@ class AlreadyListeningTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
@mock.patch("letsencrypt.client.plugins.standalone.authenticator.psutil."
"net_connections")
@@ -296,7 +296,7 @@ class PerformTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
test_key = pkg_resources.resource_string(
"letsencrypt.client.tests", "testdata/rsa256_key.pem")
@@ -375,7 +375,7 @@ class StartListenerTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
@mock.patch("letsencrypt.client.plugins.standalone.authenticator."
"Crypto.Random.atfork")
@@ -410,7 +410,7 @@ class DoParentProcessTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
@mock.patch("letsencrypt.client.plugins.standalone.authenticator."
"signal.signal")
@@ -464,7 +464,7 @@ class DoChildProcessTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
test_key = pkg_resources.resource_string(
"letsencrypt.client.tests", "testdata/rsa256_key.pem")
key = le_util.Key("foo", test_key)
@@ -562,7 +562,7 @@ class CleanupTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import \
StandaloneAuthenticator
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
self.achall = achallenges.DVSNI(
challb=acme_util.chall_to_challb(
challenges.DVSNI(r="whee", nonce="foononce"), "pending"),
@@ -595,7 +595,7 @@ class MoreInfoTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import (
StandaloneAuthenticator)
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
def test_more_info(self):
"""Make sure exceptions aren't raised."""
@@ -607,7 +607,7 @@ class InitTest(unittest.TestCase):
def setUp(self):
from letsencrypt.client.plugins.standalone.authenticator import (
StandaloneAuthenticator)
self.authenticator = StandaloneAuthenticator(None)
self.authenticator = StandaloneAuthenticator(config=None, name=None)
def test_prepare(self):
"""Make sure exceptions aren't raised.