From 352b7d29225a945f7beec1d9376067d8ead27080 Mon Sep 17 00:00:00 2001 From: Mark McLoughlin Date: Mon, 23 Jan 2012 11:51:14 +0000 Subject: [PATCH] Refactor away the flags.DEFINE_* helpers The next obvious step in porting to cfg is to define all options using cfg schemas directly rather than using the flags.DEFINE_* helpers. This is a large change, but it is almost entirely pure refactoring and does not result in any functional changes. The only change to note is that the default values for glance_host, glance_api_servers and default_publisher_id options are now using opt value interpolation i.e. -glance_host=_get_my_ip() +glance_host='$my_ip' -glance_api_servers=['%s:%d' % (FLAGS.glance_host, FLAGS.glance_port)] +glance_api_servers=['$glance_host:$glance_port'] -default_publisher_id=FLAGS.host +default_publisher_id='$host' Also note that the lower_bound check on the {report,periodic}_interval options are no more, but this has been true since cfg was first added. Change-Id: Ia58c8f0aaf61628bb55b1b8485118a2a9852ed17 --- bin/clear_rabbit_queues | 8 +- bin/nova-ajax-console-proxy | 10 +- bin/nova-direct-api | 13 +- nova/auth/ldapdriver.py | 88 +++-- nova/auth/manager.py | 87 +++-- nova/flags.py | 616 +++++++++++++++++-------------- nova/log.py | 68 ++-- nova/notifier/api.py | 18 +- nova/notifier/list_notifier.py | 10 +- nova/notifier/rabbit_notifier.py | 10 +- nova/rpc/__init__.py | 12 +- nova/rpc/common.py | 15 +- nova/rpc/impl_qpid.py | 69 ++-- nova/scheduler/api.py | 11 +- nova/scheduler/least_cost.py | 26 +- nova/scheduler/multi.py | 19 +- nova/scheduler/simple.py | 26 +- nova/scheduler/vsa.py | 21 +- nova/scheduler/zone_manager.py | 16 +- nova/tests/declare_flags.py | 4 +- nova/tests/runtime_flags.py | 4 +- nova/tests/test_flags.py | 57 +-- nova/vsa/api.py | 25 +- nova/vsa/manager.py | 9 +- 24 files changed, 752 insertions(+), 490 deletions(-) diff --git a/bin/clear_rabbit_queues b/bin/clear_rabbit_queues index 7a000e5d..f697ef6b 100755 --- a/bin/clear_rabbit_queues +++ b/bin/clear_rabbit_queues @@ -40,6 +40,7 @@ if os.path.exists(os.path.join(POSSIBLE_TOPDIR, 'nova', '__init__.py')): gettext.install('nova', unicode=1) +from nova.common import cfg from nova import context from nova import exception from nova import flags @@ -48,8 +49,13 @@ from nova import rpc from nova import utils +delete_exchange_opt = \ + cfg.BoolOpt('delete_exchange', + default=False, + help='delete nova exchange too.') + FLAGS = flags.FLAGS -flags.DEFINE_boolean('delete_exchange', False, 'delete nova exchange too.') +FLAGS.add_option(delete_exchange_opt) def delete_exchange(exch): diff --git a/bin/nova-ajax-console-proxy b/bin/nova-ajax-console-proxy index a6b28498..7dd5266a 100755 --- a/bin/nova-ajax-console-proxy +++ b/bin/nova-ajax-console-proxy @@ -38,6 +38,7 @@ if os.path.exists(os.path.join(possible_topdir, 'nova', '__init__.py')): sys.path.insert(0, possible_topdir) +from nova.common import cfg from nova import flags from nova import log as logging from nova import rpc @@ -45,9 +46,14 @@ from nova import service from nova import utils from nova import wsgi + +ajax_console_idle_timeout_opt = \ + cfg.IntOpt('ajax_console_idle_timeout', + default=300, + help='Seconds before idle connection destroyed') + FLAGS = flags.FLAGS -flags.DEFINE_integer('ajax_console_idle_timeout', 300, - 'Seconds before idle connection destroyed') +FLAGS.add_option(ajax_console_idle_timeout_opt) LOG = logging.getLogger('nova.ajax_console_proxy') diff --git a/bin/nova-direct-api b/bin/nova-direct-api index 28cc2963..f7731191 100755 --- a/bin/nova-direct-api +++ b/bin/nova-direct-api @@ -35,6 +35,7 @@ if os.path.exists(os.path.join(possible_topdir, 'nova', '__init__.py')): sys.path.insert(0, possible_topdir) +from nova.common import cfg from nova import compute from nova import flags from nova import log as logging @@ -46,9 +47,17 @@ from nova import wsgi from nova.api import direct +direct_api_opts = [ + cfg.IntOpt('direct_port', + default=8001, + help='Direct API port'), + cfg.StrOpt('direct_host', + default='0.0.0.0', + help='Direct API host'), + ] + FLAGS = flags.FLAGS -flags.DEFINE_integer('direct_port', 8001, 'Direct API port') -flags.DEFINE_string('direct_host', '0.0.0.0', 'Direct API host') +FLAGS.add_options(direct_api_opts) # An example of an API that only exposes read-only methods. diff --git a/nova/auth/ldapdriver.py b/nova/auth/ldapdriver.py index 6f8ae6e6..79da5bd8 100644 --- a/nova/auth/ldapdriver.py +++ b/nova/auth/ldapdriver.py @@ -27,44 +27,68 @@ public methods. import functools import sys +from nova.common import cfg from nova import exception from nova import flags from nova import log as logging -FLAGS = flags.FLAGS -flags.DEFINE_integer('ldap_schema_version', 2, - 'Current version of the LDAP schema') -flags.DEFINE_string('ldap_url', 'ldap://localhost', - 'Point this at your ldap server') -flags.DEFINE_string('ldap_password', 'changeme', 'LDAP password') -flags.DEFINE_string('ldap_user_dn', 'cn=Manager,dc=example,dc=com', - 'DN of admin user') -flags.DEFINE_string('ldap_user_id_attribute', 'uid', 'Attribute to use as id') -flags.DEFINE_string('ldap_user_name_attribute', 'cn', - 'Attribute to use as name') -flags.DEFINE_string('ldap_user_unit', 'Users', 'OID for Users') -flags.DEFINE_string('ldap_user_subtree', 'ou=Users,dc=example,dc=com', - 'OU for Users') -flags.DEFINE_boolean('ldap_user_modify_only', False, - 'Modify attributes for users instead of creating/deleting') -flags.DEFINE_string('ldap_project_subtree', 'ou=Groups,dc=example,dc=com', - 'OU for Projects') -flags.DEFINE_string('role_project_subtree', 'ou=Groups,dc=example,dc=com', - 'OU for Roles') +ldap_opts = [ + cfg.IntOpt('ldap_schema_version', + default=2, + help='Current version of the LDAP schema'), + cfg.StrOpt('ldap_url', + default='ldap://localhost', + help='Point this at your ldap server'), + cfg.StrOpt('ldap_password', + default='changeme', + help='LDAP password'), + cfg.StrOpt('ldap_user_dn', + default='cn=Manager,dc=example,dc=com', + help='DN of admin user'), + cfg.StrOpt('ldap_user_id_attribute', + default='uid', + help='Attribute to use as id'), + cfg.StrOpt('ldap_user_name_attribute', + default='cn', + help='Attribute to use as name'), + cfg.StrOpt('ldap_user_unit', + default='Users', + help='OID for Users'), + cfg.StrOpt('ldap_user_subtree', + default='ou=Users,dc=example,dc=com', + help='OU for Users'), + cfg.BoolOpt('ldap_user_modify_only', + default=False, + help='Modify user attributes instead of creating/deleting'), + cfg.StrOpt('ldap_project_subtree', + default='ou=Groups,dc=example,dc=com', + help='OU for Projects'), + cfg.StrOpt('role_project_subtree', + default='ou=Groups,dc=example,dc=com', + help='OU for Roles'), -# NOTE(vish): mapping with these flags is necessary because we're going -# to tie in to an existing ldap schema -flags.DEFINE_string('ldap_cloudadmin', - 'cn=cloudadmins,ou=Groups,dc=example,dc=com', 'cn for Cloud Admins') -flags.DEFINE_string('ldap_itsec', - 'cn=itsec,ou=Groups,dc=example,dc=com', 'cn for ItSec') -flags.DEFINE_string('ldap_sysadmin', - 'cn=sysadmins,ou=Groups,dc=example,dc=com', 'cn for Sysadmins') -flags.DEFINE_string('ldap_netadmin', - 'cn=netadmins,ou=Groups,dc=example,dc=com', 'cn for NetAdmins') -flags.DEFINE_string('ldap_developer', - 'cn=developers,ou=Groups,dc=example,dc=com', 'cn for Developers') + # NOTE(vish): mapping with these flags is necessary because we're going + # to tie in to an existing ldap schema + cfg.StrOpt('ldap_cloudadmin', + default='cn=cloudadmins,ou=Groups,dc=example,dc=com', + help='cn for Cloud Admins'), + cfg.StrOpt('ldap_itsec', + default='cn=itsec,ou=Groups,dc=example,dc=com', + help='cn for ItSec'), + cfg.StrOpt('ldap_sysadmin', + default='cn=sysadmins,ou=Groups,dc=example,dc=com', + help='cn for Sysadmins'), + cfg.StrOpt('ldap_netadmin', + default='cn=netadmins,ou=Groups,dc=example,dc=com', + help='cn for NetAdmins'), + cfg.StrOpt('ldap_developer', + default='cn=developers,ou=Groups,dc=example,dc=com', + help='cn for Developers'), + ] + +FLAGS = flags.FLAGS +FLAGS.add_options(ldap_opts) LOG = logging.getLogger("nova.ldapdriver") diff --git a/nova/auth/manager.py b/nova/auth/manager.py index f6f55255..234b9bf3 100644 --- a/nova/auth/manager.py +++ b/nova/auth/manager.py @@ -30,6 +30,7 @@ import tempfile import uuid import zipfile +from nova.common import cfg from nova import context from nova import crypto from nova import db @@ -40,45 +41,61 @@ from nova import utils from nova.auth import signer +auth_opts = [ + cfg.BoolOpt('use_deprecated_auth', + default=False, + help='This flag must be set to use old style auth'), + cfg.ListOpt('allowed_roles', + default=[ + 'cloudadmin', + 'itsec', + 'sysadmin', + 'netadmin', + 'developer' + ], + help='Allowed roles for project'), + + # NOTE(vish): a user with one of these roles will be a superuser and + # have access to all api commands + cfg.ListOpt('superuser_roles', + default=['cloudadmin'], + help='Roles that ignore authorization checking completely'), + + # NOTE(vish): a user with one of these roles will have it for every + # project, even if he or she is not a member of the project + cfg.ListOpt('global_roles', + default=['cloudadmin', 'itsec'], + help='Roles that apply to all projects'), + + cfg.StrOpt('credentials_template', + default=utils.abspath('auth/novarc.template'), + help='Template for creating users rc file'), + cfg.StrOpt('vpn_client_template', + default=utils.abspath('cloudpipe/client.ovpn.template'), + help='Template for creating users vpn file'), + cfg.StrOpt('credential_vpn_file', + default='nova-vpn.conf', + help='Filename of certificate in credentials zip'), + cfg.StrOpt('credential_key_file', + default='pk.pem', + help='Filename of private key in credentials zip'), + cfg.StrOpt('credential_cert_file', + default='cert.pem', + help='Filename of certificate in credentials zip'), + cfg.StrOpt('credential_rc_file', + default='%src', + help='Filename of rc in credentials zip %s will be replaced by ' + 'name of the region (nova by default)'), + cfg.StrOpt('auth_driver', + default='nova.auth.dbdriver.DbDriver', + help='Driver that auth manager uses'), + ] + FLAGS = flags.FLAGS -flags.DEFINE_bool('use_deprecated_auth', - False, - 'This flag must be set to use old style auth') - -flags.DEFINE_list('allowed_roles', - ['cloudadmin', 'itsec', 'sysadmin', 'netadmin', 'developer'], - 'Allowed roles for project') -# NOTE(vish): a user with one of these roles will be a superuser and -# have access to all api commands -flags.DEFINE_list('superuser_roles', ['cloudadmin'], - 'Roles that ignore authorization checking completely') - -# NOTE(vish): a user with one of these roles will have it for every -# project, even if he or she is not a member of the project -flags.DEFINE_list('global_roles', ['cloudadmin', 'itsec'], - 'Roles that apply to all projects') - -flags.DEFINE_string('credentials_template', - utils.abspath('auth/novarc.template'), - 'Template for creating users rc file') -flags.DEFINE_string('vpn_client_template', - utils.abspath('cloudpipe/client.ovpn.template'), - 'Template for creating users vpn file') -flags.DEFINE_string('credential_vpn_file', 'nova-vpn.conf', - 'Filename of certificate in credentials zip') -flags.DEFINE_string('credential_key_file', 'pk.pem', - 'Filename of private key in credentials zip') -flags.DEFINE_string('credential_cert_file', 'cert.pem', - 'Filename of certificate in credentials zip') -flags.DEFINE_string('credential_rc_file', '%src', - 'Filename of rc in credentials zip, %s will be ' - 'replaced by name of the region (nova by default)') -flags.DEFINE_string('auth_driver', 'nova.auth.dbdriver.DbDriver', - 'Driver that auth manager uses') +FLAGS.add_options(auth_opts) flags.DECLARE('osapi_compute_listen_port', 'nova.service') - LOG = logging.getLogger('nova.auth.manager') diff --git a/nova/flags.py b/nova/flags.py index 59c44470..14681727 100644 --- a/nova/flags.py +++ b/nova/flags.py @@ -151,7 +151,7 @@ class FlagValues(object): ret[opt.dest] = getattr(self, opt.dest) return ret - def _add_option(self, opt): + def add_option(self, opt): if opt.dest in self._opts: return @@ -164,57 +164,14 @@ class FlagValues(object): self._conf.register_cli_opts(self._opts.values()) self._extra = None - def define_string(self, name, default, help): - self._add_option(cfg.StrOpt(name, default=default, help=help)) - - def define_integer(self, name, default, help): - self._add_option(cfg.IntOpt(name, default=default, help=help)) - - def define_float(self, name, default, help): - self._add_option(cfg.FloatOpt(name, default=default, help=help)) - - def define_bool(self, name, default, help): - self._add_option(cfg.BoolOpt(name, default=default, help=help)) - - def define_list(self, name, default, help): - self._add_option(cfg.ListOpt(name, default=default, help=help)) - - def define_multistring(self, name, default, help): - self._add_option(cfg.MultiStrOpt(name, default=default, help=help)) + def add_options(self, opts): + for opt in opts: + self.add_option(opt) FLAGS = FlagValues() -def DEFINE_string(name, default, help, flag_values=FLAGS): - flag_values.define_string(name, default, help) - - -def DEFINE_integer(name, default, help, lower_bound=None, flag_values=FLAGS): - # FIXME(markmc): ignoring lower_bound - flag_values.define_integer(name, default, help) - - -def DEFINE_bool(name, default, help, flag_values=FLAGS): - flag_values.define_bool(name, default, help) - - -def DEFINE_boolean(name, default, help, flag_values=FLAGS): - DEFINE_bool(name, default, help, flag_values) - - -def DEFINE_list(name, default, help, flag_values=FLAGS): - flag_values.define_list(name, default, help) - - -def DEFINE_float(name, default, help, flag_values=FLAGS): - flag_values.define_float(name, default, help) - - -def DEFINE_multistring(name, default, help, flag_values=FLAGS): - flag_values.define_multistring(name, default, help) - - class UnrecognizedFlag(Exception): pass @@ -238,227 +195,346 @@ def _get_my_ip(): return "127.0.0.1" -# __GLOBAL FLAGS ONLY__ -# Define any app-specific flags in their own files, docs at: -# http://code.google.com/p/python-gflags/source/browse/trunk/gflags.py#a9 -DEFINE_string('my_ip', _get_my_ip(), 'host ip address') -DEFINE_list('region_list', - [], - 'list of region=fqdn pairs separated by commas') -DEFINE_string('connection_type', None, 'libvirt, xenapi or fake') -DEFINE_string('aws_access_key_id', 'admin', 'AWS Access ID') -DEFINE_string('aws_secret_access_key', 'admin', 'AWS Access Key') -# NOTE(sirp): my_ip interpolation doesn't work within nested structures -DEFINE_string('glance_host', _get_my_ip(), 'default glance host') -DEFINE_integer('glance_port', 9292, 'default glance port') -DEFINE_list('glance_api_servers', - ['%s:%d' % (FLAGS.glance_host, FLAGS.glance_port)], - 'list of glance api servers available to nova (host:port)') -DEFINE_integer('glance_num_retries', 0, - 'The number of times to retry downloading an image from glance') -DEFINE_integer('s3_port', 3333, 's3 port') -DEFINE_string('s3_host', '$my_ip', 's3 host (for infrastructure)') -DEFINE_string('s3_dmz', '$my_ip', 's3 dmz ip (for instances)') -DEFINE_string('cert_topic', 'cert', 'the topic cert nodes listen on') -DEFINE_string('compute_topic', 'compute', 'the topic compute nodes listen on') -DEFINE_string('console_topic', 'console', - 'the topic console proxy nodes listen on') -DEFINE_string('scheduler_topic', 'scheduler', - 'the topic scheduler nodes listen on') -DEFINE_string('volume_topic', 'volume', 'the topic volume nodes listen on') -DEFINE_string('network_topic', 'network', 'the topic network nodes listen on') -DEFINE_string('ajax_console_proxy_topic', 'ajax_proxy', - 'the topic ajax proxy nodes listen on') -DEFINE_string('ajax_console_proxy_url', - 'http://127.0.0.1:8000', - 'location of ajax console proxy, \ - in the form "http://127.0.0.1:8000"') -DEFINE_integer('ajax_console_proxy_port', - 8000, 'port that ajax_console_proxy binds') -DEFINE_string('vsa_topic', 'vsa', 'the topic that nova-vsa service listens on') -DEFINE_bool('verbose', False, 'show debug output') -DEFINE_boolean('fake_rabbit', False, 'use a fake rabbit') -DEFINE_bool('fake_network', False, - 'should we use fake network devices and addresses') -DEFINE_string('rabbit_host', 'localhost', 'rabbit host') -DEFINE_integer('rabbit_port', 5672, 'rabbit port') -DEFINE_bool('rabbit_use_ssl', False, 'connect over SSL') -DEFINE_string('rabbit_userid', 'guest', 'rabbit userid') -DEFINE_string('rabbit_password', 'guest', 'rabbit password') -DEFINE_string('rabbit_virtual_host', '/', 'rabbit virtual host') -DEFINE_integer('rabbit_retry_interval', 1, - 'rabbit connection retry interval to start') -DEFINE_integer('rabbit_retry_backoff', 2, - 'rabbit connection retry backoff in seconds') -DEFINE_integer('rabbit_max_retries', 0, - 'maximum rabbit connection attempts (0=try forever)') -DEFINE_string('control_exchange', 'nova', 'the main exchange to connect to') -DEFINE_boolean('rabbit_durable_queues', False, 'use durable queues') -DEFINE_list('enabled_apis', - ['ec2', 'osapi_compute', 'osapi_volume', 'metadata'], - 'list of APIs to enable by default') -DEFINE_string('ec2_host', '$my_ip', 'ip of api server') -DEFINE_string('ec2_dmz_host', '$my_ip', 'internal ip of api server') -DEFINE_integer('ec2_port', 8773, 'cloud controller port') -DEFINE_string('ec2_scheme', 'http', 'prefix for ec2') -DEFINE_string('ec2_path', '/services/Cloud', 'suffix for ec2') -DEFINE_multistring('osapi_compute_extension', - ['nova.api.openstack.compute.contrib.standard_extensions'], - 'osapi compute extension to load') -DEFINE_multistring('osapi_volume_extension', - ['nova.api.openstack.volume.contrib.standard_extensions'], - 'osapi volume extension to load') -DEFINE_string('osapi_scheme', 'http', 'prefix for openstack') -DEFINE_string('osapi_path', '/v1.1/', 'suffix for openstack') -DEFINE_integer('osapi_max_limit', 1000, - 'max number of items returned in a collection response') -DEFINE_string('metadata_host', '$my_ip', 'ip of metadata server') -DEFINE_integer('metadata_port', 8775, 'Metadata API port') -DEFINE_string('default_project', 'openstack', 'default project for openstack') -DEFINE_string('default_image', 'ami-11111', - 'default image to use, testing only') -DEFINE_string('default_instance_type', 'm1.small', - 'default instance type to use, testing only') -DEFINE_string('null_kernel', 'nokernel', - 'kernel image that indicates not to use a kernel,' - ' but to use a raw disk image instead') +global_opts = [ + cfg.StrOpt('my_ip', + default=_get_my_ip(), + help='host ip address'), + cfg.ListOpt('region_list', + default=[], + help='list of region=fqdn pairs separated by commas'), + cfg.StrOpt('connection_type', + default=None, + help='libvirt, xenapi or fake'), + cfg.StrOpt('aws_access_key_id', + default='admin', + help='AWS Access ID'), + cfg.StrOpt('aws_secret_access_key', + default='admin', + help='AWS Access Key'), + cfg.StrOpt('glance_host', + default='$my_ip', + help='default glance host'), + cfg.IntOpt('glance_port', + default=9292, + help='default glance port'), + cfg.ListOpt('glance_api_servers', + default=['$glance_host:$glance_port'], + help='glance api servers available to nova (host:port)'), + cfg.IntOpt('glance_num_retries', + default=0, + help='Number retries when downloading an image from glance'), + cfg.IntOpt('s3_port', + default=3333, + help='s3 port'), + cfg.StrOpt('s3_host', + default='$my_ip', + help='s3 host (for infrastructure)'), + cfg.StrOpt('s3_dmz', + default='$my_ip', + help='s3 dmz ip (for instances)'), + cfg.StrOpt('cert_topic', + default='cert', + help='the topic cert nodes listen on'), + cfg.StrOpt('compute_topic', + default='compute', + help='the topic compute nodes listen on'), + cfg.StrOpt('console_topic', + default='console', + help='the topic console proxy nodes listen on'), + cfg.StrOpt('scheduler_topic', + default='scheduler', + help='the topic scheduler nodes listen on'), + cfg.StrOpt('volume_topic', + default='volume', + help='the topic volume nodes listen on'), + cfg.StrOpt('network_topic', + default='network', + help='the topic network nodes listen on'), + cfg.StrOpt('ajax_console_proxy_topic', + default='ajax_proxy', + help='the topic ajax proxy nodes listen on'), + cfg.StrOpt('ajax_console_proxy_url', + default='http://127.0.0.1:8000', + help='URL of ajax console proxy, in the form http://host:port'), + cfg.IntOpt('ajax_console_proxy_port', + default=8000, + help='port that ajax_console_proxy binds'), + cfg.StrOpt('vsa_topic', + default='vsa', + help='the topic that nova-vsa service listens on'), + cfg.BoolOpt('verbose', + default=False, + help='show debug output'), + cfg.BoolOpt('fake_rabbit', + default=False, + help='use a fake rabbit'), + cfg.BoolOpt('fake_network', + default=False, + help='should we use fake network devices and addresses'), + cfg.StrOpt('rabbit_host', + default='localhost', + help='rabbit host'), + cfg.IntOpt('rabbit_port', + default=5672, + help='rabbit port'), + cfg.BoolOpt('rabbit_use_ssl', + default=False, + help='connect over SSL'), + cfg.StrOpt('rabbit_userid', + default='guest', + help='rabbit userid'), + cfg.StrOpt('rabbit_password', + default='guest', + help='rabbit password'), + cfg.StrOpt('rabbit_virtual_host', + default='/', + help='rabbit virtual host'), + cfg.IntOpt('rabbit_retry_interval', + default=1, + help='rabbit connection retry interval to start'), + cfg.IntOpt('rabbit_retry_backoff', + default=2, + help='rabbit connection retry backoff in seconds'), + cfg.IntOpt('rabbit_max_retries', + default=0, + help='maximum rabbit connection attempts (0=try forever)'), + cfg.StrOpt('control_exchange', + default='nova', + help='the main exchange to connect to'), + cfg.BoolOpt('rabbit_durable_queues', + default=False, + help='use durable queues'), + cfg.ListOpt('enabled_apis', + default=['ec2', 'osapi_compute', 'osapi_volume', 'metadata'], + help='list of APIs to enable by default'), + cfg.StrOpt('ec2_host', + default='$my_ip', + help='ip of api server'), + cfg.StrOpt('ec2_dmz_host', + default='$my_ip', + help='internal ip of api server'), + cfg.IntOpt('ec2_port', + default=8773, + help='cloud controller port'), + cfg.StrOpt('ec2_scheme', + default='http', + help='prefix for ec2'), + cfg.StrOpt('ec2_path', + default='/services/Cloud', + help='suffix for ec2'), + cfg.MultiStrOpt('osapi_compute_extension', + default=[ + 'nova.api.openstack.compute.contrib.standard_extensions' + ], + help='osapi compute extension to load'), + cfg.MultiStrOpt('osapi_volume_extension', + default=[ + 'nova.api.openstack.volume.contrib.standard_extensions' + ], + help='osapi volume extension to load'), + cfg.StrOpt('osapi_scheme', + default='http', + help='prefix for openstack'), + cfg.StrOpt('osapi_path', + default='/v1.1/', + help='suffix for openstack'), + cfg.IntOpt('osapi_max_limit', + default=1000, + help='max number of items returned in a collection response'), + cfg.StrOpt('metadata_host', + default='$my_ip', + help='ip of metadata server'), + cfg.IntOpt('metadata_port', + default=8775, + help='Metadata API port'), + cfg.StrOpt('default_project', + default='openstack', + help='default project for openstack'), + cfg.StrOpt('default_image', + default='ami-11111', + help='default image to use, testing only'), + cfg.StrOpt('default_instance_type', + default='m1.small', + help='default instance type to use, testing only'), + cfg.StrOpt('null_kernel', + default='nokernel', + help='kernel image that indicates not to use a kernel, but to ' + 'use a raw disk image instead'), + cfg.StrOpt('vpn_image_id', + default='0', + help='image id for cloudpipe vpn server'), + cfg.StrOpt('vpn_key_suffix', + default='-vpn', + help='Suffix to add to project name for vpn key and secgroups'), + cfg.IntOpt('auth_token_ttl', + default=3600, + help='Seconds for auth tokens to linger'), + cfg.StrOpt('state_path', + default=os.path.join(os.path.dirname(__file__), '../'), + help="Top-level directory for maintaining nova's state"), + cfg.StrOpt('lock_path', + default=os.path.join(os.path.dirname(__file__), '../'), + help='Directory for lock files'), + cfg.StrOpt('logdir', + default=None, + help='output to a per-service log file in named directory'), + cfg.StrOpt('logfile_mode', + default='0644', + help='Default file mode of the logs.'), + cfg.StrOpt('sqlite_db', + default='nova.sqlite', + help='file name for sqlite'), + cfg.BoolOpt('sqlite_synchronous', + default=True, + help='Synchronous mode for sqlite'), + cfg.StrOpt('sql_connection', + default='sqlite:///$state_path/$sqlite_db', + help='connection string for sql database'), + cfg.IntOpt('sql_idle_timeout', + default=3600, + help='timeout for idle sql database connections'), + cfg.IntOpt('sql_max_retries', + default=12, + help='sql connection attempts'), + cfg.IntOpt('sql_retry_interval', + default=10, + help='sql connection retry interval'), + cfg.StrOpt('compute_manager', + default='nova.compute.manager.ComputeManager', + help='Manager for compute'), + cfg.StrOpt('console_manager', + default='nova.console.manager.ConsoleProxyManager', + help='Manager for console proxy'), + cfg.StrOpt('cert_manager', + default='nova.cert.manager.CertManager', + help='Manager for cert'), + cfg.StrOpt('instance_dns_manager', + default='nova.network.dns_driver.DNSDriver', + help='DNS Manager for instance IPs'), + cfg.StrOpt('instance_dns_domain', + default='', + help='DNS Zone for instance IPs'), + cfg.StrOpt('floating_ip_dns_manager', + default='nova.network.dns_driver.DNSDriver', + help='DNS Manager for floating IPs'), + cfg.StrOpt('network_manager', + default='nova.network.manager.VlanManager', + help='Manager for network'), + cfg.StrOpt('volume_manager', + default='nova.volume.manager.VolumeManager', + help='Manager for volume'), + cfg.StrOpt('scheduler_manager', + default='nova.scheduler.manager.SchedulerManager', + help='Manager for scheduler'), + cfg.StrOpt('vsa_manager', + default='nova.vsa.manager.VsaManager', + help='Manager for vsa'), + cfg.StrOpt('vc_image_name', + default='vc_image', + help='the VC image ID (for a VC image that exists in Glance)'), + cfg.StrOpt('default_vsa_instance_type', + default='m1.small', + help='default instance type for VSA instances'), + cfg.IntOpt('max_vcs_in_vsa', + default=32, + help='maxinum VCs in a VSA'), + cfg.IntOpt('vsa_part_size_gb', + default=100, + help='default partition size for shared capacity'), + cfg.StrOpt('firewall_driver', + default='nova.virt.libvirt.firewall.IptablesFirewallDriver', + help='Firewall driver (defaults to iptables)'), + cfg.StrOpt('image_service', + default='nova.image.glance.GlanceImageService', + help='The service to use for retrieving and searching images.'), + cfg.StrOpt('host', + default=socket.gethostname(), + help='Name of this node. This can be an opaque identifier. ' + 'It is not necessarily a hostname, FQDN, or IP address.'), + cfg.StrOpt('node_availability_zone', + default='nova', + help='availability zone of this node'), + cfg.StrOpt('notification_driver', + default='nova.notifier.no_op_notifier', + help='Default driver for sending notifications'), + cfg.ListOpt('memcached_servers', + default=None, + help='Memcached servers or None for in process cache.'), + cfg.StrOpt('zone_name', + default='nova', + help='name of this zone'), + cfg.ListOpt('zone_capabilities', + default=['hypervisor=xenserver;kvm', 'os=linux;windows'], + help='Key/Multi-value list with the capabilities of the zone'), + cfg.StrOpt('build_plan_encryption_key', + default=None, + help='128bit (hex) encryption key for scheduler build plans.'), + cfg.StrOpt('instance_usage_audit_period', + default='month', + help='time period to generate instance usages for.'), + cfg.IntOpt('bandwith_poll_interval', + default=600, + help='interval to pull bandwidth usage info'), + cfg.BoolOpt('start_guests_on_host_boot', + default=False, + help='Whether to restart guests when the host reboots'), + cfg.BoolOpt('resume_guests_state_on_host_boot', + default=False, + help='Whether to start guests that were running before the ' + 'host rebooted'), + cfg.StrOpt('default_ephemeral_format', + default=None, + help='The default format a ephemeral_volume will be ' + 'formatted with on creation.'), + cfg.StrOpt('root_helper', + default='sudo', + help='Command prefix to use for running commands as root'), + cfg.StrOpt('network_driver', + default='nova.network.linux_net', + help='Driver to use for network creation'), + cfg.BoolOpt('use_ipv6', + default=False, + help='use ipv6'), + cfg.IntOpt('password_length', + default=12, + help='Length of generated instance admin passwords'), + cfg.BoolOpt('monkey_patch', + default=False, + help='Whether to log monkey patching'), + cfg.ListOpt('monkey_patch_modules', + default=[ + 'nova.api.ec2.cloud:nova.notifier.api.notify_decorator', + 'nova.compute.api:nova.notifier.api.notify_decorator' + ], + help='List of modules/decorators to monkey patch'), + cfg.BoolOpt('allow_resize_to_same_host', + default=False, + help='Allow destination machine to match source for resize. ' + 'Useful when testing in single-host environments.'), + cfg.StrOpt('stub_network', + default=False, + help='Stub network related code'), + cfg.IntOpt('reclaim_instance_interval', + default=0, + help='Interval in seconds for reclaiming deleted instances'), + cfg.IntOpt('zombie_instance_updated_at_window', + default=172800, + help='Number of seconds zombie instances are cleaned up.'), + cfg.BoolOpt('allow_ec2_admin_api', + default=False, + help='Enable/Disable EC2 Admin API'), + cfg.IntOpt('service_down_time', + default=60, + help='maximum time since last check-in for up service'), + cfg.StrOpt('default_schedule_zone', + default=None, + help='zone to use when user doesnt specify one'), + cfg.ListOpt('isolated_images', + default=[], + help='Images to run on isolated host'), + cfg.ListOpt('isolated_hosts', + default=[], + help='Host reserved for specific images'), + ] -DEFINE_string('vpn_image_id', '0', 'image id for cloudpipe vpn server') -DEFINE_string('vpn_key_suffix', - '-vpn', - 'Suffix to add to project name for vpn key and secgroups') - -DEFINE_integer('auth_token_ttl', 3600, 'Seconds for auth tokens to linger') - -DEFINE_string('state_path', os.path.join(os.path.dirname(__file__), '../'), - "Top-level directory for maintaining nova's state") -DEFINE_string('lock_path', os.path.join(os.path.dirname(__file__), '../'), - 'Directory for lock files') -DEFINE_string('logdir', None, 'output to a per-service log file in named ' - 'directory') -DEFINE_string('logfile_mode', '0644', 'Default file mode of the logs.') -DEFINE_string('sqlite_db', 'nova.sqlite', 'file name for sqlite') -DEFINE_bool('sqlite_synchronous', True, 'Synchronous mode for sqlite') -DEFINE_string('sql_connection', - 'sqlite:///$state_path/$sqlite_db', - 'connection string for sql database') -DEFINE_integer('sql_idle_timeout', - 3600, - 'timeout for idle sql database connections') -DEFINE_integer('sql_max_retries', 12, 'sql connection attempts') -DEFINE_integer('sql_retry_interval', 10, 'sql connection retry interval') - -DEFINE_string('compute_manager', 'nova.compute.manager.ComputeManager', - 'Manager for compute') -DEFINE_string('console_manager', 'nova.console.manager.ConsoleProxyManager', - 'Manager for console proxy') -DEFINE_string('cert_manager', 'nova.cert.manager.CertManager', - 'Manager for cert') -DEFINE_string('instance_dns_manager', - 'nova.network.dns_driver.DNSDriver', - 'DNS Manager for instance IPs') -DEFINE_string('instance_dns_domain', '', - 'DNS Zone for instance IPs') -DEFINE_string('floating_ip_dns_manager', - 'nova.network.dns_driver.DNSDriver', - 'DNS Manager for floating IPs') -DEFINE_string('network_manager', 'nova.network.manager.VlanManager', - 'Manager for network') -DEFINE_string('volume_manager', 'nova.volume.manager.VolumeManager', - 'Manager for volume') -DEFINE_string('scheduler_manager', 'nova.scheduler.manager.SchedulerManager', - 'Manager for scheduler') -DEFINE_string('vsa_manager', 'nova.vsa.manager.VsaManager', - 'Manager for vsa') -DEFINE_string('vc_image_name', 'vc_image', - 'the VC image ID (for a VC image that exists in DB Glance)') -# VSA constants and enums -DEFINE_string('default_vsa_instance_type', 'm1.small', - 'default instance type for VSA instances') -DEFINE_integer('max_vcs_in_vsa', 32, - 'maxinum VCs in a VSA') -DEFINE_integer('vsa_part_size_gb', 100, - 'default partition size for shared capacity') -# Default firewall driver for security groups and provider firewall -DEFINE_string('firewall_driver', - 'nova.virt.libvirt.firewall.IptablesFirewallDriver', - 'Firewall driver (defaults to iptables)') -# The service to use for image search and retrieval -DEFINE_string('image_service', 'nova.image.glance.GlanceImageService', - 'The service to use for retrieving and searching for images.') - -DEFINE_string('host', socket.gethostname(), - 'Name of this node. This can be an opaque identifier. It is ' - 'not necessarily a hostname, FQDN, or IP address.') - -DEFINE_string('node_availability_zone', 'nova', - 'availability zone of this node') - -DEFINE_string('notification_driver', - 'nova.notifier.no_op_notifier', - 'Default driver for sending notifications') -DEFINE_list('memcached_servers', None, - 'Memcached servers or None for in process cache.') - -DEFINE_string('zone_name', 'nova', 'name of this zone') -DEFINE_list('zone_capabilities', - ['hypervisor=xenserver;kvm', 'os=linux;windows'], - 'Key/Multi-value list representng capabilities of this zone') -DEFINE_string('build_plan_encryption_key', None, - '128bit (hex) encryption key for scheduler build plans.') -DEFINE_string('instance_usage_audit_period', 'month', - 'time period to generate instance usages for.') -DEFINE_integer('bandwith_poll_interval', 600, - 'interval to pull bandwidth usage info') - -DEFINE_bool('start_guests_on_host_boot', False, - 'Whether to restart guests when the host reboots') -DEFINE_bool('resume_guests_state_on_host_boot', False, - 'Whether to start guests, that was running before the host reboot') -DEFINE_string('default_ephemeral_format', - None, - 'The default format a ephemeral_volume will be formatted ' - 'with on creation.') - -DEFINE_string('root_helper', 'sudo', - 'Command prefix to use for running commands as root') - -DEFINE_string('network_driver', 'nova.network.linux_net', - 'Driver to use for network creation') - -DEFINE_bool('use_ipv6', False, 'use ipv6') - -DEFINE_integer('password_length', 12, - 'Length of generated instance admin passwords') - -DEFINE_bool('monkey_patch', False, - 'Whether to log monkey patching') - -DEFINE_list('monkey_patch_modules', - ['nova.api.ec2.cloud:nova.notifier.api.notify_decorator', - 'nova.compute.api:nova.notifier.api.notify_decorator'], - 'Module list representing monkey ' - 'patched module and decorator') - -DEFINE_bool('allow_resize_to_same_host', False, - 'Allow destination machine to match source for resize. Useful' - ' when testing in environments with only one host machine.') - -DEFINE_string('stub_network', False, - 'Stub network related code') - -DEFINE_integer('reclaim_instance_interval', 0, - 'Interval in seconds for reclaiming deleted instances') - -DEFINE_integer('zombie_instance_updated_at_window', 172800, - 'Limit in seconds that a zombie instance can exist before ' - 'being cleaned up.') - -DEFINE_boolean('allow_ec2_admin_api', False, 'Enable/Disable EC2 Admin API') - -DEFINE_integer('service_down_time', 60, - 'maximum time since last check-in for up service') -DEFINE_string('default_schedule_zone', None, - 'zone to use when user doesnt specify one') -DEFINE_list('isolated_images', [], 'Images to run on isolated host') -DEFINE_list('isolated_hosts', [], 'Host reserved for specific images') +FLAGS.add_options(global_opts) diff --git a/nova/log.py b/nova/log.py index 8400f700..8052f79a 100644 --- a/nova/log.py +++ b/nova/log.py @@ -38,40 +38,52 @@ import sys import traceback import nova +from nova.common import cfg from nova import flags from nova import local from nova import version -FLAGS = flags.FLAGS -flags.DEFINE_string('logging_context_format_string', - '%(asctime)s %(levelname)s %(name)s ' - '[%(request_id)s %(user_id)s ' - '%(project_id)s] %(message)s', - 'format string to use for log messages with context') -flags.DEFINE_string('logging_default_format_string', - '%(asctime)s %(levelname)s %(name)s [-] ' - '%(message)s', - 'format string to use for log messages without context') -flags.DEFINE_string('logging_debug_format_suffix', - 'from (pid=%(process)d) %(funcName)s' - ' %(pathname)s:%(lineno)d', - 'data to append to log format when level is DEBUG') -flags.DEFINE_string('logging_exception_prefix', - '(%(name)s): TRACE: ', - 'prefix each line of exception output with this format') -flags.DEFINE_list('default_log_levels', - ['amqplib=WARN', - 'sqlalchemy=WARN', - 'boto=WARN', - 'suds=INFO', - 'eventlet.wsgi.server=WARN'], - 'list of logger=LEVEL pairs') -flags.DEFINE_bool('use_syslog', False, 'output to syslog') -flags.DEFINE_bool('publish_errors', False, 'publish error events') -flags.DEFINE_string('logfile', None, 'output to named file') -flags.DEFINE_bool('use_stderr', True, 'log to standard error') +log_opts = [ + cfg.StrOpt('logging_context_format_string', + default='%(asctime)s %(levelname)s %(name)s [%(request_id)s ' + '%(user_id)s %(project_id)s] %(message)s', + help='format string to use for log messages with context'), + cfg.StrOpt('logging_default_format_string', + default='%(asctime)s %(levelname)s %(name)s [-] %(message)s', + help='format string to use for log messages without context'), + cfg.StrOpt('logging_debug_format_suffix', + default='from (pid=%(process)d) %(funcName)s ' + '%(pathname)s:%(lineno)d', + help='data to append to log format when level is DEBUG'), + cfg.StrOpt('logging_exception_prefix', + default='(%(name)s): TRACE: ', + help='prefix each line of exception output with this format'), + cfg.ListOpt('default_log_levels', + default=[ + 'amqplib=WARN', + 'sqlalchemy=WARN', + 'boto=WARN', + 'suds=INFO', + 'eventlet.wsgi.server=WARN' + ], + help='list of logger=LEVEL pairs'), + cfg.BoolOpt('use_syslog', + default=False, + help='output to syslog'), + cfg.BoolOpt('publish_errors', + default=False, + help='publish error events'), + cfg.StrOpt('logfile', + default=None, + help='output to named file'), + cfg.BoolOpt('use_stderr', + default=True, + help='log to standard error'), + ] +FLAGS = flags.FLAGS +FLAGS.add_options(log_opts) # A list of things we want to replicate from logging. # levels diff --git a/nova/notifier/api.py b/nova/notifier/api.py index 04383853..50730cb0 100644 --- a/nova/notifier/api.py +++ b/nova/notifier/api.py @@ -15,19 +15,25 @@ import uuid +from nova.common import cfg from nova import flags from nova import utils from nova import log as logging + LOG = logging.getLogger('nova.exception') +notifier_opts = [ + cfg.StrOpt('default_notification_level', + default='INFO', + help='Default notification level for outgoing notifications'), + cfg.StrOpt('default_publisher_id', + default='$host', + help='Default publisher_id for outgoing notifications'), + ] + FLAGS = flags.FLAGS - -flags.DEFINE_string('default_notification_level', 'INFO', - 'Default notification level for outgoing notifications') -flags.DEFINE_string('default_publisher_id', FLAGS.host, - 'Default publisher_id for outgoing notifications') - +FLAGS.add_options(notifier_opts) WARN = 'WARN' INFO = 'INFO' diff --git a/nova/notifier/list_notifier.py b/nova/notifier/list_notifier.py index 62847c85..29c6ba72 100644 --- a/nova/notifier/list_notifier.py +++ b/nova/notifier/list_notifier.py @@ -13,16 +13,20 @@ # License for the specific language governing permissions and limitations # under the License. +from nova.common import cfg from nova import flags from nova import log as logging from nova import utils from nova.exception import ClassNotFound -flags.DEFINE_multistring('list_notifier_drivers', - ['nova.notifier.no_op_notifier'], - 'List of drivers to send notifications') + +list_notifier_drivers_opt = \ + cfg.MultiStrOpt('list_notifier_drivers', + default=['nova.notifier.no_op_notifier'], + help='List of drivers to send notifications') FLAGS = flags.FLAGS +FLAGS.add_option(list_notifier_drivers_opt) LOG = logging.getLogger('nova.notifier.list_notifier') diff --git a/nova/notifier/rabbit_notifier.py b/nova/notifier/rabbit_notifier.py index 64e03697..c88f76cb 100644 --- a/nova/notifier/rabbit_notifier.py +++ b/nova/notifier/rabbit_notifier.py @@ -16,14 +16,18 @@ import nova.context +from nova.common import cfg from nova import flags from nova import rpc -FLAGS = flags.FLAGS +notification_topic_opt = \ + cfg.StrOpt('notification_topic', + default='notifications', + help='RabbitMQ topic used for Nova notifications') -flags.DEFINE_string('notification_topic', 'notifications', - 'RabbitMQ topic used for Nova notifications') +FLAGS = flags.FLAGS +FLAGS.add_option(notification_topic_opt) def notify(message): diff --git a/nova/rpc/__init__.py b/nova/rpc/__init__.py index a26d53d0..db42640b 100644 --- a/nova/rpc/__init__.py +++ b/nova/rpc/__init__.py @@ -17,15 +17,19 @@ # License for the specific language governing permissions and limitations # under the License. - +from nova.common import cfg from nova.utils import import_object from nova.rpc.common import RemoteError, LOG from nova import flags + +rpc_backend_opt = \ + cfg.StrOpt('rpc_backend', + default='nova.rpc.impl_kombu', + help="The messaging module to use, defaults to kombu.") + FLAGS = flags.FLAGS -flags.DEFINE_string('rpc_backend', - 'nova.rpc.impl_kombu', - "The messaging module to use, defaults to kombu.") +FLAGS.add_option(rpc_backend_opt) def create_connection(new=True): diff --git a/nova/rpc/common.py b/nova/rpc/common.py index 25f28725..ff057701 100644 --- a/nova/rpc/common.py +++ b/nova/rpc/common.py @@ -19,6 +19,7 @@ import copy +from nova.common import cfg from nova import exception from nova import flags from nova import log as logging @@ -26,10 +27,16 @@ from nova import log as logging LOG = logging.getLogger('nova.rpc') -flags.DEFINE_integer('rpc_thread_pool_size', 1024, - 'Size of RPC thread pool') -flags.DEFINE_integer('rpc_conn_pool_size', 30, - 'Size of RPC connection pool') +rpc_opts = [ + cfg.IntOpt('rpc_thread_pool_size', + default=1024, + help='Size of RPC thread pool'), + cfg.IntOpt('rpc_conn_pool_size', + default=30, + help='Size of RPC connection pool'), + ] + +flags.FLAGS.add_options(rpc_opts) class RemoteError(exception.NovaException): diff --git a/nova/rpc/impl_qpid.py b/nova/rpc/impl_qpid.py index cddc318f..3ea921a8 100644 --- a/nova/rpc/impl_qpid.py +++ b/nova/rpc/impl_qpid.py @@ -25,36 +25,59 @@ import greenlet import qpid.messaging import qpid.messaging.exceptions +from nova.common import cfg from nova import flags from nova.rpc import amqp as rpc_amqp from nova.rpc.common import LOG -flags.DEFINE_string('qpid_hostname', 'localhost', 'Qpid broker hostname') -flags.DEFINE_string('qpid_port', '5672', 'Qpid broker port') -flags.DEFINE_string('qpid_username', '', 'Username for qpid connection') -flags.DEFINE_string('qpid_password', '', 'Password for qpid connection') -flags.DEFINE_string('qpid_sasl_mechanisms', '', - 'Space separated list of SASL mechanisms to use for auth') -flags.DEFINE_boolean('qpid_reconnect', True, 'Automatically reconnect') -flags.DEFINE_integer('qpid_reconnect_timeout', 0, - 'Reconnection timeout in seconds') -flags.DEFINE_integer('qpid_reconnect_limit', 0, - 'Max reconnections before giving up') -flags.DEFINE_integer('qpid_reconnect_interval_min', 0, - 'Minimum seconds between reconnection attempts') -flags.DEFINE_integer('qpid_reconnect_interval_max', 0, - 'Maximum seconds between reconnection attempts') -flags.DEFINE_integer('qpid_reconnect_interval', 0, - 'Equivalent to setting max and min to the same value') -flags.DEFINE_integer('qpid_heartbeat', 5, - 'Seconds between heartbeats used to keep the connection alive') -flags.DEFINE_string('qpid_protocol', 'tcp', - "Transport to use, either 'tcp' or 'ssl'") -flags.DEFINE_boolean('qpid_tcp_nodelay', True, 'Disable Nagle algorithm') - +qpid_opts = [ + cfg.StrOpt('qpid_hostname', + default='localhost', + help='Qpid broker hostname'), + cfg.StrOpt('qpid_port', + default='5672', + help='Qpid broker port'), + cfg.StrOpt('qpid_username', + default='', + help='Username for qpid connection'), + cfg.StrOpt('qpid_password', + default='', + help='Password for qpid connection'), + cfg.StrOpt('qpid_sasl_mechanisms', + default='', + help='Space separated list of SASL mechanisms to use for auth'), + cfg.BoolOpt('qpid_reconnect', + default=True, + help='Automatically reconnect'), + cfg.IntOpt('qpid_reconnect_timeout', + default=0, + help='Reconnection timeout in seconds'), + cfg.IntOpt('qpid_reconnect_limit', + default=0, + help='Max reconnections before giving up'), + cfg.IntOpt('qpid_reconnect_interval_min', + default=0, + help='Minimum seconds between reconnection attempts'), + cfg.IntOpt('qpid_reconnect_interval_max', + default=0, + help='Maximum seconds between reconnection attempts'), + cfg.IntOpt('qpid_reconnect_interval', + default=0, + help='Equivalent to setting max and min to the same value'), + cfg.IntOpt('qpid_heartbeat', + default=5, + help='Seconds between connection keepalive heartbeats'), + cfg.StrOpt('qpid_protocol', + default='tcp', + help="Transport to use, either 'tcp' or 'ssl'"), + cfg.BoolOpt('qpid_tcp_nodelay', + default=True, + help='Disable Nagle algorithm'), + ] FLAGS = flags.FLAGS +FLAGS.add_options(qpid_opts) class ConsumerBase(object): diff --git a/nova/scheduler/api.py b/nova/scheduler/api.py index 59f93b95..c814ad66 100644 --- a/nova/scheduler/api.py +++ b/nova/scheduler/api.py @@ -22,6 +22,7 @@ import functools from novaclient import v1_1 as novaclient from novaclient import exceptions as novaclient_exceptions +from nova.common import cfg from nova import db from nova import exception from nova import flags @@ -31,10 +32,14 @@ from nova import utils from eventlet import greenpool + +enable_zone_routing_opt = \ + cfg.BoolOpt('enable_zone_routing', + default=False, + help='When True, routing to child zones will occur.') + FLAGS = flags.FLAGS -flags.DEFINE_bool('enable_zone_routing', - False, - 'When True, routing to child zones will occur.') +FLAGS.add_option(enable_zone_routing_opt) LOG = logging.getLogger('nova.scheduler.api') diff --git a/nova/scheduler/least_cost.py b/nova/scheduler/least_cost.py index c14e9374..90ba4c2a 100644 --- a/nova/scheduler/least_cost.py +++ b/nova/scheduler/least_cost.py @@ -22,24 +22,32 @@ The cost-function and weights are tabulated, and the host with the least cost is then selected for provisioning. """ - +from nova.common import cfg from nova import flags from nova import log as logging + LOG = logging.getLogger('nova.scheduler.least_cost') -FLAGS = flags.FLAGS -flags.DEFINE_list('least_cost_functions', - ['nova.scheduler.least_cost.compute_fill_first_cost_fn'], - 'Which cost functions the LeastCostScheduler should use.') +least_cost_opts = [ + cfg.ListOpt('least_cost_functions', + default=[ + 'nova.scheduler.least_cost.compute_fill_first_cost_fn' + ], + help='Which cost functions the LeastCostScheduler should use'), + cfg.FloatOpt('noop_cost_fn_weight', + default=1.0, + help='How much weight to give the noop cost function'), + cfg.FloatOpt('compute_fill_first_cost_fn_weight', + default=1.0, + help='How much weight to give the fill-first cost function'), + ] +FLAGS = flags.FLAGS +FLAGS.add_options(least_cost_opts) # TODO(sirp): Once we have enough of these rules, we can break them out into a # cost_functions.py file (perhaps in a least_cost_scheduler directory) -flags.DEFINE_float('noop_cost_fn_weight', 1.0, - 'How much weight to give the noop cost function') -flags.DEFINE_float('compute_fill_first_cost_fn_weight', 1.0, - 'How much weight to give the fill-first cost function') class WeightedHost(object): diff --git a/nova/scheduler/multi.py b/nova/scheduler/multi.py index 31d92583..3bc67052 100644 --- a/nova/scheduler/multi.py +++ b/nova/scheduler/multi.py @@ -20,19 +20,24 @@ """ Scheduler that allows routing some calls to one driver and others to another. """ + +from nova.common import cfg from nova import flags from nova import utils from nova.scheduler import driver -FLAGS = flags.FLAGS -flags.DEFINE_string('compute_scheduler_driver', - 'nova.scheduler.chance.ChanceScheduler', - 'Driver to use for scheduling compute calls') -flags.DEFINE_string('volume_scheduler_driver', - 'nova.scheduler.chance.ChanceScheduler', - 'Driver to use for scheduling volume calls') +multi_scheduler_opts = [ + cfg.StrOpt('compute_scheduler_driver', + default='nova.scheduler.chance.ChanceScheduler', + help='Driver to use for scheduling compute calls'), + cfg.StrOpt('volume_scheduler_driver', + default='nova.scheduler.chance.ChanceScheduler', + help='Driver to use for scheduling volume calls'), + ] +FLAGS = flags.FLAGS +FLAGS.add_options(multi_scheduler_opts) # A mapping of methods to topics so we can figure out which driver to use. _METHOD_MAP = {'run_instance': 'compute', diff --git a/nova/scheduler/simple.py b/nova/scheduler/simple.py index a61005bf..e913730c 100644 --- a/nova/scheduler/simple.py +++ b/nova/scheduler/simple.py @@ -21,6 +21,7 @@ Simple Scheduler """ +from nova.common import cfg from nova import db from nova import flags from nova import exception @@ -28,15 +29,24 @@ from nova.scheduler import driver from nova.scheduler import chance from nova import utils + +simple_scheduler_opts = [ + cfg.IntOpt("max_cores", + default=16, + help="maximum number of instance cores to allow per host"), + cfg.IntOpt("max_gigabytes", + default=10000, + help="maximum number of volume gigabytes to allow per host"), + cfg.IntOpt("max_networks", + default=1000, + help="maximum number of networks to allow per host"), + cfg.BoolOpt('skip_isolated_core_check', + default=True, + help='Allow overcommitting vcpus on isolated hosts'), + ] + FLAGS = flags.FLAGS -flags.DEFINE_integer("max_cores", 16, - "maximum number of instance cores to allow per host") -flags.DEFINE_integer("max_gigabytes", 10000, - "maximum number of volume gigabytes to allow per host") -flags.DEFINE_integer("max_networks", 1000, - "maximum number of networks to allow per host") -flags.DEFINE_boolean('skip_isolated_core_check', True, - 'Allow overcommitting vcpus on isolated hosts') +FLAGS.add_options(simple_scheduler_opts) class SimpleScheduler(chance.ChanceScheduler): diff --git a/nova/scheduler/vsa.py b/nova/scheduler/vsa.py index 7b45e93e..989841d3 100644 --- a/nova/scheduler/vsa.py +++ b/nova/scheduler/vsa.py @@ -19,6 +19,7 @@ VSA Simple Scheduler """ +from nova.common import cfg from nova import context from nova import db from nova import flags @@ -31,15 +32,23 @@ from nova.scheduler import simple from nova.vsa.api import VsaState from nova.volume import volume_types + LOG = logging.getLogger('nova.scheduler.vsa') +vsa_scheduler_opts = [ + cfg.IntOpt('drive_type_approx_capacity_percent', + default=10, + help='The percentage range for capacity comparison'), + cfg.IntOpt('vsa_unique_hosts_per_alloc', + default=10, + help='The number of unique hosts per storage allocation'), + cfg.BoolOpt('vsa_select_unique_drives', + default=True, + help='Allow selection of same host for multiple drives'), + ] + FLAGS = flags.FLAGS -flags.DEFINE_integer('drive_type_approx_capacity_percent', 10, - 'The percentage range for capacity comparison') -flags.DEFINE_integer('vsa_unique_hosts_per_alloc', 10, - 'The number of unique hosts per storage allocation') -flags.DEFINE_boolean('vsa_select_unique_drives', True, - 'Allow selection of same host for multiple drives') +FLAGS.add_options(vsa_scheduler_opts) def BYTES_TO_GB(bytes): diff --git a/nova/scheduler/zone_manager.py b/nova/scheduler/zone_manager.py index 0e86a89c..c27e6bdb 100644 --- a/nova/scheduler/zone_manager.py +++ b/nova/scheduler/zone_manager.py @@ -23,16 +23,24 @@ import traceback from eventlet import greenpool from novaclient import v1_1 as novaclient +from nova.common import cfg from nova import db from nova import flags from nova import log as logging from nova import utils + +zone_manager_opts = [ + cfg.IntOpt('zone_db_check_interval', + default=60, + help='Seconds between getting fresh zone info from db.'), + cfg.IntOpt('zone_failures_to_offline', + default=3, + help='Number of consecutive errors before offlining a zone'), + ] + FLAGS = flags.FLAGS -flags.DEFINE_integer('zone_db_check_interval', 60, - 'Seconds between getting fresh zone info from db.') -flags.DEFINE_integer('zone_failures_to_offline', 3, - 'Number of consecutive errors before marking zone offline') +FLAGS.add_options(zone_manager_opts) LOG = logging.getLogger('nova.scheduler.zone_manager') diff --git a/nova/tests/declare_flags.py b/nova/tests/declare_flags.py index 51a55ec7..9dc57886 100644 --- a/nova/tests/declare_flags.py +++ b/nova/tests/declare_flags.py @@ -16,8 +16,8 @@ # License for the specific language governing permissions and limitations # under the License. +from nova.common import cfg from nova import flags FLAGS = flags.FLAGS - -flags.DEFINE_integer('answer', 42, 'test flag') +FLAGS.add_option(cfg.IntOpt('answer', default=42, help='test flag')) diff --git a/nova/tests/runtime_flags.py b/nova/tests/runtime_flags.py index 1eb50140..1a28f4fb 100644 --- a/nova/tests/runtime_flags.py +++ b/nova/tests/runtime_flags.py @@ -16,8 +16,8 @@ # License for the specific language governing permissions and limitations # under the License. +from nova.common import cfg from nova import flags FLAGS = flags.FLAGS - -flags.DEFINE_integer('runtime_answer', 54, 'test flag') +FLAGS.add_option(cfg.IntOpt('runtime_answer', default=54, help='test flag')) diff --git a/nova/tests/test_flags.py b/nova/tests/test_flags.py index b5fe1198..02ee49ef 100644 --- a/nova/tests/test_flags.py +++ b/nova/tests/test_flags.py @@ -21,11 +21,14 @@ import exceptions import os import tempfile +from nova.common import cfg from nova import flags from nova import test FLAGS = flags.FLAGS -flags.DEFINE_string('flags_unittest', 'foo', 'for testing purposes only') +FLAGS.add_option(cfg.StrOpt('flags_unittest', + default='foo', + help='for testing purposes only')) class FlagsTestCase(test.TestCase): @@ -41,11 +44,11 @@ class FlagsTestCase(test.TestCase): self.assert_('false' not in self.FLAGS) self.assert_('true' not in self.FLAGS) - flags.DEFINE_string('string', 'default', 'desc', - flag_values=self.FLAGS) - flags.DEFINE_integer('int', 1, 'desc', flag_values=self.FLAGS) - flags.DEFINE_bool('false', False, 'desc', flag_values=self.FLAGS) - flags.DEFINE_bool('true', True, 'desc', flag_values=self.FLAGS) + self.FLAGS.add_option(cfg.StrOpt('string', + default='default', help='desc')) + self.FLAGS.add_option(cfg.IntOpt('int', default=1, help='desc')) + self.FLAGS.add_option(cfg.BoolOpt('false', default=False, help='desc')) + self.FLAGS.add_option(cfg.BoolOpt('true', default=True, help='desc')) self.assert_(self.FLAGS['string']) self.assert_(self.FLAGS['int']) @@ -69,12 +72,12 @@ class FlagsTestCase(test.TestCase): self.assertEqual(self.FLAGS.true, False) def test_define_float(self): - flags.DEFINE_float('float', 6.66, 'desc', flag_values=self.FLAGS) + self.FLAGS.add_option(cfg.FloatOpt('float', default=6.66, help='desc')) self.assertEqual(self.FLAGS.float, 6.66) def test_define_multistring(self): - flags.DEFINE_multistring('multi', ['blaa'], 'desc', - flag_values=self.FLAGS) + self.FLAGS.add_option(cfg.MultiStrOpt('multi', + default=['blaa'], help='desc')) self.assert_(self.FLAGS['multi']) self.assertEqual(self.FLAGS.multi, ['blaa']) @@ -89,7 +92,8 @@ class FlagsTestCase(test.TestCase): self.assertEqual(self.FLAGS.multi, ['foo', 'bar']) def test_define_list(self): - flags.DEFINE_list('list', ['foo'], 'desc', flag_values=self.FLAGS) + self.FLAGS.add_option(cfg.ListOpt('list', + default=['foo'], help='desc')) self.assert_(self.FLAGS['list']) self.assertEqual(self.FLAGS.list, ['foo']) @@ -100,7 +104,7 @@ class FlagsTestCase(test.TestCase): self.assertEqual(self.FLAGS.list, ['a', 'b', 'c', 'd']) def test_error(self): - flags.DEFINE_integer('error', 1, 'desc', flag_values=self.FLAGS) + self.FLAGS.add_option(cfg.IntOpt('error', default=1, help='desc')) self.assertEqual(self.FLAGS.error, 1) @@ -143,16 +147,16 @@ class FlagsTestCase(test.TestCase): self.assertEqual(self.global_FLAGS.runtime_answer, 60) def test_long_vs_short_flags(self): - flags.DEFINE_string('duplicate_answer_long', 'val', 'desc', - flag_values=self.global_FLAGS) + self.global_FLAGS.add_option(cfg.StrOpt('duplicate_answer_long', + default='val', help='desc')) argv = ['flags_test', '--duplicate_answer=60', 'extra_arg'] args = self.global_FLAGS(argv) self.assert_('duplicate_answer' not in self.global_FLAGS) self.assert_(self.global_FLAGS.duplicate_answer_long, 60) - flags.DEFINE_integer('duplicate_answer', 60, 'desc', - flag_values=self.global_FLAGS) + self.global_FLAGS.add_option(cfg.IntOpt('duplicate_answer', + default=60, help='desc')) self.assertEqual(self.global_FLAGS.duplicate_answer, 60) self.assertEqual(self.global_FLAGS.duplicate_answer_long, 'val') @@ -178,13 +182,13 @@ class FlagsTestCase(test.TestCase): self.assertEqual(FLAGS.FlagValuesDict()['flags_unittest'], 'foo') def test_flagfile(self): - flags.DEFINE_string('string', 'default', 'desc', - flag_values=self.FLAGS) - flags.DEFINE_integer('int', 1, 'desc', flag_values=self.FLAGS) - flags.DEFINE_bool('false', False, 'desc', flag_values=self.FLAGS) - flags.DEFINE_bool('true', True, 'desc', flag_values=self.FLAGS) - flags.DEFINE_multistring('multi', ['blaa'], 'desc', - flag_values=self.FLAGS) + self.FLAGS.add_option(cfg.StrOpt('string', + default='default', help='desc')) + self.FLAGS.add_option(cfg.IntOpt('int', default=1, help='desc')) + self.FLAGS.add_option(cfg.BoolOpt('false', default=False, help='desc')) + self.FLAGS.add_option(cfg.BoolOpt('true', default=True, help='desc')) + self.FLAGS.add_option(cfg.MultiStrOpt('multi', + default=['blaa'], help='desc')) (fd, path) = tempfile.mkstemp(prefix='nova', suffix='.flags') @@ -208,14 +212,15 @@ class FlagsTestCase(test.TestCase): os.remove(path) def test_defaults(self): - flags.DEFINE_string('foo', 'bar', 'help', flag_values=self.FLAGS) + self.FLAGS.add_option(cfg.StrOpt('foo', default='bar', help='desc')) self.assertEqual(self.FLAGS.foo, 'bar') self.FLAGS['foo'].SetDefault('blaa') self.assertEqual(self.FLAGS.foo, 'blaa') def test_templated_values(self): - flags.DEFINE_string('foo', 'foo', 'help', flag_values=self.FLAGS) - flags.DEFINE_string('bar', 'bar', 'help', flag_values=self.FLAGS) - flags.DEFINE_string('blaa', '$foo$bar', 'help', flag_values=self.FLAGS) + self.FLAGS.add_option(cfg.StrOpt('foo', default='foo', help='desc')) + self.FLAGS.add_option(cfg.StrOpt('bar', default='bar', help='desc')) + self.FLAGS.add_option(cfg.StrOpt('blaa', + default='$foo$bar', help='desc')) self.assertEqual(self.FLAGS.blaa, 'foobar') diff --git a/nova/vsa/api.py b/nova/vsa/api.py index 27baff15..9c2bc0ce 100644 --- a/nova/vsa/api.py +++ b/nova/vsa/api.py @@ -25,6 +25,7 @@ For assistance and guidelines pls contact import sys +from nova.common import cfg from nova import compute from nova import exception from nova import flags @@ -45,15 +46,23 @@ class VsaState: DELETING = 'deleting' # VSA started the deletion procedure +vsa_opts = [ + cfg.StrOpt('vsa_ec2_access_key', + default=None, + help='EC2 access key used by VSA for accessing nova'), + cfg.StrOpt('vsa_ec2_user_id', + default=None, + help='User ID used by VSA for accessing nova'), + cfg.BoolOpt('vsa_multi_vol_creation', + default=True, + help='Ask scheduler to create multiple volumes in one call'), + cfg.StrOpt('vsa_volume_type_name', + default='VSA volume type', + help='Name of volume type associated with FE VSA volumes'), + ] + FLAGS = flags.FLAGS -flags.DEFINE_string('vsa_ec2_access_key', None, - 'EC2 access key used by VSA for accessing nova') -flags.DEFINE_string('vsa_ec2_user_id', None, - 'User ID used by VSA for accessing nova') -flags.DEFINE_boolean('vsa_multi_vol_creation', True, - 'Ask scheduler to create multiple volumes in one call') -flags.DEFINE_string('vsa_volume_type_name', 'VSA volume type', - 'Name of volume type associated with FE VSA volumes') +FLAGS.add_options(vsa_opts) LOG = logging.getLogger('nova.vsa') diff --git a/nova/vsa/manager.py b/nova/vsa/manager.py index 850d9958..42b5b103 100644 --- a/nova/vsa/manager.py +++ b/nova/vsa/manager.py @@ -22,6 +22,7 @@ Handles all processes relating to Virtual Storage Arrays (VSA). """ +from nova.common import cfg from nova import compute from nova import exception from nova import flags @@ -34,9 +35,13 @@ from nova.compute import instance_types from nova.vsa import utils as vsa_utils from nova.vsa.api import VsaState +vsa_driver_opt = \ + cfg.StrOpt('vsa_driver', + default='nova.vsa.connection.get_connection', + help='Driver to use for controlling VSAs') + FLAGS = flags.FLAGS -flags.DEFINE_string('vsa_driver', 'nova.vsa.connection.get_connection', - 'Driver to use for controlling VSAs') +FLAGS.add_option(vsa_driver_opt) LOG = logging.getLogger('nova.vsa.manager')