.. pyassert::
- constants.IPOLICY_ALL_KEYS == set([constants.ISPECS_MIN,
- constants.ISPECS_MAX,
+ constants.IPOLICY_ALL_KEYS == set([constants.ISPECS_MINMAX,
constants.ISPECS_STD,
constants.IPOLICY_DTS,
constants.IPOLICY_VCPU_RATIO,
.. |ispec-std| replace:: :pyeval:`constants.ISPECS_STD`
-|ispec-min|, |ispec-max|, |ispec-std|
- A sub- `dict` with the following fields, which sets the limit and standard
- values of the instances:
-
- :pyeval:`constants.ISPEC_MEM_SIZE`
- The size in MiB of the memory used
- :pyeval:`constants.ISPEC_DISK_SIZE`
- The size in MiB of the disk used
- :pyeval:`constants.ISPEC_DISK_COUNT`
- The numbers of disks used
- :pyeval:`constants.ISPEC_CPU_COUNT`
- The numbers of cpus used
- :pyeval:`constants.ISPEC_NIC_COUNT`
- The numbers of nics used
- :pyeval:`constants.ISPEC_SPINDLE_USE`
- The numbers of virtual disk spindles used by this instance. They are
- not real in the sense of actual HDD spindles, but useful for
- accounting the spindle usage on the residing node
+:pyeval:`constants.ISPECS_MINMAX`
+ A dict with the following two fields:
+
+ |ispec-min|, |ispec-max|
+ A sub- `dict` with the following fields, which sets the limit of the
+ instances:
+
+ :pyeval:`constants.ISPEC_MEM_SIZE`
+ The size in MiB of the memory used
+ :pyeval:`constants.ISPEC_DISK_SIZE`
+ The size in MiB of the disk used
+ :pyeval:`constants.ISPEC_DISK_COUNT`
+ The numbers of disks used
+ :pyeval:`constants.ISPEC_CPU_COUNT`
+ The numbers of cpus used
+ :pyeval:`constants.ISPEC_NIC_COUNT`
+ The numbers of nics used
+ :pyeval:`constants.ISPEC_SPINDLE_USE`
+ The numbers of virtual disk spindles used by this instance. They
+ are not real in the sense of actual HDD spindles, but useful for
+ accounting the spindle usage on the residing node
+|ispec-std|
+ A sub- `dict` with the same fields as |ispec-min| and |ispec-max| above,
+ which sets the standard values of the instances.
:pyeval:`constants.IPOLICY_DTS`
A `list` of disk templates allowed for instances using this policy
:pyeval:`constants.IPOLICY_VCPU_RATIO`
utils.ForceDictType(specs, forced_type, allowed_values=allowed_values)
# then transpose
+ ispecs = {
+ constants.ISPECS_MIN: {},
+ constants.ISPECS_MAX: {},
+ constants.ISPECS_STD: {},
+ }
for (name, specs) in ispecs_transposed.iteritems():
assert name in constants.ISPECS_PARAMETERS
for key, val in specs.items(): # {min: .. ,max: .., std: ..}
- ipolicy[key][name] = val
+ assert key in ispecs
+ ispecs[key][name] = val
+ for key in constants.ISPECS_MINMAX_KEYS:
+ ipolicy[constants.ISPECS_MINMAX][key] = ispecs[key]
+ ipolicy[constants.ISPECS_STD] = ispecs[constants.ISPECS_STD]
def CreateIPolicyFromOpts(ispecs_mem_size=None,
("Instance policy - limits for instances",
[
(key,
- _FormatGroupedParams(result["ipolicy"][key], roman=opts.roman_integers))
- for key in constants.IPOLICY_ISPECS
+ _FormatGroupedParams(result["ipolicy"][constants.ISPECS_MINMAX][key],
+ roman=opts.roman_integers))
+ for key in constants.ISPECS_MINMAX_KEYS
] +
[
+ (constants.ISPECS_STD,
+ _FormatGroupedParams(result["ipolicy"][constants.ISPECS_STD],
+ roman=opts.roman_integers)),
("enabled disk templates",
utils.CommaJoin(result["ipolicy"][constants.IPOLICY_DTS])),
] +
return params_copy
+def _UpdateMinMaxISpecs(ipolicy, new_minmax, group_policy):
+ use_none = use_default = group_policy
+ minmax = ipolicy.setdefault(constants.ISPECS_MINMAX, {})
+ for (key, value) in new_minmax.items():
+ if key not in constants.ISPECS_MINMAX_KEYS:
+ raise errors.OpPrereqError("Invalid key in new ipolicy/%s: %s" %
+ (constants.ISPECS_MINMAX, key),
+ errors.ECODE_INVAL)
+ old_spec = minmax.get(key, {})
+ minmax[key] = _GetUpdatedParams(old_spec, value, use_none=use_none,
+ use_default=use_default)
+ utils.ForceDictType(minmax[key], constants.ISPECS_PARAMETER_TYPES)
+
+
def _GetUpdatedIPolicy(old_ipolicy, new_ipolicy, group_policy=False):
- """Return the new version of a instance policy.
+ """Return the new version of an instance policy.
@param group_policy: whether this policy applies to a group and thus
we should support removal of policy entries
if key not in constants.IPOLICY_ALL_KEYS:
raise errors.OpPrereqError("Invalid key in new ipolicy: %s" % key,
errors.ECODE_INVAL)
- if key in constants.IPOLICY_ISPECS:
+ if key == constants.ISPECS_MINMAX:
+ _UpdateMinMaxISpecs(ipolicy, value, group_policy)
+ elif key == constants.ISPECS_STD:
ipolicy[key] = _GetUpdatedParams(old_ipolicy.get(key, {}), value,
use_none=use_none,
use_default=use_default)
" is down")
-def _ComputeMinMaxSpec(name, qualifier, ipolicy, value):
+def _ComputeMinMaxSpec(name, qualifier, ispecs, value):
"""Computes if value is in the desired range.
@param name: name of the parameter for which we perform the check
@param qualifier: a qualifier used in the error message (e.g. 'disk/1',
not just 'disk')
- @param ipolicy: dictionary containing min, max and std values
+ @param ispecs: dictionary containing min and max values
@param value: actual value that we want to use
- @return: None or element not meeting the criteria
-
+ @return: None or an error string
"""
if value in [None, constants.VALUE_AUTO]:
return None
- max_v = ipolicy[constants.ISPECS_MAX].get(name, value)
- min_v = ipolicy[constants.ISPECS_MIN].get(name, value)
+ max_v = ispecs[constants.ISPECS_MAX].get(name, value)
+ min_v = ispecs[constants.ISPECS_MIN].get(name, value)
if value > max_v or min_v > value:
if qualifier:
fqn = "%s/%s" % (name, qualifier)
ret.append("Disk template %s is not allowed (allowed templates: %s)" %
(disk_template, utils.CommaJoin(allowed_dts)))
+ minmax = ipolicy[constants.ISPECS_MINMAX]
return ret + filter(None,
- (_compute_fn(name, qualifier, ipolicy, value)
+ (_compute_fn(name, qualifier, minmax, value)
for (name, qualifier, value) in test_settings))
except errors.ConfigurationError, err:
result.append("%s has invalid nicparams: %s" % (owner, err))
- def _helper_ipolicy(owner, params, check_std):
+ def _helper_ipolicy(owner, ipolicy, iscluster):
try:
- objects.InstancePolicy.CheckParameterSyntax(params, check_std)
+ objects.InstancePolicy.CheckParameterSyntax(ipolicy, iscluster)
except errors.ConfigurationError, err:
result.append("%s has invalid instance policy: %s" % (owner, err))
-
- def _helper_ispecs(owner, params):
- for key, value in params.items():
- if key in constants.IPOLICY_ISPECS:
- fullkey = "ipolicy/" + key
- _helper(owner, fullkey, value, constants.ISPECS_PARAMETER_TYPES)
+ for key, value in ipolicy.items():
+ if key == constants.ISPECS_MINMAX:
+ _helper_ispecs(owner, "ipolicy/" + key, value)
+ elif key == constants.ISPECS_STD:
+ _helper(owner, "ipolicy/" + key, value,
+ constants.ISPECS_PARAMETER_TYPES)
else:
# FIXME: assuming list type
if key in constants.IPOLICY_PARAMETERS:
" expecting %s, got %s" %
(owner, key, exp_type.__name__, type(value)))
+ def _helper_ispecs(owner, parentkey, params):
+ for (key, value) in params.items():
+ fullkey = "/".join([parentkey, key])
+ _helper(owner, fullkey, value, constants.ISPECS_PARAMETER_TYPES)
+
# check cluster parameters
_helper("cluster", "beparams", cluster.SimpleFillBE({}),
constants.BES_PARAMETER_TYPES)
_helper_nic("cluster", cluster.SimpleFillNIC({}))
_helper("cluster", "ndparams", cluster.SimpleFillND({}),
constants.NDS_PARAMETER_TYPES)
- _helper_ipolicy("cluster", cluster.SimpleFillIPolicy({}), True)
- _helper_ispecs("cluster", cluster.SimpleFillIPolicy({}))
+ _helper_ipolicy("cluster", cluster.ipolicy, True)
# per-instance checks
for instance_name in data.instances:
group_name = "group %s" % nodegroup.name
_helper_ipolicy(group_name, cluster.SimpleFillIPolicy(nodegroup.ipolicy),
False)
- _helper_ispecs(group_name, cluster.SimpleFillIPolicy(nodegroup.ipolicy))
if nodegroup.ndparams:
_helper(group_name, "ndparams",
cluster.SimpleFillND(nodegroup.ndparams),
ISPECS_PARAMETERS = frozenset(ISPECS_PARAMETER_TYPES.keys())
+ISPECS_MINMAX = "minmax"
ISPECS_MIN = "min"
ISPECS_MAX = "max"
ISPECS_STD = "std"
IPOLICY_VCPU_RATIO = "vcpu-ratio"
IPOLICY_SPINDLE_RATIO = "spindle-ratio"
-IPOLICY_ISPECS = compat.UniqueFrozenset([
+ISPECS_MINMAX_KEYS = compat.UniqueFrozenset([
ISPECS_MIN,
ISPECS_MAX,
- ISPECS_STD,
])
IPOLICY_PARAMETERS = compat.UniqueFrozenset([
IPOLICY_SPINDLE_RATIO,
])
-IPOLICY_ALL_KEYS = (IPOLICY_ISPECS |
- IPOLICY_PARAMETERS |
- frozenset([IPOLICY_DTS]))
+IPOLICY_ALL_KEYS = (IPOLICY_PARAMETERS |
+ frozenset([ISPECS_MINMAX, ISPECS_STD, IPOLICY_DTS]))
# Node parameter names
ND_OOB_PROGRAM = "oob_program"
# All of the following values are quite arbitrarily - there are no
# "good" defaults, these must be customised per-site
-IPOLICY_DEFAULTS = {
+ISPECS_MINMAX_DEFAULTS = {
ISPECS_MIN: {
ISPEC_MEM_SIZE: 128,
ISPEC_CPU_COUNT: 1,
ISPEC_NIC_COUNT: MAX_NICS,
ISPEC_SPINDLE_USE: 12,
},
+ }
+IPOLICY_DEFAULTS = {
+ ISPECS_MINMAX: ISPECS_MINMAX_DEFAULTS,
ISPECS_STD: {
ISPEC_MEM_SIZE: 128,
ISPEC_CPU_COUNT: 1,
return ret_dict
-def FillIPolicy(default_ipolicy, custom_ipolicy, skip_keys=None):
+def _FillMinMaxISpecs(default_specs, custom_specs):
+ assert frozenset(default_specs.keys()) == constants.ISPECS_MINMAX_KEYS
+ ret_specs = {}
+ for key in constants.ISPECS_MINMAX_KEYS:
+ ret_specs[key] = FillDict(default_specs[key],
+ custom_specs.get(key, {}))
+ return ret_specs
+
+
+def FillIPolicy(default_ipolicy, custom_ipolicy):
"""Fills an instance policy with defaults.
"""
assert frozenset(default_ipolicy.keys()) == constants.IPOLICY_ALL_KEYS
ret_dict = {}
- for key in constants.IPOLICY_ISPECS:
- ret_dict[key] = FillDict(default_ipolicy[key],
- custom_ipolicy.get(key, {}),
- skip_keys=skip_keys)
+ # Instance specs
+ new_mm = _FillMinMaxISpecs(default_ipolicy[constants.ISPECS_MINMAX],
+ custom_ipolicy.get(constants.ISPECS_MINMAX, {}))
+ ret_dict[constants.ISPECS_MINMAX] = new_mm
+ new_std = FillDict(default_ipolicy[constants.ISPECS_STD],
+ custom_ipolicy.get(constants.ISPECS_STD, {}))
+ ret_dict[constants.ISPECS_STD] = new_std
# list items
for key in [constants.IPOLICY_DTS]:
ret_dict[key] = list(custom_ipolicy.get(key, default_ipolicy[key]))
"""Create empty IPolicy dictionary.
"""
- return dict([
- (constants.ISPECS_MIN, {}),
- (constants.ISPECS_MAX, {}),
- (constants.ISPECS_STD, {}),
- ])
+ return {
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MIN: {},
+ constants.ISPECS_MAX: {},
+ },
+ constants.ISPECS_STD: {},
+ }
class ConfigObject(outils.ValidatedSlots):
class InstancePolicy(ConfigObject):
"""Config object representing instance policy limits dictionary.
-
Note that this object is not actually used in the config, it's just
used as a placeholder for a few functions.
def CheckParameterSyntax(cls, ipolicy, check_std):
""" Check the instance policy for validity.
+ @type ipolicy: dict
+ @param ipolicy: dictionary with min/max/std specs and policies
+ @type check_std: bool
+ @param check_std: Whether to check std value or just assume compliance
+ @raise errors.ConfigurationError: when the policy is not legal
+
"""
- for param in constants.ISPECS_PARAMETERS:
- InstancePolicy.CheckISpecSyntax(ipolicy, param, check_std)
+ if constants.ISPECS_MINMAX in ipolicy:
+ if check_std and constants.ISPECS_STD not in ipolicy:
+ msg = "Missing key in ipolicy: %s" % constants.ISPECS_STD
+ raise errors.ConfigurationError(msg)
+ minmaxspecs = ipolicy[constants.ISPECS_MINMAX]
+ stdspec = ipolicy.get(constants.ISPECS_STD)
+ for param in constants.ISPECS_PARAMETERS:
+ InstancePolicy.CheckISpecSyntax(minmaxspecs, stdspec, param, check_std)
if constants.IPOLICY_DTS in ipolicy:
InstancePolicy.CheckDiskTemplates(ipolicy[constants.IPOLICY_DTS])
for key in constants.IPOLICY_PARAMETERS:
utils.CommaJoin(wrong_keys))
@classmethod
- def CheckISpecSyntax(cls, ipolicy, name, check_std):
- """Check the instance policy for validity on a given key.
+ def CheckISpecSyntax(cls, minmaxspecs, stdspec, name, check_std):
+ """Check the instance policy specs for validity on a given key.
- We check if the instance policy makes sense for a given key, that is
- if ipolicy[min][name] <= ipolicy[std][name] <= ipolicy[max][name].
+ We check if the instance specs makes sense for a given key, that is
+ if minmaxspecs[min][name] <= stdspec[name] <= minmaxspec[max][name].
- @type ipolicy: dict
- @param ipolicy: dictionary with min, max, std specs
+ @type minmaxspecs: dict
+ @param minmaxspecs: dictionary with min and max instance spec
+ @type stdspec: dict
+ @param stdspec: dictionary with standard instance spec
@type name: string
@param name: what are the limits for
@type check_std: bool
@param check_std: Whether to check std value or just assume compliance
- @raise errors.ConfigureError: when specs for given name are not valid
+ @raise errors.ConfigurationError: when specs for the given name are not
+ valid
"""
- min_v = ipolicy[constants.ISPECS_MIN].get(name, 0)
+ missing = constants.ISPECS_MINMAX_KEYS - frozenset(minmaxspecs.keys())
+ if missing:
+ msg = "Missing instance specification: %s" % utils.CommaJoin(missing)
+ raise errors.ConfigurationError(msg)
+
+ minspec = minmaxspecs[constants.ISPECS_MIN]
+ maxspec = minmaxspecs[constants.ISPECS_MAX]
+ min_v = minspec.get(name, 0)
if check_std:
- std_v = ipolicy[constants.ISPECS_STD].get(name, min_v)
+ std_v = stdspec.get(name, min_v)
std_msg = std_v
else:
std_v = min_v
std_msg = "-"
- max_v = ipolicy[constants.ISPECS_MAX].get(name, std_v)
- err = ("Invalid specification of min/max/std values for %s: %s/%s/%s" %
- (name,
- ipolicy[constants.ISPECS_MIN].get(name, "-"),
- ipolicy[constants.ISPECS_MAX].get(name, "-"),
- std_msg))
+ max_v = maxspec.get(name, std_v)
if min_v > std_v or std_v > max_v:
+ err = ("Invalid specification of min/max/std values for %s: %s/%s/%s" %
+ (name,
+ minspec.get(name, "-"),
+ maxspec.get(name, "-"),
+ std_msg))
raise errors.ConfigurationError(err)
@classmethod
policy = info["Instance policy - limits for instances"]
ret_specs = {}
ret_policy = {}
+ ispec_keys = constants.ISPECS_MINMAX_KEYS | frozenset([constants.ISPECS_STD])
for (key, val) in policy.items():
- if key in constants.IPOLICY_ISPECS:
+ if key in ispec_keys:
for (par, pval) in val.items():
if par == "memory-size":
par = "mem-size"
{-
-Copyright (C) 2009, 2010, 2011, 2012 Google Inc.
+Copyright (C) 2009, 2010, 2011, 2012, 2013 Google Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
-- | Generate policy data from a given policy object.
serializeIPolicy :: String -> IPolicy -> String
serializeIPolicy owner ipol =
- let IPolicy stdspec minspec maxspec dts vcpu_ratio spindle_ratio = ipol
+ let IPolicy minmax stdspec dts vcpu_ratio spindle_ratio = ipol
+ MinMaxISpecs minspec maxspec = minmax
strings = [ owner
, serializeISpec stdspec
, serializeISpec minspec
xvcpu_ratio <- tryRead (owner ++ "/vcpu_ratio") vcpu_ratio
xspindle_ratio <- tryRead (owner ++ "/spindle_ratio") spindle_ratio
return (owner,
- IPolicy xstdspec xminspec xmaxspec xdts xvcpu_ratio xspindle_ratio)
+ IPolicy (MinMaxISpecs xminspec xmaxspec) xstdspec
+ xdts xvcpu_ratio xspindle_ratio)
loadIPolicy s = fail $ "Invalid ipolicy data: '" ++ show s ++ "'"
loadOnePolicy :: (IPolicy, Group.List) -> String
{-
-Copyright (C) 2009, 2010, 2011, 2012 Google Inc.
+Copyright (C) 2009, 2010, 2011, 2012, 2013 Google Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
-- | Checks if an instance matches a policy.
instMatchesPolicy :: Instance -> T.IPolicy -> T.OpResult ()
instMatchesPolicy inst ipol = do
- instAboveISpec inst (T.iPolicyMinSpec ipol)
- instBelowISpec inst (T.iPolicyMaxSpec ipol)
+ let minmax = T.iPolicyMinMaxISpecs ipol
+ instAboveISpec inst (T.minMaxISpecsMinSpec minmax)
+ instBelowISpec inst (T.minMaxISpecsMaxSpec minmax)
if diskTemplate inst `elem` T.iPolicyDiskTemplates ipol
then Ok ()
else Bad T.FailDisk
-- Run the tiered allocation
- let tspec = fromMaybe (rspecFromISpec (iPolicyMaxSpec ipol))
+ let minmax = iPolicyMinMaxISpecs ipol
+ let tspec = fromMaybe (rspecFromISpec (minMaxISpecsMaxSpec minmax))
(optTieredSpec opts)
(treason, trl_nl, _, spec_map) <-
{-
-Copyright (C) 2009, 2010, 2011, 2012 Google Inc.
+Copyright (C) 2009, 2010, 2011, 2012, 2013 Google Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
, opToResult
, EvacMode(..)
, ISpec(..)
+ , MinMaxISpecs(..)
, IPolicy(..)
, defIPolicy
, rspecFromISpec
-- | The default minimum ispec.
defMinISpec :: ISpec
-defMinISpec = ISpec { iSpecMemorySize = C.ipolicyDefaultsMinMemorySize
- , iSpecCpuCount = C.ipolicyDefaultsMinCpuCount
- , iSpecDiskSize = C.ipolicyDefaultsMinDiskSize
- , iSpecDiskCount = C.ipolicyDefaultsMinDiskCount
- , iSpecNicCount = C.ipolicyDefaultsMinNicCount
- , iSpecSpindleUse = C.ipolicyDefaultsMinSpindleUse
+defMinISpec = ISpec { iSpecMemorySize = C.ipolicyDefaultsMinmaxMinMemorySize
+ , iSpecCpuCount = C.ipolicyDefaultsMinmaxMinCpuCount
+ , iSpecDiskSize = C.ipolicyDefaultsMinmaxMinDiskSize
+ , iSpecDiskCount = C.ipolicyDefaultsMinmaxMinDiskCount
+ , iSpecNicCount = C.ipolicyDefaultsMinmaxMinNicCount
+ , iSpecSpindleUse = C.ipolicyDefaultsMinmaxMinSpindleUse
}
-- | The default standard ispec.
-- | The default max ispec.
defMaxISpec :: ISpec
-defMaxISpec = ISpec { iSpecMemorySize = C.ipolicyDefaultsMaxMemorySize
- , iSpecCpuCount = C.ipolicyDefaultsMaxCpuCount
- , iSpecDiskSize = C.ipolicyDefaultsMaxDiskSize
- , iSpecDiskCount = C.ipolicyDefaultsMaxDiskCount
- , iSpecNicCount = C.ipolicyDefaultsMaxNicCount
- , iSpecSpindleUse = C.ipolicyDefaultsMaxSpindleUse
+defMaxISpec = ISpec { iSpecMemorySize = C.ipolicyDefaultsMinmaxMaxMemorySize
+ , iSpecCpuCount = C.ipolicyDefaultsMinmaxMaxCpuCount
+ , iSpecDiskSize = C.ipolicyDefaultsMinmaxMaxDiskSize
+ , iSpecDiskCount = C.ipolicyDefaultsMinmaxMaxDiskCount
+ , iSpecNicCount = C.ipolicyDefaultsMinmaxMaxNicCount
+ , iSpecSpindleUse = C.ipolicyDefaultsMinmaxMaxSpindleUse
}
+-- | Minimum and maximum instance specs type.
+$(THH.buildObject "MinMaxISpecs" "minMaxISpecs"
+ [ THH.renameField "MinSpec" $ THH.simpleField "min" [t| ISpec |]
+ , THH.renameField "MaxSpec" $ THH.simpleField "max" [t| ISpec |]
+ ])
+
+-- | Defult minimum and maximum instance specs.
+defMinMaxISpecs :: MinMaxISpecs
+defMinMaxISpecs = MinMaxISpecs { minMaxISpecsMinSpec = defMinISpec
+ , minMaxISpecsMaxSpec = defMaxISpec
+ }
+
-- | Instance policy type.
$(THH.buildObject "IPolicy" "iPolicy"
- [ THH.renameField "StdSpec" $ THH.simpleField C.ispecsStd [t| ISpec |]
- , THH.renameField "MinSpec" $ THH.simpleField C.ispecsMin [t| ISpec |]
- , THH.renameField "MaxSpec" $ THH.simpleField C.ispecsMax [t| ISpec |]
+ [ THH.renameField "MinMaxISpecs" $
+ THH.simpleField C.ispecsMinmax [t| MinMaxISpecs |]
+ , THH.renameField "StdSpec" $ THH.simpleField C.ispecsStd [t| ISpec |]
, THH.renameField "DiskTemplates" $
THH.simpleField C.ipolicyDts [t| [DiskTemplate] |]
, THH.renameField "VcpuRatio" $
-- | The default instance policy.
defIPolicy :: IPolicy
-defIPolicy = IPolicy { iPolicyStdSpec = defStdISpec
- , iPolicyMinSpec = defMinISpec
- , iPolicyMaxSpec = defMaxISpec
+defIPolicy = IPolicy { iPolicyMinMaxISpecs = defMinMaxISpecs
+ , iPolicyStdSpec = defStdISpec
-- hardcoding here since Constants.hs exports the
-- string values, not the actual type; and in
-- htools, we are mostly looking at DRBD
, PartialISpecParams(..)
, fillISpecParams
, allISpecParamFields
+ , FilledMinMaxISpecs(..)
+ , PartialMinMaxISpecs(..)
+ , fillMinMaxISpecs
, FilledIPolicy(..)
, PartialIPolicy(..)
, fillIPolicy
, simpleField C.ispecSpindleUse [t| Int |]
])
+-- | Partial min-max instance specs. These is not built via buildParam since
+-- it has a special 2-level inheritance mode.
+$(buildObject "PartialMinMaxISpecs" "mmis"
+ [ renameField "MinSpecP" $ simpleField "min" [t| PartialISpecParams |]
+ , renameField "MaxSpecP" $ simpleField "max" [t| PartialISpecParams |]
+ ])
+
+-- | Filled min-max instance specs. This is not built via buildParam since
+-- it has a special 2-level inheritance mode.
+$(buildObject "FilledMinMaxISpecs" "mmis"
+ [ renameField "MinSpec" $ simpleField "min" [t| FilledISpecParams |]
+ , renameField "MaxSpec" $ simpleField "max" [t| FilledISpecParams |]
+ ])
+
-- | Custom partial ipolicy. This is not built via buildParam since it
-- has a special 2-level inheritance mode.
$(buildObject "PartialIPolicy" "ipolicy"
- [ renameField "MinSpecP" $ simpleField "min" [t| PartialISpecParams |]
- , renameField "MaxSpecP" $ simpleField "max" [t| PartialISpecParams |]
+ [ optionalField . renameField "MinMaxISpecsP"
+ $ simpleField C.ispecsMinmax [t| PartialMinMaxISpecs |]
, renameField "StdSpecP" $ simpleField "std" [t| PartialISpecParams |]
, optionalField . renameField "SpindleRatioP"
$ simpleField "spindle-ratio" [t| Double |]
-- | Custom filled ipolicy. This is not built via buildParam since it
-- has a special 2-level inheritance mode.
$(buildObject "FilledIPolicy" "ipolicy"
- [ renameField "MinSpec" $ simpleField "min" [t| FilledISpecParams |]
- , renameField "MaxSpec" $ simpleField "max" [t| FilledISpecParams |]
+ [ renameField "MinMaxISpecs"
+ $ simpleField C.ispecsMinmax [t| FilledMinMaxISpecs |]
, renameField "StdSpec" $ simpleField "std" [t| FilledISpecParams |]
, simpleField "spindle-ratio" [t| Double |]
, simpleField "vcpu-ratio" [t| Double |]
, simpleField "disk-templates" [t| [DiskTemplate] |]
])
+-- | Custom filler for the min-max instance specs.
+fillMinMaxISpecs :: FilledMinMaxISpecs -> Maybe PartialMinMaxISpecs ->
+ FilledMinMaxISpecs
+fillMinMaxISpecs fminmax Nothing = fminmax
+fillMinMaxISpecs (FilledMinMaxISpecs { mmisMinSpec = fmin
+ , mmisMaxSpec = fmax })
+ (Just PartialMinMaxISpecs { mmisMinSpecP = pmin
+ , mmisMaxSpecP = pmax }) =
+ FilledMinMaxISpecs { mmisMinSpec = fillISpecParams fmin pmin
+ , mmisMaxSpec = fillISpecParams fmax pmax }
+
-- | Custom filler for the ipolicy types.
fillIPolicy :: FilledIPolicy -> PartialIPolicy -> FilledIPolicy
-fillIPolicy (FilledIPolicy { ipolicyMinSpec = fmin
- , ipolicyMaxSpec = fmax
+fillIPolicy (FilledIPolicy { ipolicyMinMaxISpecs = fminmax
, ipolicyStdSpec = fstd
, ipolicySpindleRatio = fspindleRatio
, ipolicyVcpuRatio = fvcpuRatio
, ipolicyDiskTemplates = fdiskTemplates})
- (PartialIPolicy { ipolicyMinSpecP = pmin
- , ipolicyMaxSpecP = pmax
+ (PartialIPolicy { ipolicyMinMaxISpecsP = pminmax
, ipolicyStdSpecP = pstd
, ipolicySpindleRatioP = pspindleRatio
, ipolicyVcpuRatioP = pvcpuRatio
, ipolicyDiskTemplatesP = pdiskTemplates}) =
- FilledIPolicy { ipolicyMinSpec = fillISpecParams fmin pmin
- , ipolicyMaxSpec = fillISpecParams fmax pmax
+ FilledIPolicy { ipolicyMinMaxISpecs = fillMinMaxISpecs fminmax pminmax
, ipolicyStdSpec = fillISpecParams fstd pstd
, ipolicySpindleRatio = fromMaybe fspindleRatio pspindleRatio
, ipolicyVcpuRatio = fromMaybe fvcpuRatio pvcpuRatio
"cpu-count": 1,
"spindle-use": 1
},
- "min": {
- "nic-count": 1,
- "disk-size": 128,
- "disk-count": 1,
- "memory-size": 128,
- "cpu-count": 1,
- "spindle-use": 1
- },
- "max": {
- "nic-count": 8,
- "disk-size": 1048576,
- "disk-count": 16,
- "memory-size": 32768,
- "cpu-count": 8,
- "spindle-use": 8
+ "minmax": {
+ "min": {
+ "nic-count": 1,
+ "disk-size": 128,
+ "disk-count": 1,
+ "memory-size": 128,
+ "cpu-count": 1,
+ "spindle-use": 1
+ },
+ "max": {
+ "nic-count": 8,
+ "disk-size": 1048576,
+ "disk-count": 16,
+ "memory-size": 32768,
+ "cpu-count": 8,
+ "spindle-use": 8
+ }
},
"vcpu-ratio": 4.0,
"disk-templates": [
"cpu-count": 1,
"spindle-use": 1
},
- "min": {
- "nic-count": 1,
- "disk-size": 128,
- "disk-count": 1,
- "memory-size": 128,
- "cpu-count": 1,
- "spindle-use": 1
- },
- "max": {
- "nic-count": 8,
- "disk-size": 1048576,
- "disk-count": 16,
- "memory-size": 32768,
- "cpu-count": 8,
- "spindle-use": 8
+ "minmax": {
+ "min": {
+ "nic-count": 1,
+ "disk-size": 128,
+ "disk-count": 1,
+ "memory-size": 128,
+ "cpu-count": 1,
+ "spindle-use": 1
+ },
+ "max": {
+ "nic-count": 8,
+ "disk-size": 1048576,
+ "disk-count": 16,
+ "memory-size": 32768,
+ "cpu-count": 8,
+ "spindle-use": 8
+ }
},
"vcpu-ratio": 4.0,
"disk-templates": [
"cpu-count": 1,
"spindle-use": 1
},
- "min": {
- "nic-count": 1,
- "disk-size": 128,
- "disk-count": 1,
- "memory-size": 128,
- "cpu-count": 1,
- "spindle-use": 1
- },
- "max": {
- "nic-count": 8,
- "disk-size": 1048576,
- "disk-count": 16,
- "memory-size": 32768,
- "cpu-count": 8,
- "spindle-use": 8
+ "minmax": {
+ "min": {
+ "nic-count": 1,
+ "disk-size": 128,
+ "disk-count": 1,
+ "memory-size": 128,
+ "cpu-count": 1,
+ "spindle-use": 1
+ },
+ "max": {
+ "nic-count": 8,
+ "disk-size": 1048576,
+ "disk-count": 16,
+ "memory-size": 32768,
+ "cpu-count": 8,
+ "spindle-use": 8
+ }
},
"vcpu-ratio": 4.0,
"disk-templates": [
"disk-count": 1,
"spindle-use": 1
},
- "min": {
- "nic-count": 1,
- "disk-size": 1024,
- "memory-size": 128,
- "cpu-count": 1,
- "disk-count": 1,
- "spindle-use": 1
- },
- "max": {
- "nic-count": 8,
- "disk-size": 1048576,
- "memory-size": 32768,
- "cpu-count": 8,
- "disk-count": 16,
- "spindle-use": 8
+ "minmax": {
+ "min": {
+ "nic-count": 1,
+ "disk-size": 1024,
+ "memory-size": 128,
+ "cpu-count": 1,
+ "disk-count": 1,
+ "spindle-use": 1
+ },
+ "max": {
+ "nic-count": 8,
+ "disk-size": 1048576,
+ "memory-size": 32768,
+ "cpu-count": 8,
+ "disk-count": 16,
+ "spindle-use": 8
+ }
},
"vcpu-ratio": 4.0,
"disk-templates": [
"cpu-count": 1,
"spindle-use": 1
},
- "min": {
- "nic-count": 1,
- "disk-size": 128,
- "disk-count": 1,
- "memory-size": 128,
- "cpu-count": 1,
- "spindle-use": 1
- },
- "max": {
- "nic-count": 8,
- "disk-size": 1048576,
- "disk-count": 16,
- "memory-size": 32768,
- "cpu-count": 8,
- "spindle-use": 8
+ "minmax": {
+ "min": {
+ "nic-count": 1,
+ "disk-size": 128,
+ "disk-count": 1,
+ "memory-size": 128,
+ "cpu-count": 1,
+ "spindle-use": 1
+ },
+ "max": {
+ "nic-count": 8,
+ "disk-size": 1048576,
+ "disk-count": 16,
+ "memory-size": 32768,
+ "cpu-count": 8,
+ "spindle-use": 8
+ }
},
"vcpu-ratio": 4.0,
"disk-templates": [
"cpu-count": 1,
"spindle-use": 1
},
- "min": {
- "nic-count": 1,
- "disk-size": 128,
- "disk-count": 1,
- "memory-size": 128,
- "cpu-count": 1,
- "spindle-use": 1
- },
- "max": {
- "nic-count": 8,
- "disk-size": 1048576,
- "disk-count": 16,
- "memory-size": 32768,
- "cpu-count": 8,
- "spindle-use": 8
+ "minmax": {
+ "min": {
+ "nic-count": 1,
+ "disk-size": 128,
+ "disk-count": 1,
+ "memory-size": 128,
+ "cpu-count": 1,
+ "spindle-use": 1
+ },
+ "max": {
+ "nic-count": 8,
+ "disk-size": 1048576,
+ "disk-count": 16,
+ "memory-size": 32768,
+ "cpu-count": 8,
+ "spindle-use": 8
+ }
},
"vcpu-ratio": 4.0,
"disk-templates": [
"disk-count": 1,
"spindle-use": 1
},
- "min": {
- "cpu-count": 1,
- "nic-count": 1,
- "disk-size": 1024,
- "memory-size": 128,
- "disk-count": 1,
- "spindle-use": 1
- },
- "max": {
- "cpu-count": 8,
- "nic-count": 8,
- "disk-size": 1048576,
- "memory-size": 32768,
- "disk-count": 16,
- "spindle-use": 8
+ "minmax": {
+ "min": {
+ "cpu-count": 1,
+ "nic-count": 1,
+ "disk-size": 1024,
+ "memory-size": 128,
+ "disk-count": 1,
+ "spindle-use": 1
+ },
+ "max": {
+ "cpu-count": 8,
+ "nic-count": 8,
+ "disk-size": 1048576,
+ "memory-size": 32768,
+ "disk-count": 16,
+ "spindle-use": 8
+ }
},
"vcpu-ratio": 4.0,
"disk-templates": [
"cpu-count": 1,
"spindle-use": 1
},
- "min": {
- "nic-count": 1,
- "disk-size": 128,
- "disk-count": 1,
- "memory-size": 128,
- "cpu-count": 1,
- "spindle-use": 1
- },
- "max": {
- "nic-count": 8,
- "disk-size": 1048576,
- "disk-count": 16,
- "memory-size": 32768,
- "cpu-count": 8,
- "spindle-use": 8
+ "minmax": {
+ "min": {
+ "nic-count": 1,
+ "disk-size": 128,
+ "disk-count": 1,
+ "memory-size": 128,
+ "cpu-count": 1,
+ "spindle-use": 1
+ },
+ "max": {
+ "nic-count": 8,
+ "disk-size": 1048576,
+ "disk-count": 16,
+ "memory-size": 32768,
+ "cpu-count": 8,
+ "spindle-use": 8
+ }
},
"vcpu-ratio": 4.0,
"disk-templates": [
dts <- genUniquesList num_tmpl arbitrary
vcpu_ratio <- choose (1.0, maxVcpuRatio)
spindle_ratio <- choose (1.0, maxSpindleRatio)
- return Types.IPolicy { Types.iPolicyMinSpec = imin
+ return Types.IPolicy { Types.iPolicyMinMaxISpecs = Types.MinMaxISpecs
+ { Types.minMaxISpecsMinSpec = imin
+ , Types.minMaxISpecsMaxSpec = imax
+ }
, Types.iPolicyStdSpec = istd
- , Types.iPolicyMaxSpec = imax
, Types.iPolicyDiskTemplates = dts
, Types.iPolicyVcpuRatio = vcpu_ratio
, Types.iPolicySpindleRatio = spindle_ratio
-- | FIXME: This generates completely random data, without normal
-- validation rules.
$(genArbitrary ''PartialISpecParams)
+$(genArbitrary ''PartialMinMaxISpecs)
-- | FIXME: This generates completely random data, without normal
-- validation rules.
$(genArbitrary ''PartialIPolicy)
$(genArbitrary ''FilledISpecParams)
+$(genArbitrary ''FilledMinMaxISpecs)
$(genArbitrary ''FilledIPolicy)
$(genArbitrary ''IpFamily)
$(genArbitrary ''FilledNDParams)
-- | Null iPolicy, and by null we mean very liberal.
nullIPolicy :: Types.IPolicy
nullIPolicy = Types.IPolicy
- { Types.iPolicyMinSpec = Types.ISpec { Types.iSpecMemorySize = 0
- , Types.iSpecCpuCount = 0
- , Types.iSpecDiskSize = 0
- , Types.iSpecDiskCount = 0
- , Types.iSpecNicCount = 0
- , Types.iSpecSpindleUse = 0
- }
- , Types.iPolicyMaxSpec = Types.ISpec { Types.iSpecMemorySize = maxBound
- , Types.iSpecCpuCount = maxBound
- , Types.iSpecDiskSize = maxBound
- , Types.iSpecDiskCount = C.maxDisks
- , Types.iSpecNicCount = C.maxNics
- , Types.iSpecSpindleUse = maxBound
- }
+ { Types.iPolicyMinMaxISpecs = Types.MinMaxISpecs
+ { Types.minMaxISpecsMinSpec = Types.ISpec { Types.iSpecMemorySize = 0
+ , Types.iSpecCpuCount = 0
+ , Types.iSpecDiskSize = 0
+ , Types.iSpecDiskCount = 0
+ , Types.iSpecNicCount = 0
+ , Types.iSpecSpindleUse = 0
+ }
+ , Types.minMaxISpecsMaxSpec = Types.ISpec
+ { Types.iSpecMemorySize = maxBound
+ , Types.iSpecCpuCount = maxBound
+ , Types.iSpecDiskSize = maxBound
+ , Types.iSpecDiskCount = C.maxDisks
+ , Types.iSpecNicCount = C.maxNics
+ , Types.iSpecSpindleUse = maxBound
+ }
+ }
, Types.iPolicyStdSpec = Types.ISpec { Types.iSpecMemorySize = Types.unitMem
, Types.iSpecCpuCount = Types.unitCpu
, Types.iSpecDiskSize = Types.unitDsk
def testClusterPolicy(self):
exp_pol0 = {
- constants.ISPECS_MIN: {},
- constants.ISPECS_MAX: {},
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MIN: {},
+ constants.ISPECS_MAX: {},
+ },
constants.ISPECS_STD: {},
}
exp_pol1 = {
- constants.ISPECS_MIN: {
- constants.ISPEC_CPU_COUNT: 2,
- constants.ISPEC_DISK_COUNT: 1,
- },
- constants.ISPECS_MAX: {
- constants.ISPEC_MEM_SIZE: 12*1024,
- constants.ISPEC_DISK_COUNT: 2,
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MIN: {
+ constants.ISPEC_CPU_COUNT: 2,
+ constants.ISPEC_DISK_COUNT: 1,
+ },
+ constants.ISPECS_MAX: {
+ constants.ISPEC_MEM_SIZE: 12*1024,
+ constants.ISPEC_DISK_COUNT: 2,
+ },
},
constants.ISPECS_STD: {
constants.ISPEC_CPU_COUNT: 2,
constants.IPOLICY_VCPU_RATIO: 3.1,
}
exp_pol2 = {
- constants.ISPECS_MIN: {
- constants.ISPEC_DISK_SIZE: 512,
- constants.ISPEC_NIC_COUNT: 2,
- },
- constants.ISPECS_MAX: {
- constants.ISPEC_NIC_COUNT: 3,
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MIN: {
+ constants.ISPEC_DISK_SIZE: 512,
+ constants.ISPEC_NIC_COUNT: 2,
+ },
+ constants.ISPECS_MAX: {
+ constants.ISPEC_NIC_COUNT: 3,
+ },
},
constants.ISPECS_STD: {
constants.ISPEC_CPU_COUNT: 2,
def testAllowedValues(self):
allowedv = "blah"
exp_pol1 = {
- constants.ISPECS_MIN: {
- constants.ISPEC_CPU_COUNT: allowedv,
- },
- constants.ISPECS_MAX: {
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MIN: {
+ constants.ISPEC_CPU_COUNT: allowedv,
+ },
+ constants.ISPECS_MAX: {
+ },
},
constants.ISPECS_STD: {
},
#!/usr/bin/python
#
-# Copyright (C) 2008, 2011, 2012 Google Inc.
+# Copyright (C) 2008, 2011, 2012, 2013 Google Inc.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
class TestComputeMinMaxSpec(unittest.TestCase):
def setUp(self):
- self.ipolicy = {
+ self.ispecs = {
constants.ISPECS_MAX: {
constants.ISPEC_MEM_SIZE: 512,
constants.ISPEC_DISK_SIZE: 1024,
def testNoneValue(self):
self.assertTrue(cmdlib._ComputeMinMaxSpec(constants.ISPEC_MEM_SIZE, None,
- self.ipolicy, None) is None)
+ self.ispecs, None) is None)
def testAutoValue(self):
self.assertTrue(cmdlib._ComputeMinMaxSpec(constants.ISPEC_MEM_SIZE, None,
- self.ipolicy,
+ self.ispecs,
constants.VALUE_AUTO) is None)
def testNotDefined(self):
self.assertTrue(cmdlib._ComputeMinMaxSpec(constants.ISPEC_NIC_COUNT, None,
- self.ipolicy, 3) is None)
+ self.ispecs, 3) is None)
def testNoMinDefined(self):
self.assertTrue(cmdlib._ComputeMinMaxSpec(constants.ISPEC_DISK_SIZE, None,
- self.ipolicy, 128) is None)
+ self.ispecs, 128) is None)
def testNoMaxDefined(self):
self.assertTrue(cmdlib._ComputeMinMaxSpec(constants.ISPEC_DISK_COUNT, None,
- self.ipolicy, 16) is None)
+ self.ispecs, 16) is None)
def testOutOfRange(self):
for (name, val) in ((constants.ISPEC_MEM_SIZE, 64),
(constants.ISPEC_MEM_SIZE, 768),
(constants.ISPEC_DISK_SIZE, 4096),
(constants.ISPEC_DISK_COUNT, 0)):
- min_v = self.ipolicy[constants.ISPECS_MIN].get(name, val)
- max_v = self.ipolicy[constants.ISPECS_MAX].get(name, val)
+ min_v = self.ispecs[constants.ISPECS_MIN].get(name, val)
+ max_v = self.ispecs[constants.ISPECS_MAX].get(name, val)
self.assertEqual(cmdlib._ComputeMinMaxSpec(name, None,
- self.ipolicy, val),
+ self.ispecs, val),
"%s value %s is not in range [%s, %s]" %
(name, val,min_v, max_v))
self.assertEqual(cmdlib._ComputeMinMaxSpec(name, "1",
- self.ipolicy, val),
+ self.ispecs, val),
"%s/1 value %s is not in range [%s, %s]" %
(name, val,min_v, max_v))
(constants.ISPEC_DISK_SIZE, 0),
(constants.ISPEC_DISK_COUNT, 1),
(constants.ISPEC_DISK_COUNT, 5)):
- self.assertTrue(cmdlib._ComputeMinMaxSpec(name, None, self.ipolicy, val)
+ self.assertTrue(cmdlib._ComputeMinMaxSpec(name, None, self.ispecs, val)
is None)
# Minimal policy accepted by _ComputeIPolicySpecViolation()
_MICRO_IPOL = {
constants.IPOLICY_DTS: [constants.DT_PLAIN, constants.DT_DISKLESS],
+ constants.ISPECS_MINMAX: NotImplemented,
}
def test(self):
"""Tests for cmdlib._GetUpdatedIPolicy()"""
_OLD_CLUSTER_POLICY = {
constants.IPOLICY_VCPU_RATIO: 1.5,
- constants.ISPECS_MIN: {
- constants.ISPEC_MEM_SIZE: 20,
- constants.ISPEC_CPU_COUNT: 2,
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MIN: {
+ constants.ISPEC_MEM_SIZE: 20,
+ constants.ISPEC_CPU_COUNT: 2,
+ },
+ constants.ISPECS_MAX: {},
},
- constants.ISPECS_MAX: {},
constants.ISPECS_STD: {},
}
-
_OLD_GROUP_POLICY = {
constants.IPOLICY_SPINDLE_RATIO: 2.5,
- constants.ISPECS_MIN: {
- constants.ISPEC_DISK_SIZE: 20,
- constants.ISPEC_NIC_COUNT: 2,
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MIN: {
+ constants.ISPEC_DISK_SIZE: 20,
+ constants.ISPEC_NIC_COUNT: 2,
+ },
+ constants.ISPECS_MAX: {},
},
- constants.ISPECS_MAX: {},
}
def _TestSetSpecs(self, old_policy, isgroup):
constants.ISPEC_DISK_SIZE: 30,
}
diff_policy = {
- ispec_key: diff_ispec
+ constants.ISPECS_MINMAX: {
+ ispec_key: diff_ispec,
+ },
}
+ if not isgroup:
+ diff_std = {
+ constants.ISPEC_CPU_COUNT: 3,
+ constants.ISPEC_DISK_COUNT: 3,
+ }
+ diff_policy[constants.ISPECS_STD] = diff_std
new_policy = cmdlib._GetUpdatedIPolicy(old_policy, diff_policy,
group_policy=isgroup)
- new_ispec = new_policy[ispec_key]
+
+ self.assertTrue(constants.ISPECS_MINMAX in new_policy)
+ new_ispec = new_policy[constants.ISPECS_MINMAX][ispec_key]
for key in diff_ispec:
self.assertTrue(key in new_ispec)
self.assertEqual(new_ispec[key], diff_ispec[key])
if not key in diff_policy:
self.assertTrue(key in new_policy)
self.assertEqual(new_policy[key], old_policy[key])
- old_ispec = old_policy[ispec_key]
- for key in old_ispec:
- if not key in diff_ispec:
- self.assertTrue(key in new_ispec)
- self.assertEqual(new_ispec[key], old_ispec[key])
+
+ if constants.ISPECS_MINMAX in old_policy:
+ old_minmax = old_policy[constants.ISPECS_MINMAX]
+ for key in old_minmax:
+ if key != ispec_key:
+ self.assertTrue(key in new_policy[constants.ISPECS_MINMAX])
+ self.assertEqual(new_policy[constants.ISPECS_MINMAX][key],
+ old_minmax[key])
+ old_ispec = old_policy[constants.ISPECS_MINMAX][ispec_key]
+ for key in old_ispec:
+ if not key in diff_ispec:
+ self.assertTrue(key in new_ispec)
+ self.assertEqual(new_ispec[key], old_ispec[key])
+
+ if not isgroup:
+ new_std = new_policy[constants.ISPECS_STD]
+ for key in diff_std:
+ self.assertTrue(key in new_std)
+ self.assertEqual(new_std[key], diff_std[key])
+
def _TestSet(self, old_policy, isgroup):
diff_policy = {
invalid_policy = INVALID_DICT
self.assertRaises(errors.OpPrereqError, cmdlib._GetUpdatedIPolicy,
old_policy, invalid_policy, group_policy=isgroup)
- for key in constants.IPOLICY_ISPECS:
+ invalid_ispecs = {
+ constants.ISPECS_MINMAX: INVALID_DICT,
+ }
+ self.assertRaises(errors.OpPrereqError, cmdlib._GetUpdatedIPolicy,
+ old_policy, invalid_ispecs, group_policy=isgroup)
+ for key in constants.ISPECS_MINMAX_KEYS:
invalid_ispec = {
- key: INVALID_DICT,
+ constants.ISPECS_MINMAX: {
+ key: INVALID_DICT,
+ },
}
self.assertRaises(errors.TypeEnforcementError, cmdlib._GetUpdatedIPolicy,
old_policy, invalid_ispec, group_policy=isgroup)
#!/usr/bin/python
#
-# Copyright (C) 2006, 2007, 2008, 2010, 2012 Google Inc.
+# Copyright (C) 2006, 2007, 2008, 2010, 2012, 2013 Google Inc.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
def _AssertIPolicyIsFull(self, policy):
self.assertEqual(frozenset(policy.keys()), constants.IPOLICY_ALL_KEYS)
- for key in constants.IPOLICY_ISPECS:
- spec = policy[key]
- self.assertEqual(frozenset(spec.keys()), constants.ISPECS_PARAMETERS)
+ minmax = policy[constants.ISPECS_MINMAX]
+ self.assertEqual(frozenset(minmax.keys()), constants.ISPECS_MINMAX_KEYS)
+ for key in constants.ISPECS_MINMAX_KEYS:
+ self.assertEqual(frozenset(minmax[key].keys()),
+ constants.ISPECS_PARAMETERS)
+ self.assertEqual(frozenset(policy[constants.ISPECS_STD].keys()),
+ constants.ISPECS_PARAMETERS)
def testDefaultIPolicy(self):
objects.InstancePolicy.CheckParameterSyntax(constants.IPOLICY_DEFAULTS,
def testCheckISpecSyntax(self):
par = "my_parameter"
for check_std in [True, False]:
- if check_std:
- allkeys = constants.IPOLICY_ISPECS
- else:
- allkeys = constants.IPOLICY_ISPECS - frozenset([constants.ISPECS_STD])
# Only one policy limit
- for key in allkeys:
- policy = dict((k, {}) for k in allkeys)
- policy[key][par] = 11
- objects.InstancePolicy.CheckISpecSyntax(policy, par, check_std)
+ for key in constants.ISPECS_MINMAX_KEYS:
+ minmax = dict((k, {}) for k in constants.ISPECS_MINMAX_KEYS)
+ minmax[key][par] = 11
+ objects.InstancePolicy.CheckISpecSyntax(minmax, {}, par, check_std)
+ if check_std:
+ minmax = dict((k, {}) for k in constants.ISPECS_MINMAX_KEYS)
+ stdspec = {par: 11}
+ objects.InstancePolicy.CheckISpecSyntax(minmax, stdspec, par, check_std)
+
# Min and max only
good_values = [(11, 11), (11, 40), (0, 0)]
for (mn, mx) in good_values:
- policy = dict((k, {}) for k in allkeys)
- policy[constants.ISPECS_MIN][par] = mn
- policy[constants.ISPECS_MAX][par] = mx
- objects.InstancePolicy.CheckISpecSyntax(policy, par, check_std)
- policy = dict((k, {}) for k in allkeys)
- policy[constants.ISPECS_MIN][par] = 11
- policy[constants.ISPECS_MAX][par] = 5
+ minmax = dict((k, {}) for k in constants.ISPECS_MINMAX_KEYS)
+ minmax[constants.ISPECS_MIN][par] = mn
+ minmax[constants.ISPECS_MAX][par] = mx
+ objects.InstancePolicy.CheckISpecSyntax(minmax, {}, par, check_std)
+ minmax = dict((k, {}) for k in constants.ISPECS_MINMAX_KEYS)
+ minmax[constants.ISPECS_MIN][par] = 11
+ minmax[constants.ISPECS_MAX][par] = 5
self.assertRaises(errors.ConfigurationError,
objects.InstancePolicy.CheckISpecSyntax,
- policy, par, check_std)
+ minmax, {}, par, check_std)
# Min, std, max
good_values = [
(11, 11, 11),
(11, 40, 40),
]
for (mn, st, mx) in good_values:
- policy = {
+ minmax = {
constants.ISPECS_MIN: {par: mn},
- constants.ISPECS_STD: {par: st},
constants.ISPECS_MAX: {par: mx},
}
- objects.InstancePolicy.CheckISpecSyntax(policy, par, True)
+ stdspec = {par: st}
+ objects.InstancePolicy.CheckISpecSyntax(minmax, stdspec, par, True)
bad_values = [
(11, 11, 5),
(40, 11, 11),
(40, 40, 11),
]
for (mn, st, mx) in bad_values:
- policy = {
+ minmax = {
constants.ISPECS_MIN: {par: mn},
- constants.ISPECS_STD: {par: st},
constants.ISPECS_MAX: {par: mx},
}
+ stdspec = {par: st}
self.assertRaises(errors.ConfigurationError,
objects.InstancePolicy.CheckISpecSyntax,
- policy, par, True)
+ minmax, stdspec, par, True)
def testCheckDiskTemplates(self):
invalid = "this_is_not_a_good_template"
def testCheckParameterSyntax(self):
invalid = "this_key_shouldnt_be_here"
for check_std in [True, False]:
- self.assertRaises(KeyError,
- objects.InstancePolicy.CheckParameterSyntax,
- {}, check_std)
- policy = objects.MakeEmptyIPolicy()
- policy[invalid] = None
+ objects.InstancePolicy.CheckParameterSyntax({}, check_std)
+ policy = {invalid: None}
self.assertRaises(errors.ConfigurationError,
objects.InstancePolicy.CheckParameterSyntax,
policy, check_std)
for par in constants.IPOLICY_PARAMETERS:
- policy = objects.MakeEmptyIPolicy()
for val in ("blah", None, {}, [42]):
- policy[par] = val
+ policy = {par: val}
self.assertRaises(errors.ConfigurationError,
objects.InstancePolicy.CheckParameterSyntax,
policy, check_std)
def _AssertIPolicyMerged(self, default_pol, diff_pol, merged_pol):
for (key, value) in merged_pol.items():
if key in diff_pol:
- if key in constants.IPOLICY_ISPECS:
+ if key == constants.ISPECS_MINMAX:
+ self.assertEqual(frozenset(value), constants.ISPECS_MINMAX_KEYS)
+ for k in constants.ISPECS_MINMAX_KEYS:
+ self._AssertISpecsMerged(default_pol[key][k], diff_pol[key][k],
+ value[k])
+ elif key == constants.ISPECS_STD:
self._AssertISpecsMerged(default_pol[key], diff_pol[key], value)
else:
self.assertEqual(value, diff_pol[key])
self._AssertIPolicyMerged(constants.IPOLICY_DEFAULTS, diff_pol, policy)
def testFillIPolicySpecs(self):
- partial_policies = [
- {constants.ISPECS_MIN: {constants.ISPEC_MEM_SIZE: 32},
- constants.ISPECS_MAX: {constants.ISPEC_CPU_COUNT: 1024}},
- {constants.ISPECS_STD: {constants.ISPEC_DISK_SIZE: 2048},
- constants.ISPECS_MAX: {
- constants.ISPEC_DISK_COUNT: constants.MAX_DISKS - 1,
- constants.ISPEC_NIC_COUNT: constants.MAX_NICS - 1,
- }},
- {constants.ISPECS_STD: {constants.ISPEC_SPINDLE_USE: 3}},
+ partial_ipolicies = [
+ {
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MIN: {constants.ISPEC_MEM_SIZE: 32},
+ constants.ISPECS_MAX: {constants.ISPEC_CPU_COUNT: 1024}
+ },
+ },
+ {
+ constants.ISPECS_MINMAX: {
+ constants.ISPECS_MAX: {
+ constants.ISPEC_DISK_COUNT: constants.MAX_DISKS - 1,
+ constants.ISPEC_NIC_COUNT: constants.MAX_NICS - 1,
+ },
+ constants.ISPECS_MIN: {},
+ },
+ constants.ISPECS_STD: {constants.ISPEC_DISK_SIZE: 2048},
+ },
+ {
+ constants.ISPECS_STD: {constants.ISPEC_SPINDLE_USE: 3},
+ },
]
- for diff_pol in partial_policies:
+ for diff_pol in partial_ipolicies:
policy = objects.FillIPolicy(constants.IPOLICY_DEFAULTS, diff_pol)
objects.InstancePolicy.CheckParameterSyntax(policy, True)
self._AssertIPolicyIsFull(policy)