Browse Source

Merge "Perf: Use dicts for ProviderTree roots" into stable/rocky

tags/18.2.2
Zuul 1 month ago
parent
commit
afd7a5a681
1 changed files with 23 additions and 4 deletions
  1. 23
    4
      nova/compute/provider_tree.py

+ 23
- 4
nova/compute/provider_tree.py View File

@@ -25,6 +25,7 @@ import os_traits
25 25
 from oslo_concurrency import lockutils
26 26
 from oslo_log import log as logging
27 27
 from oslo_utils import uuidutils
28
+import six
28 29
 
29 30
 from nova.i18n import _
30 31
 
@@ -226,7 +227,12 @@ class ProviderTree(object):
226 227
     def __init__(self):
227 228
         """Create an empty provider tree."""
228 229
         self.lock = lockutils.internal_lock(_LOCK_NAME)
229
-        self.roots = []
230
+        self.roots_by_uuid = {}
231
+        self.roots_by_name = {}
232
+
233
+    @property
234
+    def roots(self):
235
+        return six.itervalues(self.roots_by_uuid)
230 236
 
231 237
     def get_provider_uuids(self, name_or_uuid=None):
232 238
         """Return a list, in top-down traversable order, of the UUIDs of all
@@ -325,7 +331,8 @@ class ProviderTree(object):
325 331
 
326 332
                 provider = _Provider.from_dict(pd)
327 333
                 if parent_uuid is None:
328
-                    self.roots.append(provider)
334
+                    self.roots_by_uuid[provider.uuid] = provider
335
+                    self.roots_by_name[provider.name] = provider
329 336
                 else:
330 337
                     parent = self._find_with_lock(parent_uuid)
331 338
                     parent.add_child(provider)
@@ -339,7 +346,8 @@ class ProviderTree(object):
339 346
             parent = self._find_with_lock(found.parent_uuid)
340 347
             parent.remove_child(found)
341 348
         else:
342
-            self.roots.remove(found)
349
+            del self.roots_by_uuid[found.uuid]
350
+            del self.roots_by_name[found.name]
343 351
 
344 352
     def remove(self, name_or_uuid):
345 353
         """Safely removes the provider identified by the supplied name_or_uuid
@@ -375,10 +383,21 @@ class ProviderTree(object):
375 383
                 raise ValueError(err % uuid)
376 384
 
377 385
             p = _Provider(name, uuid=uuid, generation=generation)
378
-            self.roots.append(p)
386
+            self.roots_by_uuid[uuid] = p
387
+            self.roots_by_name[name] = p
379 388
             return p.uuid
380 389
 
381 390
     def _find_with_lock(self, name_or_uuid):
391
+        # Optimization for large number of roots (e.g. ironic): if name_or_uuid
392
+        # represents a root, this is O(1).
393
+        found = self.roots_by_uuid.get(name_or_uuid)
394
+        if found:
395
+            return found
396
+        found = self.roots_by_name.get(name_or_uuid)
397
+        if found:
398
+            return found
399
+
400
+        # Okay, it's a child; do it the hard way.
382 401
         for root in self.roots:
383 402
             found = root.find(name_or_uuid)
384 403
             if found:

Loading…
Cancel
Save