# HG changeset patch # User BenoƮt Allard # Date 1413298102 -7200 # Node ID 90852c11fabd6c0b2addc042607bc864c8ebd7d8 # Parent 858d8c0b49e25b79eeb651d027529376bad7056f Add methods to extract Product references in a document. diff -r 858d8c0b49e2 -r 90852c11fabd CHANGES --- a/CHANGES Tue Oct 14 16:47:01 2014 +0200 +++ b/CHANGES Tue Oct 14 16:48:22 2014 +0200 @@ -10,6 +10,7 @@ * Allow writing of incomplete CVRF documents. * Allow parsing of incomplete CVRF documents. * Add a method to extract a document ID. +* Add methods to extract Product references in a Document. * Add method to get a Vulnerability Note per ordinal. * Fix issue where Acknowledgment could only have one Name and Organization. * Complete the CVRF template with missing elements diff -r 858d8c0b49e2 -r 90852c11fabd farolluz/cvrf.py --- a/farolluz/cvrf.py Tue Oct 14 16:47:01 2014 +0200 +++ b/farolluz/cvrf.py Tue Oct 14 16:48:22 2014 +0200 @@ -673,6 +673,40 @@ return note return None + def mentionsProdId(self, productid): + """ Returns in which sub element, self is mentioning the productid """ + for category in (self._productstatuses, self._threats, self._cvsss, self._remediations): + for subelem in category: + if productid in subelem._productids: + yield subelem + + def isMentioningProdId(self, productid): + """ Returns if self is mentioning the productid """ + for e in self.mentionsProdId(productid): + # We only need to know if the generator yield at least one elem. + return True + return False + + def mentionsGroupId(self, groupid): + for category in (self._threats, self._remediations): + for subelem in category: + if groupid in subelem._groupids: + yield subelem + + def isMentioningGroupId(self, groupids): + """ Make sure you call this with a list (not a generator or a tuple) + when wished """ + if not isinstance(groupids, list): + groupids = [groupids] + for groupid in groupids: + print "testing GroupId: ", groupid + for _ in self.mentionsGroupId(groupid): + # We only need to know if the generator yield at least one elem. + print 'True' + return True + print 'False' + return False + def validate(self, productids, groupids): if not self._ordinal: raise ValidationError('A Vulnerability must have an ordinal') @@ -714,7 +748,6 @@ acknowledgment.validate() - class CVRFInvolvement(object): PARTIES = CVRFPublisher.TYPES STATUSES = ('Open', 'Disputed', 'In Progress', 'Completed', @@ -756,6 +789,7 @@ class CVRFProductStatus(object): TYPES = ('First Affected', 'Known Affected', 'Known Not Affected', 'First Fixed', 'Fixed', 'Recommended', 'Last Affected') + NAME = "Product Status" def __init__(self, _type): self._type = _type self._productids = [] @@ -780,6 +814,7 @@ class CVRFThreat(object): TYPES = ('Impact', 'Exploit Status', 'Target Set') + NAME = "Threat" def __init__(self, _type, description): self._type = _type self._description = description @@ -822,6 +857,7 @@ 'C': {'N':0.0, 'P':0.275, 'C':0.66}, 'I': {'N':0.0, 'P':0.275, 'C':0.66}, 'A': {'N':0.0, 'P':0.275, 'C':0.66}} + NAME = "CVSS Score Set" def __init__(self, basescore): self._basescore = basescore self._temporalscore = None @@ -874,6 +910,7 @@ class CVRFRemediation(object): TYPES = ('Workaround', 'Mitigation', 'Vendor Fix', 'None Available', 'Will Not Fix') + NAME = "Remediation" def __init__(self, _type, description): self._type = _type self._description = description @@ -1002,6 +1039,27 @@ products.add(productid) return set(self.getProductForID(p) for p in products) + def isProductOrphan(self, productid): + """ Returns if a productid is mentionned nowhere in the document """ + # We first look at the ProductTree + ptree = self._producttree + for relation in ptree._relationships: + if productid == relation._productreference: + return False + if productid == relation._relatestoproductreference: + return False + groupids = [g._groupid for g in ptree._groups if productid in g._productids] + if len(groupids) > 0: + return False + # Go through all the Vulnerabilities + for vulnerability in self._vulnerabilities: + if vulnerability.isMentioningProdId(productid): + return False + for groupid in groupids: + if vulnerability.isMentioningGroupId(groupid): + return False + return True + def getNote(self, ordinal): for note in self._notes: if note._ordinal == ordinal: