Merge "Move QuotaInformation to driver utils"
This commit is contained in:
commit
8983deb296
|
@ -22,12 +22,9 @@ from kazoo import exceptions as kze
|
|||
from nodepool import exceptions
|
||||
from nodepool import nodeutils as utils
|
||||
from nodepool import zk
|
||||
from nodepool.driver.utils import NodeLauncher
|
||||
from nodepool.driver.utils import NodeLauncher, QuotaInformation
|
||||
from nodepool.driver import NodeRequestHandler
|
||||
|
||||
# Import entire module to avoid partial-loading, circular import
|
||||
from nodepool.driver.openstack import provider
|
||||
|
||||
|
||||
class OpenStackNodeLauncher(NodeLauncher):
|
||||
def __init__(self, handler, node, provider_config, provider_label):
|
||||
|
@ -303,10 +300,10 @@ class OpenStackNodeRequestHandler(NodeRequestHandler):
|
|||
|
||||
# Now calculate pool specific quota. Values indicating no quota default
|
||||
# to math.inf representing infinity that can be calculated with.
|
||||
pool_quota = provider.QuotaInformation(cores=self.pool.max_cores,
|
||||
instances=self.pool.max_servers,
|
||||
ram=self.pool.max_ram,
|
||||
default=math.inf)
|
||||
pool_quota = QuotaInformation(cores=self.pool.max_cores,
|
||||
instances=self.pool.max_servers,
|
||||
ram=self.pool.max_ram,
|
||||
default=math.inf)
|
||||
pool_quota.subtract(
|
||||
self.manager.estimatedNodepoolQuotaUsed(self.zk, self.pool))
|
||||
pool_quota.subtract(needed_quota)
|
||||
|
@ -315,7 +312,7 @@ class OpenStackNodeRequestHandler(NodeRequestHandler):
|
|||
return pool_quota.non_negative()
|
||||
|
||||
def hasProviderQuota(self, node_types):
|
||||
needed_quota = provider.QuotaInformation()
|
||||
needed_quota = QuotaInformation()
|
||||
|
||||
for ntype in node_types:
|
||||
needed_quota.add(
|
||||
|
@ -329,10 +326,10 @@ class OpenStackNodeRequestHandler(NodeRequestHandler):
|
|||
|
||||
# Now calculate pool specific quota. Values indicating no quota default
|
||||
# to math.inf representing infinity that can be calculated with.
|
||||
pool_quota = provider.QuotaInformation(cores=self.pool.max_cores,
|
||||
instances=self.pool.max_servers,
|
||||
ram=self.pool.max_ram,
|
||||
default=math.inf)
|
||||
pool_quota = QuotaInformation(cores=self.pool.max_cores,
|
||||
instances=self.pool.max_servers,
|
||||
ram=self.pool.max_ram,
|
||||
default=math.inf)
|
||||
pool_quota.subtract(needed_quota)
|
||||
return pool_quota.non_negative()
|
||||
|
||||
|
|
|
@ -16,7 +16,6 @@
|
|||
|
||||
import copy
|
||||
import logging
|
||||
import math
|
||||
import operator
|
||||
import time
|
||||
|
||||
|
@ -24,6 +23,7 @@ import shade
|
|||
|
||||
from nodepool import exceptions
|
||||
from nodepool.driver import Provider
|
||||
from nodepool.driver.utils import QuotaInformation
|
||||
from nodepool.nodeutils import iterate_timeout
|
||||
from nodepool.task_manager import ManagerStoppedException
|
||||
from nodepool.task_manager import TaskManager
|
||||
|
@ -37,74 +37,6 @@ IPS_LIST_AGE = 5 # How long to keep a cached copy of the ip list
|
|||
MAX_QUOTA_AGE = 5 * 60 # How long to keep the quota information cached
|
||||
|
||||
|
||||
class QuotaInformation:
|
||||
|
||||
def __init__(self, cores=None, instances=None, ram=None, default=0):
|
||||
'''
|
||||
Initializes the quota information with some values. None values will
|
||||
be initialized with default which will be typically 0 or math.inf
|
||||
indicating an infinite limit.
|
||||
|
||||
:param cores:
|
||||
:param instances:
|
||||
:param ram:
|
||||
:param default:
|
||||
'''
|
||||
self.quota = {
|
||||
'compute': {
|
||||
'cores': self._get_default(cores, default),
|
||||
'instances': self._get_default(instances, default),
|
||||
'ram': self._get_default(ram, default),
|
||||
}
|
||||
}
|
||||
|
||||
@staticmethod
|
||||
def construct_from_flavor(flavor):
|
||||
return QuotaInformation(instances=1,
|
||||
cores=flavor.vcpus,
|
||||
ram=flavor.ram)
|
||||
|
||||
@staticmethod
|
||||
def construct_from_limits(limits):
|
||||
def bound_value(value):
|
||||
if value == -1:
|
||||
return math.inf
|
||||
return value
|
||||
|
||||
return QuotaInformation(
|
||||
instances=bound_value(limits.max_total_instances),
|
||||
cores=bound_value(limits.max_total_cores),
|
||||
ram=bound_value(limits.max_total_ram_size))
|
||||
|
||||
def _get_default(self, value, default):
|
||||
return value if value is not None else default
|
||||
|
||||
def _add_subtract(self, other, add=True):
|
||||
for category in self.quota.keys():
|
||||
for resource in self.quota[category].keys():
|
||||
second_value = other.quota.get(category, {}).get(resource, 0)
|
||||
if add:
|
||||
self.quota[category][resource] += second_value
|
||||
else:
|
||||
self.quota[category][resource] -= second_value
|
||||
|
||||
def subtract(self, other):
|
||||
self._add_subtract(other, add=False)
|
||||
|
||||
def add(self, other):
|
||||
self._add_subtract(other, True)
|
||||
|
||||
def non_negative(self):
|
||||
for key_i, category in self.quota.items():
|
||||
for resource, value in category.items():
|
||||
if value < 0:
|
||||
return False
|
||||
return True
|
||||
|
||||
def __str__(self):
|
||||
return str(self.quota)
|
||||
|
||||
|
||||
class OpenStackProvider(Provider):
|
||||
log = logging.getLogger("nodepool.driver.openstack.OpenStackProvider")
|
||||
|
||||
|
|
|
@ -16,6 +16,7 @@
|
|||
|
||||
import abc
|
||||
import logging
|
||||
import math
|
||||
import threading
|
||||
import time
|
||||
|
||||
|
@ -84,3 +85,71 @@ class NodeLauncher(threading.Thread,
|
|||
self.updateNodeStats(self.zk, self.provider_config)
|
||||
except Exception:
|
||||
self.log.exception("Exception while reporting stats:")
|
||||
|
||||
|
||||
class QuotaInformation:
|
||||
|
||||
def __init__(self, cores=None, instances=None, ram=None, default=0):
|
||||
'''
|
||||
Initializes the quota information with some values. None values will
|
||||
be initialized with default which will be typically 0 or math.inf
|
||||
indicating an infinite limit.
|
||||
|
||||
:param cores:
|
||||
:param instances:
|
||||
:param ram:
|
||||
:param default:
|
||||
'''
|
||||
self.quota = {
|
||||
'compute': {
|
||||
'cores': self._get_default(cores, default),
|
||||
'instances': self._get_default(instances, default),
|
||||
'ram': self._get_default(ram, default),
|
||||
}
|
||||
}
|
||||
|
||||
@staticmethod
|
||||
def construct_from_flavor(flavor):
|
||||
return QuotaInformation(instances=1,
|
||||
cores=flavor.vcpus,
|
||||
ram=flavor.ram)
|
||||
|
||||
@staticmethod
|
||||
def construct_from_limits(limits):
|
||||
def bound_value(value):
|
||||
if value == -1:
|
||||
return math.inf
|
||||
return value
|
||||
|
||||
return QuotaInformation(
|
||||
instances=bound_value(limits.max_total_instances),
|
||||
cores=bound_value(limits.max_total_cores),
|
||||
ram=bound_value(limits.max_total_ram_size))
|
||||
|
||||
def _get_default(self, value, default):
|
||||
return value if value is not None else default
|
||||
|
||||
def _add_subtract(self, other, add=True):
|
||||
for category in self.quota.keys():
|
||||
for resource in self.quota[category].keys():
|
||||
second_value = other.quota.get(category, {}).get(resource, 0)
|
||||
if add:
|
||||
self.quota[category][resource] += second_value
|
||||
else:
|
||||
self.quota[category][resource] -= second_value
|
||||
|
||||
def subtract(self, other):
|
||||
self._add_subtract(other, add=False)
|
||||
|
||||
def add(self, other):
|
||||
self._add_subtract(other, True)
|
||||
|
||||
def non_negative(self):
|
||||
for key_i, category in self.quota.items():
|
||||
for resource, value in category.items():
|
||||
if value < 0:
|
||||
return False
|
||||
return True
|
||||
|
||||
def __str__(self):
|
||||
return str(self.quota)
|
||||
|
|
Loading…
Reference in New Issue