Expose lockutils opts to config generator

* Adds an opts module for the config generator to use.
* Makes the opts in lockutils private since we don't want consumers
  using them directly.
* Moves the options to an oslo_concurrency group with appropriate
  deprecated_group settings to keep existing configs working.

Change-Id: Ifdb4d99e27588e8a91d941c60b248ea526c06e0a
This commit is contained in:
Ben Nemec 2014-09-26 16:02:26 +00:00
parent 5cba7d1830
commit c98d5edc44
4 changed files with 68 additions and 17 deletions

View File

@ -35,23 +35,25 @@ from oslo.concurrency.openstack.common import fileutils
LOG = logging.getLogger(__name__) LOG = logging.getLogger(__name__)
util_opts = [ _opts = [
cfg.BoolOpt('disable_process_locking', default=False, cfg.BoolOpt('disable_process_locking', default=False,
help='Enables or disables inter-process locks.'), help='Enables or disables inter-process locks.',
deprecated_group='DEFAULT'),
cfg.StrOpt('lock_path', cfg.StrOpt('lock_path',
default=os.environ.get("OSLO_LOCK_PATH"), default=os.environ.get("OSLO_LOCK_PATH"),
help='Directory to use for lock files. For security, the ' help='Directory to use for lock files. For security, the '
'specified directory should only be writable by the user ' 'specified directory should only be writable by the user '
'running the processes that need locking.') 'running the processes that need locking.',
deprecated_group='DEFAULT')
] ]
CONF = cfg.CONF CONF = cfg.CONF
CONF.register_opts(util_opts) CONF.register_opts(_opts, group='oslo_concurrency')
def set_defaults(lock_path): def set_defaults(lock_path):
cfg.set_defaults(util_opts, lock_path=lock_path) cfg.set_defaults(_opts, lock_path=lock_path)
class _FileLock(object): class _FileLock(object):
@ -180,7 +182,7 @@ def _get_lock_path(name, lock_file_prefix, lock_path=None):
sep = '' if lock_file_prefix.endswith('-') else '-' sep = '' if lock_file_prefix.endswith('-') else '-'
name = '%s%s%s' % (lock_file_prefix, sep, name) name = '%s%s%s' % (lock_file_prefix, sep, name)
local_lock_path = lock_path or CONF.lock_path local_lock_path = lock_path or CONF.oslo_concurrency.lock_path
if not local_lock_path: if not local_lock_path:
raise cfg.RequiredOptError('lock_path') raise cfg.RequiredOptError('lock_path')
@ -243,7 +245,7 @@ def lock(name, lock_file_prefix=None, external=False, lock_path=None):
with int_lock: with int_lock:
LOG.debug('Acquired semaphore "%(lock)s"', {'lock': name}) LOG.debug('Acquired semaphore "%(lock)s"', {'lock': name})
try: try:
if external and not CONF.disable_process_locking: if external and not CONF.oslo_concurrency.disable_process_locking:
ext_lock = external_lock(name, lock_file_prefix, lock_path) ext_lock = external_lock(name, lock_file_prefix, lock_path)
with ext_lock: with ext_lock:
yield ext_lock yield ext_lock

45
oslo/concurrency/opts.py Normal file
View File

@ -0,0 +1,45 @@
# Copyright 2014 Red Hat, Inc.
#
# 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.
__all__ = [
'list_opts',
]
import copy
from oslo.concurrency import lockutils
def list_opts():
"""Return a list of oslo.config options available in the library.
The returned list includes all oslo.config options which may be registered
at runtime by the library.
Each element of the list is a tuple. The first element is the name of the
group under which the list of elements in the second element will be
registered. A group name of None corresponds to the [DEFAULT] group in
config files.
This function is also discoverable via the 'oslo.concurrency' entry point
under the 'oslo.config.opts' namespace.
The purpose of this is to allow tools like the Oslo sample config file
generator to discover the options exposed to users by this library.
:returns: a list of (group_name, opts) tuples
"""
return [('oslo_concurrency', copy.deepcopy(lockutils._opts))]

View File

@ -26,6 +26,10 @@ packages =
namespace_packages = namespace_packages =
oslo oslo
[entry_points]
oslo.config.opts =
oslo.concurrency = oslo.concurrency.opts:list_opts
[build_sphinx] [build_sphinx]
source-dir = doc/source source-dir = doc/source
build-dir = doc/build build-dir = doc/build

View File

@ -127,7 +127,7 @@ class LockTestCase(test_base.BaseTestCase):
"""We can nest external syncs.""" """We can nest external syncs."""
tempdir = tempfile.mkdtemp() tempdir = tempfile.mkdtemp()
try: try:
self.config(lock_path=tempdir) self.config(lock_path=tempdir, group='oslo_concurrency')
sentinel = object() sentinel = object()
@lockutils.synchronized('testlock1', 'test-', external=True) @lockutils.synchronized('testlock1', 'test-', external=True)
@ -197,7 +197,7 @@ class LockTestCase(test_base.BaseTestCase):
def test_lock_externally(self): def test_lock_externally(self):
lock_dir = tempfile.mkdtemp() lock_dir = tempfile.mkdtemp()
self.config(lock_path=lock_dir) self.config(lock_path=lock_dir, group='oslo_concurrency')
try: try:
self._do_test_lock_externally() self._do_test_lock_externally()
@ -208,7 +208,7 @@ class LockTestCase(test_base.BaseTestCase):
def test_lock_externally_lock_dir_not_exist(self): def test_lock_externally_lock_dir_not_exist(self):
lock_dir = tempfile.mkdtemp() lock_dir = tempfile.mkdtemp()
os.rmdir(lock_dir) os.rmdir(lock_dir)
self.config(lock_path=lock_dir) self.config(lock_path=lock_dir, group='oslo_concurrency')
try: try:
self._do_test_lock_externally() self._do_test_lock_externally()
@ -227,13 +227,13 @@ class LockTestCase(test_base.BaseTestCase):
return True return True
lock_dir = tempfile.mkdtemp() lock_dir = tempfile.mkdtemp()
self.config(lock_path=lock_dir) self.config(lock_path=lock_dir, group='oslo_concurrency')
self.assertTrue(bar(lock_dir, lock_pfix, lock_name)) self.assertTrue(bar(lock_dir, lock_pfix, lock_name))
def test_synchronized_without_prefix(self): def test_synchronized_without_prefix(self):
lock_dir = tempfile.mkdtemp() lock_dir = tempfile.mkdtemp()
self.config(lock_path=lock_dir) self.config(lock_path=lock_dir, group='oslo_concurrency')
@lockutils.synchronized('lock', external=True) @lockutils.synchronized('lock', external=True)
def test_without_prefix(): def test_without_prefix():
@ -248,7 +248,7 @@ class LockTestCase(test_base.BaseTestCase):
def test_synchronized_prefix_without_hypen(self): def test_synchronized_prefix_without_hypen(self):
lock_dir = tempfile.mkdtemp() lock_dir = tempfile.mkdtemp()
self.config(lock_path=lock_dir) self.config(lock_path=lock_dir, group='oslo_concurrency')
@lockutils.synchronized('lock', 'hypen', True) @lockutils.synchronized('lock', 'hypen', True)
def test_without_hypen(): def test_without_hypen():
@ -263,7 +263,7 @@ class LockTestCase(test_base.BaseTestCase):
def test_contextlock(self): def test_contextlock(self):
lock_dir = tempfile.mkdtemp() lock_dir = tempfile.mkdtemp()
self.config(lock_path=lock_dir) self.config(lock_path=lock_dir, group='oslo_concurrency')
try: try:
# Note(flaper87): Lock is not external, which means # Note(flaper87): Lock is not external, which means
@ -289,7 +289,7 @@ class LockTestCase(test_base.BaseTestCase):
def test_contextlock_unlocks(self): def test_contextlock_unlocks(self):
lock_dir = tempfile.mkdtemp() lock_dir = tempfile.mkdtemp()
self.config(lock_path=lock_dir) self.config(lock_path=lock_dir, group='oslo_concurrency')
sem = None sem = None
@ -334,7 +334,7 @@ class LockTestCase(test_base.BaseTestCase):
def test_remove_lock_external_file(self): def test_remove_lock_external_file(self):
lock_dir = tempfile.mkdtemp() lock_dir = tempfile.mkdtemp()
self.config(lock_path=lock_dir) self.config(lock_path=lock_dir, group='oslo_concurrency')
self._test_remove_lock_external_file(lock_dir) self._test_remove_lock_external_file(lock_dir)
def test_remove_lock_external_file_lock_path(self): def test_remove_lock_external_file_lock_path(self):
@ -499,7 +499,7 @@ class TestLockFixture(test_base.BaseTestCase):
def test_lock_fixture(self): def test_lock_fixture(self):
# Setup lock fixture to test that teardown is inside the lock # Setup lock fixture to test that teardown is inside the lock
self.config(lock_path=self.tempdir) self.config(lock_path=self.tempdir, group='oslo_concurrency')
fixture = fixtures.LockFixture('test-lock') fixture = fixtures.LockFixture('test-lock')
self.useFixture(fixture) self.useFixture(fixture)
self.lock = fixture.lock self.lock = fixture.lock