From 7f57de5bb28b33bf321904e3171e9bb45116ddfa Mon Sep 17 00:00:00 2001 From: Victor Stinner Date: Thu, 15 Oct 2015 14:57:35 +0200 Subject: [PATCH] Use versionadded and versionchanged in doc Document in which version new types and functions were added using ".. versionadded:: x.y". Document changes using ".. versionchanged:: x.y." For new modules, add the versionadded tag in the module top docstring, not on each type/function. Add fileutils to documentation. The doc part was forgotten during the graduation. Add docstrings to convert versions of versionutils. I used "git blame" + "git tag --contains=SHA1" to find these version, and then I checked manually each version. Change-Id: Ia2f00aa29eb36410a49fc1d350896a569a7737a1 --- doc/source/api/fileutils.rst | 7 +++++++ doc/source/index.rst | 1 + oslo_utils/encodeutils.py | 2 ++ oslo_utils/eventletutils.py | 13 ++++++++++++ oslo_utils/excutils.py | 7 +++++++ oslo_utils/fileutils.py | 8 ++++++++ oslo_utils/fixture.py | 6 ++++++ oslo_utils/importutils.py | 25 +++++++++++++++++++--- oslo_utils/netutils.py | 19 ++++++++++++++++- oslo_utils/reflection.py | 11 +++++++++- oslo_utils/strutils.py | 22 +++++++++++++++++++- oslo_utils/timeutils.py | 40 ++++++++++++++++++++++++++++++++---- oslo_utils/uuidutils.py | 5 +++++ oslo_utils/versionutils.py | 16 +++++++++++++++ 14 files changed, 172 insertions(+), 10 deletions(-) create mode 100644 doc/source/api/fileutils.rst diff --git a/doc/source/api/fileutils.rst b/doc/source/api/fileutils.rst new file mode 100644 index 0000000..575bedf --- /dev/null +++ b/doc/source/api/fileutils.rst @@ -0,0 +1,7 @@ +============= + fileutils +============= + +.. automodule:: oslo_utils.fileutils + :members: + diff --git a/doc/source/index.rst b/doc/source/index.rst index 4a9e6db..9f00c10 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -21,6 +21,7 @@ API Documentation api/encodeutils api/eventletutils api/excutils + api/fileutils api/fixture api/importutils api/netutils diff --git a/oslo_utils/encodeutils.py b/oslo_utils/encodeutils.py index 52da98a..82ce6af 100644 --- a/oslo_utils/encodeutils.py +++ b/oslo_utils/encodeutils.py @@ -104,6 +104,8 @@ def exception_to_unicode(exc): If the exception message is a bytes strings, try to decode it from UTF-8 (superset of ASCII), from the locale encoding, or fallback to decoding it from ISO-8859-1 (which never fails). + + .. versionadded:: 1.6 """ msg = None if six.PY2: diff --git a/oslo_utils/eventletutils.py b/oslo_utils/eventletutils.py index 1d6a6b8..2d2a299 100644 --- a/oslo_utils/eventletutils.py +++ b/oslo_utils/eventletutils.py @@ -14,6 +14,12 @@ # License for the specific language governing permissions and limitations # under the License. +""" +Eventlet utils helper module. + +.. versionadded:: 1.3 +""" + import threading import warnings @@ -35,6 +41,13 @@ _ALL_PATCH = frozenset(['__builtin__', 'MySQLdb', 'os', def fetch_current_thread_functor(): + """Get the current thread. + + If eventlet is used to monkey-patch the threading module, return the + current eventlet greenthread. Otherwise, return the current Python thread. + + .. versionadded:: 1.5 + """ # Until https://github.com/eventlet/eventlet/issues/172 is resolved # or addressed we have to use complicated workaround to get a object # that will not be recycled; the usage of threading.current_thread() diff --git a/oslo_utils/excutils.py b/oslo_utils/excutils.py index 52073aa..66e0171 100644 --- a/oslo_utils/excutils.py +++ b/oslo_utils/excutils.py @@ -45,6 +45,8 @@ class CausedByException(Exception): should itself be an exception instance, this is useful for creating a chain of exceptions for versions of python where this is not yet implemented/supported natively. + + .. versionadded:: 2.4 """ def __init__(self, message, cause=None): super(CausedByException, self).__init__(message) @@ -126,6 +128,8 @@ def raise_with_cause(exc_cls, message, *args, **kwargs): exceptions constructor. :param kwargs: any additional keyword arguments to pass to the exceptions constructor. + + .. versionadded:: 1.6 """ if 'cause' not in kwargs: exc_type, exc, exc_tb = sys.exc_info() @@ -174,6 +178,9 @@ class save_and_reraise_exception(object): [if statements to determine whether to raise a new exception] # Not raising a new exception, so reraise ctxt.reraise = True + + .. versionchanged:: 1.4 + Added *logger* optional parameter. """ def __init__(self, reraise=True, logger=None): self.reraise = reraise diff --git a/oslo_utils/fileutils.py b/oslo_utils/fileutils.py index b2c9a7e..788d338 100644 --- a/oslo_utils/fileutils.py +++ b/oslo_utils/fileutils.py @@ -13,6 +13,12 @@ # License for the specific language governing permissions and limitations # under the License. +""" +File utilities. + +.. versionadded:: 1.8 +""" + import contextlib import errno import logging @@ -87,6 +93,8 @@ def write_to_tempfile(content, path=None, suffix='', prefix='tmp'): For example: it can be used in database tests for creating configuration files. + + .. versionadded:: 1.9 """ if path: ensure_tree(path) diff --git a/oslo_utils/fixture.py b/oslo_utils/fixture.py index 9d91695..9526154 100644 --- a/oslo_utils/fixture.py +++ b/oslo_utils/fixture.py @@ -14,6 +14,12 @@ # License for the specific language governing permissions and limitations # under the License. +""" +Test fixtures. + +.. versionadded:: 1.3 +""" + import fixtures from oslo_utils import timeutils diff --git a/oslo_utils/importutils.py b/oslo_utils/importutils.py index 15fd9bf..3ddcfde 100644 --- a/oslo_utils/importutils.py +++ b/oslo_utils/importutils.py @@ -22,7 +22,10 @@ import traceback def import_class(import_str): - """Returns a class from a string including module and class.""" + """Returns a class from a string including module and class. + + .. versionadded:: 0.3 + """ mod_str, _sep, class_str = import_str.rpartition('.') __import__(mod_str) try: @@ -34,7 +37,10 @@ def import_class(import_str): def import_object(import_str, *args, **kwargs): - """Import a class and return an instance of it.""" + """Import a class and return an instance of it. + + .. versionadded:: 0.3 + """ return import_class(import_str)(*args, **kwargs) @@ -44,6 +50,12 @@ def import_object_ns(name_space, import_str, *args, **kwargs): Imports a class and return an instance of it, first by trying to find the class in a default namespace, then failing back to a full path if not found in the default namespace. + + .. versionadded:: 0.3 + + .. versionchanged:: 2.6 + Don't capture :exc:`ImportError` when instanciating the object, only + when importing the object class. """ import_value = "%s.%s" % (name_space, import_str) try: @@ -54,12 +66,19 @@ def import_object_ns(name_space, import_str, *args, **kwargs): def import_module(import_str): - """Import a module.""" + """Import a module. + + .. versionadded:: 0.3 + """ __import__(import_str) return sys.modules[import_str] def import_versioned_module(version, submodule=None): + """Import a versioned module. + + .. versionadded:: 0.3 + """ module = 'oslo.v%s' % version if submodule: module = '.'.join((module, submodule)) diff --git a/oslo_utils/netutils.py b/oslo_utils/netutils.py index bdb4632..43c9923 100644 --- a/oslo_utils/netutils.py +++ b/oslo_utils/netutils.py @@ -87,6 +87,8 @@ def is_valid_ipv4(address): :param address: Value to verify :type address: string :returns: bool + + .. versionadded:: 1.1 """ try: return netaddr.valid_ipv4(address) @@ -100,6 +102,8 @@ def is_valid_ipv6(address): :param address: Value to verify :type address: string :returns: bool + + .. versionadded:: 1.1 """ try: return netaddr.valid_ipv6(address) @@ -117,6 +121,8 @@ def get_ipv6_addr_by_EUI64(prefix, mac): :param mac: IEEE 802 48-bit MAC address. :returns: IPv6 address on success. :raises ValueError, TypeError: For any invalid input. + + .. versionadded:: 1.4 """ # Check if the prefix is an IPv4 address if netaddr.valid_ipv4(prefix): @@ -143,6 +149,7 @@ def is_ipv6_enabled(): :returns: True if the platform has IPv6 support, False otherwise. + .. versionadded:: 1.4 """ global _IS_IPV6_ENABLED @@ -164,12 +171,17 @@ def is_valid_ip(address): :param address: Value to verify :type address: string :returns: bool + + .. versionadded:: 1.1 """ return is_valid_ipv4(address) or is_valid_ipv6(address) def is_valid_port(port): - """Verify that port represents a valid port number.""" + """Verify that port represents a valid port number. + + .. versionadded:: 1.1.1 + """ try: val = int(port) except (ValueError, TypeError): @@ -185,6 +197,11 @@ def get_my_ipv4(): were to be sent out to some well known address on the Internet. In this case, IP from RFC5737 is used, but the specific address does not matter much. No traffic is actually sent. + + .. versionadded:: 1.1 + + .. versionchanged:: 1.2.1 + Return ``'127.0.0.1'`` if there is no default interface. """ try: csock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) diff --git a/oslo_utils/reflection.py b/oslo_utils/reflection.py index 34714fc..f8ef3b1 100644 --- a/oslo_utils/reflection.py +++ b/oslo_utils/reflection.py @@ -14,6 +14,12 @@ # License for the specific language governing permissions and limitations # under the License. +""" +Reflection module. + +.. versionadded:: 1.1 +""" + import inspect import types @@ -31,7 +37,10 @@ _BUILTIN_MODULES = ('builtins', '__builtin__', '__builtins__', 'exceptions') def get_members(obj, exclude_hidden=True): - """Yields the members of an object, filtering by hidden/not hidden.""" + """Yields the members of an object, filtering by hidden/not hidden. + + .. versionadded:: 2.3 + """ for (name, value) in inspect.getmembers(obj): if name.startswith("_") and exclude_hidden: continue diff --git a/oslo_utils/strutils.py b/oslo_utils/strutils.py index 62912e2..2c643dc 100644 --- a/oslo_utils/strutils.py +++ b/oslo_utils/strutils.py @@ -213,7 +213,7 @@ def to_slug(value, incoming=None, errors="strict"): def mask_password(message, secret="***"): - """Replace password with 'secret' in message. + """Replace password with *secret* in message. :param message: The string which includes security information. :param secret: value with which to replace passwords. @@ -231,6 +231,24 @@ def mask_password(message, secret="***"): "'original_password' : '***'" >>> mask_password("u'original_password' : u'aaaaa'") "u'original_password' : u'***'" + + .. versionadded:: 0.2 + + .. versionchanged:: 1.1 + Replace also ``'auth_token'``, ``'new_pass'`` and ``'auth_password'`` + keys. + + .. versionchanged:: 1.1.1 + Replace also ``'secret_uuid'`` key. + + .. versionchanged:: 1.5 + Replace also ``'sys_pswd'`` key. + + .. versionchanged:: 2.6 + Replace also ``'token'`` key. + + .. versionchanged:: 2.7 + Replace also ``'secret'`` key. """ try: @@ -262,6 +280,8 @@ def is_int_like(val): :param val: Value to verify :type val: string :returns: bool + + .. versionadded:: 1.1 """ try: return six.text_type(int(val)) == six.text_type(val) diff --git a/oslo_utils/timeutils.py b/oslo_utils/timeutils.py index 2f03259..47ceb5e 100644 --- a/oslo_utils/timeutils.py +++ b/oslo_utils/timeutils.py @@ -105,7 +105,12 @@ def normalize_time(timestamp): def is_older_than(before, seconds): - """Return True if before is older than seconds.""" + """Return True if before is older than seconds. + + .. versionchanged:: 1.7 + Accept datetime string with timezone information. + Fix comparison with timezone aware datetime. + """ if isinstance(before, six.string_types): before = parse_isotime(before) @@ -115,7 +120,12 @@ def is_older_than(before, seconds): def is_newer_than(after, seconds): - """Return True if after is newer than seconds.""" + """Return True if after is newer than seconds. + + .. versionchanged:: 1.7 + Accept datetime string with timezone information. + Fix comparison with timezone aware datetime. + """ if isinstance(after, six.string_types): after = parse_isotime(after) @@ -129,6 +139,8 @@ def utcnow_ts(microsecond=False): See :py:class:`oslo_utils.fixture.TimeFixture`. + .. versionchanged:: 1.3 + Added optional *microsecond* parameter. """ if utcnow.override_time is None: # NOTE(kgriffs): This is several times faster @@ -152,6 +164,8 @@ def utcnow(with_timezone=False): See :py:class:`oslo_utils.fixture.TimeFixture`. + .. versionchanged:: 1.6 + Added *with_timezone* parameter. """ if utcnow.override_time: try: @@ -171,6 +185,9 @@ def utcnow(with_timezone=False): def iso8601_from_timestamp(timestamp, microsecond=False): """Returns an iso8601 formatted date from timestamp. + .. versionchanged:: 1.3 + Added optional *microsecond* parameter. + .. deprecated:: 1.5.0 Use :func:`datetime.datetime.utcfromtimestamp` and :func:`datetime.datetime.isoformat` instead. @@ -227,7 +244,11 @@ def clear_time_override(): def marshall_now(now=None): - """Make an rpc-safe datetime with microseconds.""" + """Make an rpc-safe datetime with microseconds. + + .. versionchanged:: 1.6 + Timezone information is now serialized instead of being stripped. + """ if not now: now = utcnow() d = dict(day=now.day, month=now.month, year=now.year, hour=now.hour, @@ -239,7 +260,14 @@ def marshall_now(now=None): def unmarshall_time(tyme): - """Unmarshall a datetime dict.""" + """Unmarshall a datetime dict. + + .. versionchanged:: 1.5 + Drop leap second. + + .. versionchanged:: 1.6 + Added support for timezone information. + """ # NOTE(ihrachys): datetime does not support leap seconds, # so the best thing we can do for now is dropping them @@ -298,6 +326,8 @@ class Split(object): """A *immutable* stopwatch split. See: http://en.wikipedia.org/wiki/Stopwatch for what this is/represents. + + .. versionadded:: 1.4 """ __slots__ = ['_elapsed', '_length'] @@ -337,6 +367,8 @@ class StopWatch(object): depending on operating system and python version). .. _monotonic: https://pypi.python.org/pypi/monotonic/ + + .. versionadded:: 1.4 """ _STARTED = 'STARTED' _STOPPED = 'STOPPED' diff --git a/oslo_utils/uuidutils.py b/oslo_utils/uuidutils.py index c7cc587..5a48ae6 100644 --- a/oslo_utils/uuidutils.py +++ b/oslo_utils/uuidutils.py @@ -15,6 +15,8 @@ """ UUID related utilities and helper functions. + +.. versionadded:: 1.1 """ import uuid @@ -42,6 +44,9 @@ def is_uuid_like(val): :param val: Value to verify :type val: string :returns: bool + + .. versionchanged:: 1.1.1 + Support non-lowercase UUIDs. """ try: return str(uuid.UUID(val)).replace('-', '') == _format_uuid_string(val) diff --git a/oslo_utils/versionutils.py b/oslo_utils/versionutils.py index eb1e554..09f867a 100644 --- a/oslo_utils/versionutils.py +++ b/oslo_utils/versionutils.py @@ -15,6 +15,8 @@ """ Helpers for comparing version strings. + +.. versionadded:: 1.6 """ import logging @@ -51,6 +53,12 @@ def is_compatible(requested_version, current_version, same_major=True): def convert_version_to_int(version): + """Convert a version to an integer. + + *version* must be a string with dots or a tuple of integers. + + .. versionadded:: 2.0 + """ try: if isinstance(version, six.string_types): version = convert_version_to_tuple(version) @@ -62,6 +70,10 @@ def convert_version_to_int(version): def convert_version_to_str(version_int): + """Convert a version integer to a string with dots. + + .. versionadded:: 2.0 + """ version_numbers = [] factor = 1000 while version_int != 0: @@ -73,4 +85,8 @@ def convert_version_to_str(version_int): def convert_version_to_tuple(version_str): + """Convert a version string with dots to a tuple. + + .. versionadded:: 2.0 + """ return tuple(int(part) for part in version_str.split('.'))