Support returning multiple flag descriptions when restrict is used.
authorMichał Górny <gentoo@mgorny.alt.pl>
Fri, 27 Aug 2010 16:47:22 +0000 (18:47 +0200)
committerZac Medico <zmedico@gentoo.org>
Fri, 27 Aug 2010 16:57:58 +0000 (09:57 -0700)
Return a dict of dicts in parse_metadata_use(), with second-level keys
being the restrict strings (or None when no restrict). When generating
use.local.desc, use the description from the possibly-highest-matching
atom.

bin/egencache
pym/repoman/utilities.py

index 64e60925b8525ef6bc867e5fe5c3541bed435921..1b3f98f34f8bf404e8e84a9f466dacc2917e921e 100755 (executable)
@@ -44,6 +44,8 @@ except ImportError:
 else:
        from repoman.utilities import parse_metadata_use
        from xml.parsers.expat import ExpatError
+       from portage.dep import Atom
+       from portage.versions import pkgcmp, pkgsplit
 
 if sys.hexversion >= 0x3000000:
        long = int
@@ -356,7 +358,32 @@ class GenUseLocalDesc(object):
                                        self.returncode |= 1
                                else:
                                        for flag in sorted(usedict.keys()):
-                                               output.write('%s:%s - %s\n' % (cp, flag, usedict[flag]))
+                                               def atomcmp(atoma, atomb):
+                                                       # None is better than an atom, that's why we reverse the args
+                                                       if atoma is None or atomb is None:
+                                                               return cmp(atomb, atoma)
+                                                       # Same for plain PNs (.operator is None then)
+                                                       elif atoma.operator is None or atomb.operator is None:
+                                                               return cmp(atomb.operator, atoma.operator)
+                                                       # Version matching
+                                                       elif atoma.cpv != atomb.cpv:
+                                                               return pkgcmp(pkgsplit(atoma.cpv), pkgsplit(atomb.cpv))
+                                                       # Versions match, let's fallback to operator matching
+                                                       else:
+                                                               ops = ('<', '<=', '=', '>=', '>')
+                                                               return cmp(ops.index(atoma.operator), ops.index(atomb.operator))
+
+                                               def _Atom(key):
+                                                       if key is not None:
+                                                               return Atom(key)
+                                                       return None
+
+                                               resdict = usedict[flag]
+                                               reskeys = {_Atom(k): k for k in resdict.keys()}
+                                               resatoms = sorted(reskeys.keys(), atomcmp)
+                                               resdesc = resdict[reskeys[resatoms[-1]]]
+
+                                               output.write('%s:%s - %s\n' % (cp, flag, resdesc))
 
                output.close()
 
index 3df437a01043ca66556086e81dd629ac75cbda67..a6c24d862701eb13ec842581882b054cda319609 100644 (file)
@@ -135,13 +135,7 @@ def parse_metadata_use(xml_tree):
                        pkg_flag = flag.get("name")
                        if pkg_flag is None:
                                raise exception.ParseError("missing 'name' attribute for 'flag' tag")
-
-                       if uselist.get(pkg_flag):
-                               # It's possible to have multiple elements with the same
-                               # flag name, but different 'restrict' attributes that
-                               # specify version restrictions. We use only the first
-                               # occurance.
-                               continue
+                       flag_restrict = flag.get("restrict")
 
                        # emulate the Element.itertext() method from python-2.7
                        inner_text = []
@@ -158,7 +152,11 @@ def parse_metadata_use(xml_tree):
                                        stack.append(obj.tail)
                                stack.extend(reversed(obj))
 
-                       uselist[pkg_flag] = " ".join("".join(inner_text).split())
+                       if pkg_flag not in uselist:
+                               uselist[pkg_flag] = {}
+
+                       # (flag_restrict can be None)
+                       uselist[pkg_flag][flag_restrict] = " ".join("".join(inner_text).split())
 
        return uselist