]> git.decadent.org.uk Git - dak.git/blobdiff - daklib/dbconn.py
give get_queue_build more flexibility
[dak.git] / daklib / dbconn.py
index 7d460760b9102c82a97341b3faac34a423e9c57d..43c0b6985e7ebf723423cce58f6a1c59d353bfe3 100755 (executable)
@@ -59,6 +59,18 @@ class Architecture(object):
     def __init__(self, *args, **kwargs):
         pass
 
+    def __eq__(self, val):
+        if isinstance(val, str):
+            return (self.arch_string== val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
+    def __ne__(self, val):
+        if isinstance(val, str):
+            return (self.arch_string != val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
     def __repr__(self):
         return '<Architecture %s>' % self.arch_string
 
@@ -315,6 +327,18 @@ class Component(object):
     def __init__(self, *args, **kwargs):
         pass
 
+    def __eq__(self, val):
+        if isinstance(val, str):
+            return (self.component_name == val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
+    def __ne__(self, val):
+        if isinstance(val, str):
+            return (self.component_name != val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
     def __repr__(self):
         return '<Component %s>' % self.component_name
 
@@ -579,6 +603,41 @@ class DSCFile(object):
 
 __all__.append('DSCFile')
 
+def get_dscfiles(dscfile_id=None, source_id=None, poolfile_id=None, session=None):
+    """
+    Returns a list of DSCFiles which may be empty
+
+    @type dscfile_id: int (optional)
+    @param dscfile_id: the dscfile_id of the DSCFiles to find
+
+    @type source_id: int (optional)
+    @param source_id: the source id related to the DSCFiles to find
+
+    @type poolfile_id: int (optional)
+    @param poolfile_id: the poolfile id related to the DSCFiles to find
+
+    @rtype: list
+    @return: Possibly empty list of DSCFiles
+    """
+
+    if session is None:
+        session = DBConn().session()
+
+    q = session.query(DSCFile)
+
+    if dscfile_id is not None:
+        q = q.filter_by(dscfile_id=dscfile_id)
+
+    if source_id is not None:
+        q = q.filter_by(source_id=source_id)
+
+    if poolfile_id is not None:
+        q = q.filter_by(poolfile_id=poolfile_id)
+
+    return q.all()
+
+__all__.append('get_dscfiles')
+
 ################################################################################
 
 class PoolFile(object):
@@ -590,6 +649,76 @@ class PoolFile(object):
 
 __all__.append('PoolFile')
 
+def check_poolfile(filename, filesize, md5sum, location_id, session=None):
+    """
+    Returns a tuple:
+     (ValidFileFound [boolean or None], PoolFile object or None)
+
+    @type filename: string
+    @param filename: the filename of the file to check against the DB
+
+    @type filesize: int
+    @param filesize: the size of the file to check against the DB
+
+    @type md5sum: string
+    @param md5sum: the md5sum of the file to check against the DB
+
+    @type location_id: int
+    @param location_id: the id of the location to look in
+
+    @rtype: tuple
+    @return: Tuple of length 2.
+             If more than one file found with that name:
+                    (None,  None)
+             If valid pool file found: (True, PoolFile object)
+             If valid pool file not found:
+                    (False, None) if no file found
+                    (False, PoolFile object) if file found with size/md5sum mismatch
+    """
+
+    if session is None:
+        session = DBConn().session()
+
+    q = session.query(PoolFile).filter_by(filename=filename)
+    q = q.join(Location).filter_by(location_id=location_id)
+
+    if q.count() > 1:
+        return (None, None)
+    if q.count() < 1:
+        return (False, None)
+
+    obj = q.one()
+    if obj.md5sum != md5sum or obj.filesize != filesize:
+        return (False, obj)
+
+    return (True, obj)
+
+__all__.append('check_poolfile')
+
+def get_poolfile_by_id(file_id, session=None):
+    """
+    Returns a PoolFile objects or None for the given id
+
+    @type file_id: int
+    @param file_id: the id of the file to look for
+
+    @rtype: PoolFile or None
+    @return: either the PoolFile object or None
+    """
+
+    if session is None:
+        session = DBConn().session()
+
+    q = session.query(PoolFile).filter_by(file_id=file_id)
+
+    if q.count() > 0:
+        return q.one()
+
+    return None
+
+__all__.append('get_poolfile_by_id')
+
+
 def get_poolfile_by_name(filename, location_id=None, session=None):
     """
     Returns an array of PoolFile objects for the given filename and
@@ -605,7 +734,7 @@ def get_poolfile_by_name(filename, location_id=None, session=None):
     @return: array of PoolFile objects
     """
 
-    if session is not None:
+    if session is None:
         session = DBConn().session()
 
     q = session.query(PoolFile).filter_by(filename=filename)
@@ -628,7 +757,7 @@ def get_poolfile_like_name(filename, session=None):
     @return: array of PoolFile objects
     """
 
-    if session is not None:
+    if session is None:
         session = DBConn().session()
 
     # TODO: There must be a way of properly using bind parameters with %FOO%
@@ -649,6 +778,49 @@ class Fingerprint(object):
 
 __all__.append('Fingerprint')
 
+def get_or_set_fingerprint(fpr, session=None):
+    """
+    Returns Fingerprint object for given fpr.
+
+    If no matching fpr is found, a row is inserted.
+
+    @type fpr: string
+    @param fpr: The fpr to find / add
+
+    @type session: SQLAlchemy
+    @param session: Optional SQL session object (a temporary one will be
+    generated if not supplied).  If not passed, a commit will be performed at
+    the end of the function, otherwise the caller is responsible for commiting.
+    A flush will be performed either way.
+
+    @rtype: Fingerprint
+    @return: the Fingerprint object for the given fpr
+    """
+    privatetrans = False
+    if session is None:
+        session = DBConn().session()
+        privatetrans = True
+
+    try:
+        q = session.query(Fingerprint).filter_by(fingerprint=fpr)
+        if q.count() < 1:
+            fingerprint = Fingerprint()
+            fingerprint.fingerprint = fpr
+            session.add(fingerprint)
+            if privatetrans:
+                session.commit()
+            else:
+                session.flush()
+            return fingerprint
+        else:
+            return q.one()
+
+    except:
+        traceback.print_exc()
+        raise
+
+__all__.append('get_or_set_fingerprint')
+
 ################################################################################
 
 class Keyring(object):
@@ -724,6 +896,49 @@ class Maintainer(object):
 
 __all__.append('Maintainer')
 
+def get_or_set_maintainer(name, session=None):
+    """
+    Returns Maintainer object for given maintainer name.
+
+    If no matching maintainer name is found, a row is inserted.
+
+    @type name: string
+    @param name: The maintainer name to add
+
+    @type session: SQLAlchemy
+    @param session: Optional SQL session object (a temporary one will be
+    generated if not supplied).  If not passed, a commit will be performed at
+    the end of the function, otherwise the caller is responsible for commiting.
+    A flush will be performed either way.
+
+    @rtype: Maintainer
+    @return: the Maintainer object for the given maintainer
+    """
+    privatetrans = False
+    if session is None:
+        session = DBConn().session()
+        privatetrans = True
+
+    try:
+        q = session.query(Maintainer).filter_by(name=name)
+        if q.count() < 1:
+            maintainer = Maintainer()
+            maintainer.name = name
+            session.add(maintainer)
+            if privatetrans:
+                session.commit()
+            else:
+                session.flush()
+            return maintainer
+        else:
+            return q.one()
+
+    except:
+        traceback.print_exc()
+        raise
+
+__all__.append('get_or_set_maintainer')
+
 ################################################################################
 
 class NewComment(object):
@@ -977,6 +1192,18 @@ class Priority(object):
     def __init__(self, *args, **kwargs):
         pass
 
+    def __eq__(self, val):
+        if isinstance(val, str):
+            return (self.priority == val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
+    def __ne__(self, val):
+        if isinstance(val, str):
+            return (self.priority != val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
     def __repr__(self):
         return '<Priority %s (%s)>' % (self.priority, self.priority_id)
 
@@ -1163,15 +1390,15 @@ class QueueBuild(object):
 
 __all__.append('QueueBuild')
 
-def get_queue_build(filename, suite_id, session=None):
+def get_queue_build(filename, suite, session=None):
     """
-    Returns QueueBuild object for given C{filename} and C{suite id}.
+    Returns QueueBuild object for given C{filename} and C{suite}.
 
     @type filename: string
     @param filename: The name of the file
 
-    @type suiteid: int
-    @param suiteid: Suite ID
+    @type suiteid: int or str
+    @param suiteid: Suite name or ID
 
     @type session: Session
     @param session: Optional SQLA session object (a temporary one will be
@@ -1183,7 +1410,12 @@ def get_queue_build(filename, suite_id, session=None):
     """
     if session is None:
         session = DBConn().session()
-    q = session.query(QueueBuild).filter_by(filename=filename).filter_by(suite_id=suite_id)
+    if isinstance(suite, int):
+        q = session.query(QueueBuild).filter_by(filename=filename).filter_by(suite_id=suite)
+    else:
+        q = session.query(QueueBuild).filter_by(filename=filename)
+        q = q.join(Suite).filter_by(suite_name=suite)
+
     if q.count() == 0:
         return None
     return q.one()
@@ -1196,6 +1428,18 @@ class Section(object):
     def __init__(self, *args, **kwargs):
         pass
 
+    def __eq__(self, val):
+        if isinstance(val, str):
+            return (self.section == val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
+    def __ne__(self, val):
+        if isinstance(val, str):
+            return (self.section != val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
     def __repr__(self):
         return '<Section %s>' % self.section
 
@@ -1440,6 +1684,18 @@ class Suite(object):
     def __repr__(self):
         return '<Suite %s>' % self.suite_name
 
+    def __eq__(self, val):
+        if isinstance(val, str):
+            return (self.suite_name == val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
+    def __ne__(self, val):
+        if isinstance(val, str):
+            return (self.suite_name != val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
     def details(self):
         ret = []
         for disp, field in SUITE_FIELDS:
@@ -1561,6 +1817,18 @@ class Uid(object):
     def __init__(self, *args, **kwargs):
         pass
 
+    def __eq__(self, val):
+        if isinstance(val, str):
+            return (self.uid == val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
+    def __ne__(self, val):
+        if isinstance(val, str):
+            return (self.uid != val)
+        # This signals to use the normal comparison operator
+        return NotImplemented
+
     def __repr__(self):
         return '<Uid %s (%s)>' % (self.uid, self.name)
 
@@ -1626,6 +1894,8 @@ def get_or_set_uid(uidname, session=None):
             session.add(uid)
             if privatetrans:
                 session.commit()
+            else:
+                session.flush()
             return uid
         else:
             return q.one()