Move argument parsing for dynamic_inventory to generate
At the moment osa_toolkit is installable as a package. With recent changes to PBR for python3.12 console_scripts are no longer installed "as is", but only a simple import is created. This change results in broken `openstack-ansible-inventory` binary, as `inventory` can not be imported. To avoid the issue and follow our existing logic for rest of tooling, we move argument parsing logic to generate.py itself, allowing it to be self-sufficient and be leaving a dynamic_inventory.py as a simple pointer which needs to stay in inventory folder for gropup_vars to load properly. Change-Id: Ie6d68f9c7b91d88736c5fc67c997cffd812afc61
This commit is contained in:
@@ -15,7 +15,6 @@
|
|||||||
#
|
#
|
||||||
# (c) 2014, Kevin Carter <kevin.carter@rackspace.com>
|
# (c) 2014, Kevin Carter <kevin.carter@rackspace.com>
|
||||||
|
|
||||||
import argparse
|
|
||||||
import os
|
import os
|
||||||
import sys
|
import sys
|
||||||
|
|
||||||
@@ -28,57 +27,8 @@ except ImportError:
|
|||||||
from osa_toolkit import generate
|
from osa_toolkit import generate
|
||||||
|
|
||||||
|
|
||||||
# Function kept in order to use relative pathing for the env.d directory
|
|
||||||
def args(arg_list):
|
|
||||||
"""Setup argument Parsing."""
|
|
||||||
parser = argparse.ArgumentParser(
|
|
||||||
usage='%(prog)s',
|
|
||||||
description='OpenStack Inventory Generator',
|
|
||||||
epilog='Inventory Generator Licensed "Apache 2.0"')
|
|
||||||
|
|
||||||
parser.add_argument(
|
|
||||||
'--config',
|
|
||||||
help='Path containing the user defined configuration files',
|
|
||||||
required=False,
|
|
||||||
default=os.getenv('OSA_CONFIG_DIR', None)
|
|
||||||
)
|
|
||||||
parser.add_argument(
|
|
||||||
'--list',
|
|
||||||
help='List all entries',
|
|
||||||
action='store_true'
|
|
||||||
)
|
|
||||||
|
|
||||||
parser.add_argument(
|
|
||||||
'--check',
|
|
||||||
help="Configuration check only, don't generate inventory",
|
|
||||||
action='store_true',
|
|
||||||
)
|
|
||||||
|
|
||||||
parser.add_argument(
|
|
||||||
'-d',
|
|
||||||
'--debug',
|
|
||||||
help=('Output debug messages to log file. '
|
|
||||||
'File is appended to, not overwritten'),
|
|
||||||
action='store_true',
|
|
||||||
default=False,
|
|
||||||
)
|
|
||||||
|
|
||||||
parser.add_argument(
|
|
||||||
'-e',
|
|
||||||
'--environment',
|
|
||||||
help=('Directory that contains the base env.d directory.\n'
|
|
||||||
'Defaults to <OSA_ROOT>/inventory/.'),
|
|
||||||
required=False,
|
|
||||||
default=os.path.dirname(__file__),
|
|
||||||
)
|
|
||||||
|
|
||||||
return vars(parser.parse_args(arg_list))
|
|
||||||
|
|
||||||
|
|
||||||
def main():
|
def main():
|
||||||
all_args = args(sys.argv[1:])
|
generate.main()
|
||||||
output = generate.main(**all_args)
|
|
||||||
print(output)
|
|
||||||
|
|
||||||
|
|
||||||
if __name__ == '__main__':
|
if __name__ == '__main__':
|
||||||
|
|||||||
74
osa_toolkit/generate.py
Executable file → Normal file
74
osa_toolkit/generate.py
Executable file → Normal file
@@ -15,17 +15,23 @@
|
|||||||
#
|
#
|
||||||
# (c) 2014, Kevin Carter <kevin.carter@rackspace.com>
|
# (c) 2014, Kevin Carter <kevin.carter@rackspace.com>
|
||||||
|
|
||||||
|
import argparse
|
||||||
import copy
|
import copy
|
||||||
import json
|
import json
|
||||||
import logging
|
import logging
|
||||||
import netaddr
|
from os import getenv as os_env
|
||||||
from osa_toolkit import dictutils as du
|
from os import path as os_path
|
||||||
from osa_toolkit import filesystem as filesys
|
|
||||||
from osa_toolkit import ip
|
|
||||||
import re
|
import re
|
||||||
|
import sys
|
||||||
import uuid
|
import uuid
|
||||||
import warnings
|
import warnings
|
||||||
|
|
||||||
|
import netaddr
|
||||||
|
|
||||||
|
from osa_toolkit import __path__ as repo_path
|
||||||
|
from osa_toolkit import dictutils as du
|
||||||
|
from osa_toolkit import filesystem as filesys
|
||||||
|
from osa_toolkit import ip
|
||||||
|
|
||||||
logger = logging.getLogger('osa-inventory')
|
logger = logging.getLogger('osa-inventory')
|
||||||
|
|
||||||
@@ -50,6 +56,53 @@ REQUIRED_HOSTVARS = [
|
|||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
|
def args(argv):
|
||||||
|
"""Setup argument Parsing."""
|
||||||
|
parser = argparse.ArgumentParser(
|
||||||
|
usage='%(prog)s',
|
||||||
|
description='OpenStack Inventory Generator',
|
||||||
|
epilog='Inventory Generator Licensed "Apache 2.0"')
|
||||||
|
|
||||||
|
parser.add_argument(
|
||||||
|
'--config',
|
||||||
|
help='Path containing the user defined configuration files',
|
||||||
|
required=False,
|
||||||
|
default=os_env('OSA_CONFIG_DIR', None)
|
||||||
|
)
|
||||||
|
|
||||||
|
parser.add_argument(
|
||||||
|
'--list',
|
||||||
|
help='List all entries',
|
||||||
|
action='store_true'
|
||||||
|
)
|
||||||
|
|
||||||
|
parser.add_argument(
|
||||||
|
'--check',
|
||||||
|
help="Configuration check only, don't generate inventory",
|
||||||
|
action='store_true',
|
||||||
|
)
|
||||||
|
|
||||||
|
parser.add_argument(
|
||||||
|
'-d',
|
||||||
|
'--debug',
|
||||||
|
help=('Output debug messages to log file. '
|
||||||
|
'File is appended to, not overwritten'),
|
||||||
|
action='store_true',
|
||||||
|
default=False,
|
||||||
|
)
|
||||||
|
|
||||||
|
parser.add_argument(
|
||||||
|
'-e',
|
||||||
|
'--environment',
|
||||||
|
help=('Directory that contains the base env.d directory.\n'
|
||||||
|
'Defaults to <OSA_ROOT>/inventory/.'),
|
||||||
|
required=False,
|
||||||
|
default=f'{os_path.dirname(repo_path[0])}/inventory',
|
||||||
|
)
|
||||||
|
|
||||||
|
return vars(parser.parse_args(argv))
|
||||||
|
|
||||||
|
|
||||||
class MultipleHostsWithOneIPError(Exception):
|
class MultipleHostsWithOneIPError(Exception):
|
||||||
def __init__(self, ip, assigned_host, new_host):
|
def __init__(self, ip, assigned_host, new_host):
|
||||||
self.ip = ip
|
self.ip = ip
|
||||||
@@ -1139,7 +1192,11 @@ def _prepare_debug_logger():
|
|||||||
logger.info("Beginning new inventory run")
|
logger.info("Beginning new inventory run")
|
||||||
|
|
||||||
|
|
||||||
def main(config=None, check=False, debug=False, environment=None, **kwargs):
|
def generate(config=None,
|
||||||
|
check=False,
|
||||||
|
debug=False,
|
||||||
|
environment=None,
|
||||||
|
**kwargs):
|
||||||
"""Run the main application.
|
"""Run the main application.
|
||||||
|
|
||||||
:param config: ``str`` Directory from which to pull configs and overrides
|
:param config: ``str`` Directory from which to pull configs and overrides
|
||||||
@@ -1263,3 +1320,10 @@ def main(config=None, check=False, debug=False, environment=None, **kwargs):
|
|||||||
filesys.save_inventory(inventory_json, inv_path)
|
filesys.save_inventory(inventory_json, inv_path)
|
||||||
|
|
||||||
return inventory_json
|
return inventory_json
|
||||||
|
|
||||||
|
|
||||||
|
def main(argv=sys.argv[1:]):
|
||||||
|
|
||||||
|
all_args = args(argv)
|
||||||
|
data = generate(**all_args)
|
||||||
|
print(data)
|
||||||
|
|||||||
@@ -28,4 +28,4 @@ packages = osa_toolkit
|
|||||||
|
|
||||||
[entry_points]
|
[entry_points]
|
||||||
console_scripts =
|
console_scripts =
|
||||||
openstack-ansible-inventory = inventory.dynamic_inventory:main
|
openstack-ansible-inventory = osa_toolkit.generate:main
|
||||||
|
|||||||
@@ -29,7 +29,6 @@ INV_DIR = 'inventory'
|
|||||||
|
|
||||||
sys.path.append(path.join(os.getcwd(), INV_DIR))
|
sys.path.append(path.join(os.getcwd(), INV_DIR))
|
||||||
|
|
||||||
import dynamic_inventory # noqa: E402
|
|
||||||
from osa_toolkit import dictutils # noqa: E402
|
from osa_toolkit import dictutils # noqa: E402
|
||||||
from osa_toolkit import filesystem as fs # noqa: E402
|
from osa_toolkit import filesystem as fs # noqa: E402
|
||||||
from osa_toolkit import generate as di # noqa: E402
|
from osa_toolkit import generate as di # noqa: E402
|
||||||
@@ -102,7 +101,7 @@ def get_inventory(clean=True, extra_args=None):
|
|||||||
if extra_args:
|
if extra_args:
|
||||||
args.update(extra_args)
|
args.update(extra_args)
|
||||||
try:
|
try:
|
||||||
inventory_string = di.main(**args)
|
inventory_string = di.generate(**args)
|
||||||
inventory = json.loads(inventory_string)
|
inventory = json.loads(inventory_string)
|
||||||
return inventory
|
return inventory
|
||||||
finally:
|
finally:
|
||||||
@@ -114,16 +113,16 @@ def get_inventory(clean=True, extra_args=None):
|
|||||||
|
|
||||||
class TestArgParser(unittest.TestCase):
|
class TestArgParser(unittest.TestCase):
|
||||||
def test_no_args(self):
|
def test_no_args(self):
|
||||||
arg_dict = dynamic_inventory.args([])
|
arg_dict = di.args([])
|
||||||
self.assertIsNone(arg_dict['config'])
|
self.assertIsNone(arg_dict['config'])
|
||||||
self.assertEqual(arg_dict['list'], False)
|
self.assertEqual(arg_dict['list'], False)
|
||||||
|
|
||||||
def test_list_arg(self):
|
def test_list_arg(self):
|
||||||
arg_dict = dynamic_inventory.args(['--list'])
|
arg_dict = di.args(['--list'])
|
||||||
self.assertEqual(arg_dict['list'], True)
|
self.assertEqual(arg_dict['list'], True)
|
||||||
|
|
||||||
def test_config_arg(self):
|
def test_config_arg(self):
|
||||||
arg_dict = dynamic_inventory.args(['--config',
|
arg_dict = di.args(['--config',
|
||||||
'/etc/openstack_deploy'])
|
'/etc/openstack_deploy'])
|
||||||
self.assertEqual(arg_dict['config'], '/etc/openstack_deploy')
|
self.assertEqual(arg_dict['config'], '/etc/openstack_deploy')
|
||||||
|
|
||||||
@@ -1263,7 +1262,7 @@ class TestConfigCheckFunctional(TestConfigCheckBase):
|
|||||||
self.user_defined_config['dashboard_hosts']['bogus'] = ip
|
self.user_defined_config['dashboard_hosts']['bogus'] = ip
|
||||||
|
|
||||||
def test_checking_good_config(self):
|
def test_checking_good_config(self):
|
||||||
output = di.main(config=TARGET_DIR, check=True,
|
output = di.generate(config=TARGET_DIR, check=True,
|
||||||
environment=BASE_ENV_DIR)
|
environment=BASE_ENV_DIR)
|
||||||
self.assertEqual(output, 'Configuration ok!')
|
self.assertEqual(output, 'Configuration ok!')
|
||||||
|
|
||||||
@@ -1271,7 +1270,7 @@ class TestConfigCheckFunctional(TestConfigCheckBase):
|
|||||||
self.duplicate_ip()
|
self.duplicate_ip()
|
||||||
self.write_config()
|
self.write_config()
|
||||||
with self.assertRaises(di.MultipleHostsWithOneIPError) as context:
|
with self.assertRaises(di.MultipleHostsWithOneIPError) as context:
|
||||||
di.main(config=TARGET_DIR, check=True, environment=BASE_ENV_DIR)
|
di.generate(config=TARGET_DIR, check=True, environment=BASE_ENV_DIR)
|
||||||
self.assertEqual(context.exception.ip, '172.29.236.100')
|
self.assertEqual(context.exception.ip, '172.29.236.100')
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user