Create a generic portage_util.LazyItemsDict and use it for lazy initialization portag...
authorZac Medico <zmedico@gentoo.org>
Wed, 12 Apr 2006 02:46:21 +0000 (02:46 -0000)
committerZac Medico <zmedico@gentoo.org>
Wed, 12 Apr 2006 02:46:21 +0000 (02:46 -0000)
svn path=/main/trunk/; revision=3133

pym/portage.py
pym/portage_util.py

index e986b4c92f6165c0bb1851fa2a06f48a187eefca..11877a861ffca538cd25e11fcf3d6736de1c2a21 100644 (file)
@@ -6472,28 +6472,23 @@ def getvirtuals(myroot):
        return settings.getvirtuals(myroot)
 
 def do_vartree(mysettings):
-       class LazyVirtualsDict(dict):
+       class LazyVirtualsItem(object):
                def __init__(self, myroot):
-                       super(LazyVirtualsDict, self).__init__()
-                       self.myroot = myroot
-                       self["virtuals"] = None
-               def __getitem__(self, key):
-                       if "virtuals" == key:
-                               if "virtuals" in self:
-                                       virtuals = super(LazyVirtualsDict, self).__getitem__("virtuals")
-                                       if virtuals is not None:
-                                               return virtuals
-                                       else:
-                                               global settings
-                                               virtuals = settings.getvirtuals(self.myroot)
-                                               self["virtuals"] = virtuals
-                                               return virtuals
-                       return super(LazyVirtualsDict, self).__getitem__(key)
+                       self._myroot = myroot
+                       self._virtuals = None
+               def __call__(self):
+                       if self._virtuals is None:
+                               global settings
+                               self._virtuals = settings.getvirtuals(self._myroot)
+                       return self._virtuals
+
        global db, root
-       db["/"] = LazyVirtualsDict("/")
+       db["/"] = portage_util.LazyItemsDict()
+       db["/"].addLazyItem("virtuals", LazyVirtualsItem("/"))
        db["/"]["vartree"] = vartree("/")
        if root!="/":
-               db[root] = LazyVirtualsDict(root)
+               db[root] = portage_util.LazyItemsDict()
+               db[root].addLazyItem("virtuals", LazyVirtualsItem(root))
                db[root]["vartree"] = vartree(root)
        #We need to create the vartree first, then load our settings, and then set up our other trees
 
@@ -6807,35 +6802,25 @@ if (secpass==2) and (not os.environ.has_key("SANDBOX_ACTIVE")):
                global_updates()
 
 #continue setting up other trees
-class LazyDatabasesDict(dict):
-       """This class implements lazy construction of the global databases
-       db[root]["porttree"] and db[root]["bintree"]."""
-       def __init__(self, myroot, items):
-               dict.__init__(self)
-               self.update(items)
-               self.myroot = myroot
-               self.lazy_keys = ("porttree", "bintree")
-               for x in self.lazy_keys:
-                       self[x] = None
-       def __getitem__(self, item_key):
-               if item_key in self.lazy_keys and item_key in self:
-                       myvalue = dict.__getitem__(self, item_key)
-                       if myvalue is None:
-                               if "porttree" == item_key:
-                                       myvalue = portagetree(self.myroot)
-                               elif "bintree" == item_key:
-                                       global settings
-                                       myvalue = binarytree(self.myroot, settings["PKGDIR"])
-                                       # The binarytree likely needs to be populated now, so we
-                                       # do it now to make sure that all method calls are safe.
-                                       myvalue.populate()
-                               self[item_key] = myvalue
-                       return myvalue
-               return dict.__getitem__(self, item_key)
-
-db["/"] = LazyDatabasesDict("/", db["/"])
+class LazyBintreeItem(object):
+       """This class implements lazy construction of db[root]["bintree"]."""
+       def __init__(self, myroot):
+               self._myroot = myroot
+               self._bintree = None
+       def __call__(self):
+               if self._bintree is None:
+                       global settings
+                       self._bintree = binarytree(self._myroot, settings["PKGDIR"])
+                       # The binarytree likely needs to be populated now, so we
+                       # do it now to make sure that all method calls are safe.
+                       self._bintree.populate()
+               return self._bintree
+
+db["/"]["porttree"] = portagetree("/")
+db["/"].addLazyItem("bintree", LazyBintreeItem("/"))
 if root!="/":
-       db[root] = LazyDatabasesDict(root, db[root])
+       db[root]["porttree"] = portagetree(root)
+       db[root].addLazyItem("bintree", LazyBintreeItem(root))
 
 profileroots = [settings["PORTDIR"]+"/profiles/"]
 for x in settings["PORTDIR_OVERLAY"].split():
index 46a7d10529da725f47e229ee6f73ffc9850307e9..6fd76090c21b35e9abc307bdd40e02151b1c1e83 100644 (file)
@@ -710,3 +710,30 @@ def ensure_dirs(dir_path, *args, **kwargs):
                        raise
        perms_modified = apply_permissions(dir_path, *args, **kwargs)
        return created_dir or perms_modified
+
+class LazyItemsDict(dict):
+       """A mapping object that behaves like a standard dict except that it allows
+       for lazy initialization of values via callable objects.  Lazy items can be
+       overwritten and deleted just as normal items."""
+       def __init__(self):
+               dict.__init__(self)
+               self.lazy_items = {}
+       def addLazyItem(self, item_key, value_callable):
+               """Add a lazy item for the given key.  When the item is requested,
+               value_callable will be called with no arguments."""
+               self.lazy_items[item_key] = value_callable
+               # make it show up in self.keys(), etc...
+               dict.__setitem__(self, item_key, None)
+       def __getitem__(self, item_key):
+               if item_key in self.lazy_items:
+                       return self.lazy_items[item_key]()
+               else:
+                       return dict.__getitem__(self, item_key)
+       def __setitem__(self, item_key, value):
+               if item_key in self.lazy_items:
+                       del self.lazy_items[item_key]
+               dict.__setitem__(self, item_key, value)
+       def __delitem__(self, item_key):
+               if item_key in self.lazy_items:
+                       del self.lazy_items[item_key]
+               dict.__delitem__(self, item_key)