Skip to content

Commit d1b036f

Browse files
Zuulopenstack-gerrit
authored andcommitted
Merge "Follow up for unified limits"
2 parents 3d9d328 + 5505b6f commit d1b036f

File tree

5 files changed

+55
-13
lines changed

5 files changed

+55
-13
lines changed

mypy-files.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
nova/compute/manager.py
22
nova/crypto.py
33
nova/limit/local.py
4+
nova/limit/placement.py
45
nova/network/neutron.py
56
nova/pci
67
nova/privsep/path.py

nova/limit/local.py

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@
2020
from oslo_log import log as logging
2121

2222
import nova.conf
23-
from nova import context as nova_context
2423
from nova import exception
2524
from nova.limit import utils as nova_limit_utils
2625
from nova import objects
@@ -80,7 +79,9 @@
8079
}
8180

8281

83-
def get_in_use(context, project_id):
82+
def get_in_use(
83+
context: 'nova.context.RequestContext', project_id: str
84+
) -> ty.Dict[str, int]:
8485
"""Returns in use counts for each resource, for given project.
8586
8687
This sounds simple but many resources can't be counted per project,
@@ -144,7 +145,7 @@ def enforce_api_limit(entity_type: str, count: int) -> None:
144145

145146

146147
def enforce_db_limit(
147-
context: nova_context.RequestContext,
148+
context: 'nova.context.RequestContext',
148149
entity_type: str,
149150
entity_scope: ty.Any,
150151
delta: int
@@ -192,15 +193,17 @@ def enforce_db_limit(
192193
raise EXCEPTIONS.get(entity_type, exception.OverQuota)(str(e))
193194

194195

195-
def _convert_keys_to_legacy_name(new_dict):
196+
def _convert_keys_to_legacy_name(
197+
new_dict: ty.Dict[str, int]
198+
) -> ty.Dict[str, int]:
196199
legacy = {}
197200
for new_name, old_name in LEGACY_LIMITS.items():
198201
# defensive incase oslo or keystone doesn't give us an answer
199202
legacy[old_name] = new_dict.get(new_name) or 0
200203
return legacy
201204

202205

203-
def get_legacy_default_limits():
206+
def get_legacy_default_limits() -> ty.Dict[str, int]:
204207
# TODO(johngarbutt): need oslo.limit API for this, it should do caching
205208
enforcer = limit.Enforcer(lambda: None)
206209
new_limits = enforcer.get_registered_limits(LEGACY_LIMITS.keys())

nova/limit/placement.py

Lines changed: 25 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
# License for the specific language governing permissions and limitations
1313
# under the License.
1414

15+
import typing as ty
1516

1617
import os_resource_classes as orc
1718
from oslo_limit import exception as limit_exceptions
@@ -39,17 +40,23 @@
3940
}
4041

4142

42-
def _get_placement_usages(context, project_id):
43+
def _get_placement_usages(
44+
context: 'nova.context.RequestContext', project_id: str
45+
) -> ty.Dict[str, int]:
4346
global PLACEMENT_CLIENT
4447
if not PLACEMENT_CLIENT:
4548
PLACEMENT_CLIENT = report.SchedulerReportClient()
4649
return PLACEMENT_CLIENT.get_usages_counts_for_limits(context, project_id)
4750

4851

49-
def _get_usage(context, project_id, resource_names):
52+
def _get_usage(
53+
context: 'nova.context.RequestContext',
54+
project_id: str,
55+
resource_names: ty.List[str],
56+
) -> ty.Dict[str, int]:
5057
"""Called by oslo_limit's enforcer"""
5158
if not limit_utils.use_unified_limits():
52-
raise NotImplementedError("unified limits is disabled")
59+
raise NotImplementedError("Unified limits support is disabled")
5360

5461
count_servers = False
5562
resource_classes = []
@@ -113,7 +120,9 @@ def _get_usage(context, project_id, resource_names):
113120
return resource_counts
114121

115122

116-
def _get_deltas_by_flavor(flavor, is_bfv, count):
123+
def _get_deltas_by_flavor(
124+
flavor: 'objects.Flavor', is_bfv: bool, count: int
125+
) -> ty.Dict[str, int]:
117126
if flavor is None:
118127
raise ValueError("flavor")
119128
if count < 0:
@@ -132,16 +141,25 @@ def _get_deltas_by_flavor(flavor, is_bfv, count):
132141
return deltas
133142

134143

135-
def _get_enforcer(context, project_id):
144+
def _get_enforcer(
145+
context: 'nova.context.RequestContext', project_id: str
146+
) -> limit.Enforcer:
136147
# NOTE(johngarbutt) should we move context arg into oslo.limit?
137148
def callback(project_id, resource_names):
138149
return _get_usage(context, project_id, resource_names)
139150

140151
return limit.Enforcer(callback)
141152

142153

143-
def enforce_num_instances_and_flavor(context, project_id, flavor, is_bfvm,
144-
min_count, max_count, enforcer=None):
154+
def enforce_num_instances_and_flavor(
155+
context: 'nova.context.RequestContext',
156+
project_id: str,
157+
flavor: 'objects.Flavor',
158+
is_bfvm: bool,
159+
min_count: int,
160+
max_count: int,
161+
enforcer: ty.Optional[limit.Enforcer] = None
162+
) -> int:
145163
"""Return max instances possible, else raise TooManyInstances exception."""
146164
if not limit_utils.use_unified_limits():
147165
return max_count

nova/quota.py

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1243,6 +1243,26 @@ def _server_group_count_members_by_user_legacy(context, group, user_id):
12431243

12441244

12451245
def is_qfd_populated(context):
1246+
"""Check if user_id and queued_for_delete fields are populated.
1247+
1248+
This method is related to counting quota usage from placement. It is not
1249+
yet possible to count instances from placement, so in the meantime we can
1250+
use instance mappings for counting. This method is used to determine
1251+
whether the user_id and queued_for_delete columns are populated in the API
1252+
database's instance_mappings table. Instance mapping records are not
1253+
deleted from the database until the database is archived, so
1254+
queued_for_delete tells us whether or not we should count them for instance
1255+
quota usage. The user_id field enables us to scope instance quota usage to
1256+
a user (legacy quota).
1257+
1258+
Scoping instance quota to a user is only possible
1259+
when counting quota usage from placement is configured and unified limits
1260+
is not configured. When unified limits is configured, quotas are scoped
1261+
only to projects.
1262+
1263+
In the future when it is possible to count instance usage from placement,
1264+
this method will no longer be needed.
1265+
"""
12461266
global UID_QFD_POPULATED_CACHE_ALL
12471267
if not UID_QFD_POPULATED_CACHE_ALL:
12481268
LOG.debug('Checking whether user_id and queued_for_delete are '

nova/tests/unit/limit/test_placement.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@ def test_get_usage_unified_limits_disabled(self):
7979
self.flags(driver="nova.quota.NoopQuotaDriver", group="quota")
8080
e = self.assertRaises(NotImplementedError, placement_limits._get_usage,
8181
self.context, uuids.project, [])
82-
self.assertEqual("unified limits is disabled", str(e))
82+
self.assertEqual("Unified limits support is disabled", str(e))
8383

8484
@mock.patch.object(quota, "is_qfd_populated")
8585
@mock.patch.object(objects.InstanceMappingList, "get_counts")

0 commit comments

Comments
 (0)