Add config table sphinx directive

In the past we had used an openstack-manuals tool to manually generate
config option tables that would then be included into driver config
documentation.

With the move of documentation in-tree and the deprecation and removal
of that tool, we have ended up with options that are no longer being
updated when drivers change, or maintainers are left manually updating
the existing tables.

This addes a sphinx extension to use a new config-table directive to
automatically pull in config options from the source so we no longer
need to perform any manual action to pick up changes.

Change-Id: I625fb96229001c326ed2400155e2d067279a400e
This commit is contained in:
Sean McGinnis 2018-04-24 16:29:24 -05:00
parent 45e78aaa72
commit c87da91757
9 changed files with 143 additions and 114 deletions

View File

@ -102,7 +102,7 @@ RBD_OPTS = [
help='Set to True for driver to report total capacity as a '
'dynamic value -used + current free- and to False to '
'report a static value -quota max bytes if defined and '
'global size of cluster if not-.'),
'global size of cluster if not.'),
cfg.BoolOpt('rbd_exclusive_cinder_pool', default=False,
help="Set to True if the pool is used exclusively by Cinder. "
"On exclusive use driver won't query images' provisioned "

127
doc/ext/driver_opts.py Normal file
View File

@ -0,0 +1,127 @@
# Copyright (c) 2018 Huawei Technologies Co., Ltd.
# All Rights Reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.
"""Sphinx extension to be able to extract driver config options from code."""
import importlib
from docutils import nodes
from docutils.parsers import rst
from docutils.parsers.rst import directives
from docutils import statemachine as sm
from oslo_config import cfg
class ConfigTableDirective(rst.Directive):
"""Directive to extract config options into docs output."""
option_spec = {
'table-title': directives.unchanged,
'config-target': directives.unchanged,
}
has_content = True
def _doc_module(self, module):
"""Extract config options from module."""
options = []
try:
mod = importlib.import_module(module)
for prop in dir(mod):
thing = getattr(mod, prop)
if isinstance(thing, cfg.Opt):
# An individual config option
options.append(thing)
elif (isinstance(thing, list) and len(thing) > 0 and
isinstance(thing[0], cfg.Opt)):
# A list of config opts
options.extend(thing)
except Exception as e:
self.error('Unable to import {}: {}'.format(module, e))
return options
def _get_default(self, opt):
"""Tries to pick the best text to use as the default."""
if hasattr(opt, 'sample_default') and opt.sample_default:
return opt.sample_default
if type(opt.default) == list:
return ', '.join(str(item) for item in opt.default)
result = str(opt.default)
if not result:
result = '<>'
return result
def run(self):
"""Load and find config options to document."""
modules = [c.strip() for c in self.content if c.strip()]
if not modules:
raise self.error('No modules provided to document.')
env = self.state.document.settings.env
app = env.app
result = sm.ViewList()
source = '<{}>'.format(__name__)
target = self.options.get('config-target', '')
title = self.options.get(
'table-title',
'Description of {} configuration options'.format(target))
result.append('.. _{}:'.format(title.replace(' ', '-')), source)
result.append('', source)
result.append('.. list-table:: {}'.format(title), source)
result.append(' :header-rows: 1', source)
result.append(' :class: config-ref-table', source)
result.append('', source)
result.append(' * - Configuration option = Default value', source)
result.append(' - Description', source)
options = []
for module in modules:
retval = self._doc_module(module)
if retval:
options.extend(retval)
else:
app.info('[config-table] No options found in {}'.format(
module))
# Get options sorted alphabetically but with deprecated options last
list.sort(options, key=lambda opt: opt.name)
list.sort(options, key=lambda opt: opt.deprecated_for_removal)
for opt in options:
result.append(
' * - ``{}`` = ``{}``'.format(
opt.name, self._get_default(opt)),
source)
result.append(
' - ({}) {}{}'.format(
opt.type, opt.help,
' **DEPRECATED**' if opt.deprecated_for_removal else ''),
source)
node = nodes.section()
node.document = self.state.document
self.state.nested_parse(result, 0, node)
return node.children
def setup(app):
app.add_directive('config-table', ConfigTableDirective)

View File

@ -58,6 +58,7 @@ extensions = ['sphinx.ext.coverage',
'stevedore.sphinxext',
'oslo_config.sphinxconfiggen',
'ext.cinder_driverlist',
'ext.driver_opts',
'oslo_policy.sphinxext',
'oslo_policy.sphinxpolicygen',
'sphinxcontrib.apidoc',

View File

@ -87,4 +87,7 @@ Driver options
The following table contains the configuration options supported by the
Ceph RADOS Block Device driver.
.. include:: ../../tables/cinder-storage_ceph.inc
.. config-table::
:config-target: Ceph storage
cinder.volume.drivers.rbd

View File

@ -22,7 +22,10 @@ Use the following options to configure for the iSER transport:
volume_driver = cinder.volume.drivers.lvm.LVMVolumeDriver
iscsi_protocol = iser
.. include:: ../../tables/cinder-lvm.inc
.. config-table::
:config-target: LVM
cinder.volume.drivers.lvm
.. caution::

View File

@ -33,7 +33,12 @@ in the ``cinder.conf`` configuration file:
The following table contains the options supported by the NFS driver.
.. include:: ../../tables/cinder-storage_nfs.inc
.. _cinder-storage_nfs:
.. config-table::
:config-target: NFS storage
cinder.volume.drivers.nfs
.. note::

View File

@ -1,32 +0,0 @@
..
Warning: Do not edit this file. It is automatically generated from the
software project's code and your changes will be overwritten.
The tool to generate this file lives in openstack-doc-tools repository.
Please make any changes needed in the code, then run the
autogenerate-config-doc tool from the openstack-doc-tools repository, or
ask for help on the documentation mailing list, IRC channel or meeting.
.. _cinder-lvm:
.. list-table:: Description of LVM configuration options
:header-rows: 1
:class: config-ref-table
* - Configuration option = Default value
- Description
* - **[DEFAULT]**
-
* - ``lvm_conf_file`` = ``/etc/cinder/lvm.conf``
- (String) LVM conf file to use for the LVM driver in Cinder; this setting is ignored if the specified file does not exist (You can also specify 'None' to not use a conf file even if one exists).
* - ``lvm_max_over_subscription_ratio`` = ``1.0``
- (Floating point) max_over_subscription_ratio setting for the LVM driver. If set, this takes precedence over the general max_over_subscription_ratio option. If None, the general option is used.
* - ``lvm_mirrors`` = ``0``
- (Integer) If >0, create LVs with multiple mirrors. Note that this requires lvm_mirrors + 2 PVs with available space
* - ``lvm_suppress_fd_warnings`` = ``False``
- (Boolean) Suppress leaked file descriptor warnings in LVM commands.
* - ``lvm_type`` = ``auto``
- (String) Type of LVM volumes to deploy; (default, thin, or auto). Auto defaults to thin if thin is supported.
* - ``volume_group`` = ``cinder-volumes``
- (String) Name for the VG that will contain exported volumes

View File

@ -1,44 +0,0 @@
..
Warning: Do not edit this file. It is automatically generated from the
software project's code and your changes will be overwritten.
The tool to generate this file lives in openstack-doc-tools repository.
Please make any changes needed in the code, then run the
autogenerate-config-doc tool from the openstack-doc-tools repository, or
ask for help on the documentation mailing list, IRC channel or meeting.
.. _cinder-storage_ceph:
.. list-table:: Description of Ceph storage configuration options
:header-rows: 1
:class: config-ref-table
* - Configuration option = Default value
- Description
* - **[DEFAULT]**
-
* - ``rados_connect_timeout`` = ``-1``
- (Integer) Timeout value (in seconds) used when connecting to ceph cluster. If value < 0, no timeout is set and default librados value is used.
* - ``rados_connection_interval`` = ``5``
- (Integer) Interval value (in seconds) between connection retries to ceph cluster.
* - ``rados_connection_retries`` = ``3``
- (Integer) Number of retries if connection to ceph cluster failed.
* - ``rbd_ceph_conf`` =
- (String) Path to the ceph configuration file
* - ``rbd_cluster_name`` = ``ceph``
- (String) The name of ceph cluster
* - ``rbd_flatten_volume_from_snapshot`` = ``False``
- (Boolean) Flatten volumes created from snapshots to remove dependency from volume to snapshot
* - ``rbd_max_clone_depth`` = ``5``
- (Integer) Maximum number of nested volume clones that are taken before a flatten occurs. Set to 0 to disable cloning.
* - ``rbd_pool`` = ``rbd``
- (String) The RADOS pool where rbd volumes are stored
* - ``rbd_secret_uuid`` = ``None``
- (String) The libvirt uuid of the secret for the rbd_user volumes
* - ``rbd_store_chunk_size`` = ``4``
- (Integer) Volumes will be chunked into objects of this size (in megabytes).
* - ``rbd_user`` = ``None``
- (String) The RADOS client name for accessing rbd volumes - only set when using cephx authentication
* - ``replication_connect_timeout`` = ``5``
- (Integer) Timeout value (in seconds) used when connecting to ceph cluster to do a demotion/promotion of volumes. If value < 0, no timeout is set and default librados value is used.

View File

@ -1,34 +0,0 @@
..
Warning: Do not edit this file. It is automatically generated from the
software project's code and your changes will be overwritten.
The tool to generate this file lives in openstack-doc-tools repository.
Please make any changes needed in the code, then run the
autogenerate-config-doc tool from the openstack-doc-tools repository, or
ask for help on the documentation mailing list, IRC channel or meeting.
.. _cinder-storage_nfs:
.. list-table:: Description of NFS storage configuration options
:header-rows: 1
:class: config-ref-table
* - Configuration option = Default value
- Description
* - **[DEFAULT]**
-
* - ``nfs_mount_attempts`` = ``3``
- (Integer) The number of attempts to mount NFS shares before raising an error. At least one attempt will be made to mount an NFS share, regardless of the value specified.
* - ``nfs_mount_options`` = ``None``
- (String) Mount options passed to the NFS client. See section of the NFS man page for details.
* - ``nfs_mount_point_base`` = ``$state_path/mnt``
- (String) Base dir containing mount points for NFS shares.
* - ``nfs_qcow2_volumes`` = ``False``
- (Boolean) Create volumes as QCOW2 files rather than raw files.
* - ``nfs_shares_config`` = ``/etc/cinder/nfs_shares``
- (String) File with the list of available NFS shares.
* - ``nfs_snapshot_support`` = ``False``
- (Boolean) Enable support for snapshots on the NFS driver. Platforms using libvirt <1.2.7 will encounter issues with this feature.
* - ``nfs_sparsed_volumes`` = ``True``
- (Boolean) Create volumes as sparsed files which take no space. If set to False volume is created as regular file. In such case volume creation takes a lot of time.