From 03c9114958e428c5fe6b286df9eda3bd932dc9dc Mon Sep 17 00:00:00 2001 From: Jason Gerard DeRose Date: Tue, 30 Dec 2008 13:52:36 -0700 Subject: More docstring cleanup in ipalib.config --- ipalib/base.py | 7 +++--- ipalib/config.py | 50 +++++++++++++++++++++++++++++++----------- tests/test_ipalib/test_base.py | 7 +++--- 3 files changed, 44 insertions(+), 20 deletions(-) diff --git a/ipalib/base.py b/ipalib/base.py index 2d80a0778..1651b01d1 100644 --- a/ipalib/base.py +++ b/ipalib/base.py @@ -36,9 +36,10 @@ class ReadOnly(object): The point of this class is not to make it impossible to set or to delete attributes after an instance is locked, but to make it impossible to do so - *accidentally*. Rather than simply telling our programmers something like, - "Don't set any attributes on this ``FooBar`` instance because doing so wont - be thread-safe", this class gives us a way to enforce it. + *accidentally*. Rather than constantly reminding our programmers of things + like, for example, "Don't set any attributes on this ``FooBar`` instance + because doing so wont be thread-safe", this class offers a real way to + enforce read-only attribute usage. For example, before a `ReadOnly` instance is locked, you can set and delete its attributes as normal: diff --git a/ipalib/config.py b/ipalib/config.py index c3c3a95ce..84c0aab4c 100644 --- a/ipalib/config.py +++ b/ipalib/config.py @@ -18,11 +18,14 @@ # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA """ -Basic configuration management. +Process-wide static configuration and environment. -This module handles the reading and representation of basic local settings. -It will also take care of settings that can be discovered by different -methods, such as DNS. +The standard run-time instance of the `Env` class is initialized early in the +`ipalib` process and is then locked into a read-only state, after which no +further changes can be made to the environment throughout the remaining life +of the process. + +For the per-request thread-local information, see `ipalib.request`. """ from ConfigParser import RawConfigParser, ParsingError @@ -288,6 +291,8 @@ class Env(object): (0, 3) Also see `Env._merge_from_file()`. + + :param kw: Variables provides as keyword arguments. """ i = 0 for (key, value) in kw.iteritems(): @@ -311,8 +316,23 @@ class Env(object): containing first the number of variables that were actually set, and second the total number of variables found in ``config_file``. + This method will raise a ``ValueError`` if ``config_file`` is not an + absolute path. For example: + + >>> env = Env() + >>> env._merge_from_file('my/config.conf') + Traceback (most recent call last): + ... + ValueError: config_file must be an absolute path; got 'my/config.conf' + Also see `Env._merge()`. + + :param config_file: Absolute path of the configuration file to load. """ + if path.abspath(config_file) != config_file: + raise ValueError( + 'config_file must be an absolute path; got %r' % config_file + ) if not path.isfile(config_file): return parser = RawConfigParser() @@ -361,8 +381,8 @@ class Env(object): `Env._merge()`. The intended use of ``overrides`` is to merge-in variables specified on the command-line. - 3. Intelligently fill-in the ``in_tree``, ``context``, ``conf``, - and ``conf_default`` variables if they haven`t been set already. + 3. Intelligently fill-in the *in_tree*, *context*, *conf*, and + *conf_default* variables if they haven`t been set already. Also see `Env._finalize_core()`, the next method in the bootstrap sequence. @@ -413,22 +433,24 @@ class Env(object): ``self.conf_default`` (if it exists) by calling `Env._merge_from_file()`. - 4. Intelligently fill-in the ``in_server`` and ``log`` variables + 4. Intelligently fill-in the *in_server* and *log* variables if they haven't already been set. - 5. Merge in the internal defaults by calling `Env._merge()`. In - normal circumstances, these internal defaults will simply be - those specified in `constants.DEFAULT_CONFIG`. + 5. Merge-in the variables in ``defaults`` by calling `Env._merge()`. + In normal circumstances ``defaults`` will simply be those + specified in `constants.DEFAULT_CONFIG`. - After this method is called, the all environment variables - used by all the built-in plugins will be available. As such, this - method should be called *before* any plugins are loaded. + After this method is called, all the environment variables used by all + the built-in plugins will be available. As such, this method should be + called *before* any plugins are loaded. After this method has finished, the `Env` instance is still writable so that 3rd-party plugins can set variables they may require as the plugins are registered. Also see `Env._finalize()`, the final method in the bootstrap sequence. + + :param defaults: Internal defaults for all built-in variables. """ self.__doing('_finalize_core') self.__do_if_not_done('_bootstrap') @@ -464,6 +486,8 @@ class Env(object): This method should be called after all plugins have been loaded and after `plugable.API.finalize()` has been called. + + :param lastchance: Any final variables to merge-in before locking. """ self.__doing('_finalize') self.__do_if_not_done('_finalize_core') diff --git a/tests/test_ipalib/test_base.py b/tests/test_ipalib/test_base.py index 9feac6acf..49d5f39df 100644 --- a/tests/test_ipalib/test_base.py +++ b/tests/test_ipalib/test_base.py @@ -22,7 +22,7 @@ Test the `ipalib.base` module. """ from tests.util import ClassChecker, raises -from ipalib.constants import NAME_REGEX +from ipalib.constants import NAME_REGEX, NAME_ERROR from ipalib.constants import TYPE_ERROR, SET_ERROR, DEL_ERROR from ipalib import base @@ -107,10 +107,9 @@ def test_check_name(): assert name is f(name) e = raises(TypeError, f, unicode(name)) assert str(e) == TYPE_ERROR % ('name', str, unicode(name), unicode) - error = 'name must match %r; got %r' for name in nope: e = raises(ValueError, f, name) - assert str(e) == error % (NAME_REGEX, name) + assert str(e) == NAME_ERROR % (NAME_REGEX, name) for name in okay: e = raises(ValueError, f, name.upper()) - assert str(e) == error % (NAME_REGEX, name.upper()) + assert str(e) == NAME_ERROR % (NAME_REGEX, name.upper()) -- cgit