예제 #1
0
class Message(orm.SQLObject):
    """The class generates a Message table containing information
    about user messages.

    Args:
        text (str, optional):
        time (int, optional):
        filePicture (byte, optional):
        fileVideo (byte, optional):
        fileAudio (byte, optional):
        fileDocument (byte, optional):
        emoji (str, optional):
        editedTime (int, optional):
        editedStatus (bool, optional):

    Returns:
        None
    """
    text = orm.StringCol(default=None)
    time = orm.IntCol(default=None)
    filePicture = orm.BLOBCol(default=None)
    fileVideo = orm.BLOBCol(default=None)
    fileAudio = orm.BLOBCol(default=None)
    fileDocument = orm.BLOBCol(default=None)
    emoji = orm.BLOBCol(default=None)
    editedTime = orm.IntCol(default=None)
    editedStatus = orm.BoolCol(default=False)
    userConfig = orm.ForeignKey('UserConfig', refColumn="uuid")
    flow = orm.ForeignKey('Flow', refColumn="flowId")
예제 #2
0
class Subjects(sqlobject.SQLObject):
    _connection = conn
    maths = sqlobject.IntCol(name=None)
    hindi = sqlobject.IntCol(name=None)
    science = sqlobject.IntCol(name=None)
    english = sqlobject.IntCol(name=None)
    student = sqlobject.ForeignKey('Student')
예제 #3
0
    class Author(sqlobject.SQLObject):

        name = sqlobject.StringCol(alternateID=True, length=50)
        urls = sqlobject.MultipleJoin('URL')
        comments = sqlobject.MultipleJoin('Comments')
        points_new = sqlobject.IntCol(default=0)
        points_old = sqlobject.IntCol(default=0)
        points_credit = sqlobject.IntCol(default=0)
예제 #4
0
class Mood(Record):
    """
    Table to hold mood data.
    """
    # Emotional score from -2 to +2.
    emotion = so.IntCol(default=0)

    # Eight key emotional areas.
    joy = so.IntCol(default=0)
    trust = so.IntCol(default=0)
    fear = so.IntCol(default=0)
    surprise = so.IntCol(default=0)
    sadness = so.IntCol(default=0)
    disgust = so.IntCol(default=0)
    anger = so.IntCol(default=0)
    anticipation = so.IntCol(default=0)

    def _set_emotion(self, value):
        """
        Enforce rule that emotion value must be an integer or of a type which
        can be parsed to integer.
        And must be -2, -1, 0, 1 or 2.
        """
        try:
            intValue = int(value)
        except TypeError:
            raise 'TypeError, Emotion score must be an integer.'

        assert -2<=intValue<=2, \
            'ValueError, Emotion score must be between -2 and +2.'

        self._SO_set_emotion(intValue)
예제 #5
0
class Board(SO.SQLObject):
    chunk_size = SO.IntCol()
    chunk_mines = SO.IntCol()
    chunks = SO.MultipleJoin('Chunk')

    def get_chunk(self, i, k):
        chunk = Chunk.selectBy(i=i, k=k, board=self)
        if chunk.count():
            return chunk.getOne()
        chunk = Chunk(i=i, k=k, board=self)
        chunk.generate_mines()
        return chunk
예제 #6
0
class Lyric(sqlobject.SQLObject):
    _connection = conn
    sid = sqlobject.IntCol(length=14, unique=True)
    song = sqlobject.UnicodeCol(length=255)
    lrc = sqlobject.UnicodeCol(length=255)
    artist_id = sqlobject.ForeignKey('Artist')
    aid = sqlobject.IntCol(length=14)

    #new add field
    local_path = sqlobject.UnicodeCol(length=255, default=None)
    sizes = sqlobject.IntCol(default=None)
    source = sqlobject.UnicodeCol(default=None)
class User(sqlobject.SQLObject):
    _connection = establish_connection()
    userName = sqlobject.StringCol(length=100, unique=False)
    age = sqlobject.IntCol(default=None)
    height = sqlobject.IntCol(default=None)
    weight = sqlobject.IntCol(default=None)
    gender = sqlobject.StringCol(length=6)
    activity = sqlobject.FloatCol(default=None)

    def __repr__(self):
        return "name: {}\nage: {}\nheight: {}\nweight: {}\ngender: {}\nactv: {}".format(self.userName,\
                  self.age, self.height, self.weight, self.gender, self.activity)
예제 #8
0
class FileMeta(sqlobject.SQLObject, File):
    """
    store rating metadata about a file, create thumbnails, and more!
    """

    class sqlmeta:
        lazyUpdate = True  # must call #syncUpdate or #sync to save changes

    MOCK = False

    absolute =    sqlobject.StringCol(notNone=True, unique=True,
                                      alternateID=True)
    hits =        sqlobject.IntCol(notNone=True, default=0)
    rating =      sqlobject.FloatCol(notNone=True, default=0.0)
    rating_hits = sqlobject.IntCol(notNone=True, default=0)

    def rate(self, rating):
        """
        store an incoming rating value, out of 10
        would rate/10
        """
        # no crazy bznz
        if rating > 10 or rating < 0:
            raise ValueError('Rating value out of bounds [0 - 10]')
            return self.rating

        so_far = self.rating * self.ratingHits
        now = (so_far + rating) / (self.rating_hits + 1)
        self.rating = now
        self.ratingHits = self.rating_hits + 1
        self.syncUpdate()
        return now

    def hit(self):
        self.hits += 1
        self.syncUpdate()
        return self.hits

    @classmethod
    def for_path(cls, absolute, root=None):
        """get or create for this path"""

        if cls.MOCK:
            return MockFileMeta(absolute=absolute, hits=0, rating=5.5, rating_hits=100)

        try:
            instance = cls.byAbsolute(absolute)
        except sqlobject.SQLObjectNotFound:
            instance = cls(absolute=absolute)
            instance.syncUpdate()
        instance.root = root
        return instance
예제 #9
0
class ValorMedicion(SO.SQLObject, Serializer):
    class sqlmeta:
        style = SO.MixedCaseStyle(longID=True)

    valor = SO.DecimalCol(size=10, precision=2)
    unixTimeStamp = SO.IntCol()
    medicion = SO.ForeignKey('Medicion')
예제 #10
0
class Medicion(SO.SQLObject, Serializer):
    class sqlmeta:
        style = SO.MixedCaseStyle(longID=True)
    nombre = SO.StringCol(length=40, varchar=True)      
    intervalo = SO.IntCol()
    linea = SO.ForeignKey('Linea')
    unidad = SO.ForeignKey('Unidad')
예제 #11
0
class Product(sqlobject.SQLObject):
    _connection = establish_connection()
    productName = sqlobject.StringCol(length=100)
    energyPoints = sqlobject.IntCol(default=None)
    date = sqlobject.DateCol()

    def __repr__(self):
        return "date: {} name = {}, energy = {}".format(self.date,\
                                                self.productName, self.energyPoints)
예제 #12
0
class SingleImageRow(sqlobject.SQLObject):
    # single big text field for tags
    tags = sqlobject.StringCol()
    rawData = sqlobject.StringCol()
    hits = sqlobject.IntCol()
    originalPathName = sqlobject.StringCol()
    name = sqlobject.StringCol()
    dataType = sqlobject.StringCol()
    series = sqlobject.ForeignKey("ImageSeriesRow", default=None)
예제 #13
0
class Guest(DictSQLObject):
    """
    Collects information about Guests
    Refrenced to by the ChatMsg Table
    """
    name = so.UnicodeCol()
    admin = so.BoolCol(default=False)
    parprop = so.IntCol(default=-1)
    token = so.StringCol(length=8)
    event = so.ForeignKey('Event')
예제 #14
0
class Movie(sqlobject.SQLObject):
    """Class voor het databaseobject movie"""
    _connection = conn
    ft_link = sqlobject.StringCol()
    ft_title = sqlobject.StringCol()
    ft_year = sqlobject.StringCol()
    ft_director = sqlobject.StringCol()
    ft_cast = sqlobject.StringCol()
    ft_genre = sqlobject.StringCol()
    ft_country = sqlobject.StringCol()
    ft_cover_img = sqlobject.StringCol()
    ft_tagline = sqlobject.StringCol()
    ft_length = sqlobject.StringCol()
    ft_synopsis = sqlobject.StringCol()
    ft_rating = sqlobject.FloatCol()
    ft_votes = sqlobject.IntCol()
    imdb_id = sqlobject.StringCol(unique=True)
    imdb_rating = sqlobject.FloatCol()
    imdb_votes = sqlobject.IntCol()
    ft_movietip = sqlobject.StringCol()
예제 #15
0
class Flow(orm.SQLObject):
    """The class generates a Flow table containing information
    about threads and their types (chat, channel, group).

    Args:
        flowId (int, required):
        timeCreated (int, optional):
        flowType (str, optional):
        title (str, optional):
        info (str, optional):

    Returns:
        None
    """
    flowId = orm.IntCol(alternateID=True, unique=True, notNone=True)
    timeCreated = orm.IntCol(default=None)
    flowType = orm.StringCol(default=None)
    title = orm.StringCol(default=None)
    info = orm.StringCol(default=None)
    # Connection to the Message table
    message = orm.MultipleJoin('Message')
예제 #16
0
    class URL(sqlobject.SQLObject):
        class sqlmeta:

            table = 'url'

        url = sqlobject.StringCol()
        clean = sqlobject.StringCol()
        author = sqlobject.ForeignKey('Author')
        channel = sqlobject.ForeignKey('Channel')
        citations = sqlobject.IntCol(default=0)
        posted = sqlobject.DateTimeCol(default=datetime.now)
        comments = sqlobject.MultipleJoin('Comments')
예제 #17
0
class Job(sqlobject.SQLObject):

    status = sqlobject.IntCol(default=JobStatus.UNKNOWN)
    package = sqlobject.ForeignKey('Package', cascade=True)

    dist = sqlobject.StringCol(default='unreleased')
    arch = sqlobject.StringCol(default='any')

    creation_date = sqlobject.DateTimeCol(default=sqlobject.DateTimeCol.now)
    build_host = sqlobject.StringCol(default=None)
    status_changed = sqlobject.DateTimeCol(default=None)
    build_start = sqlobject.DateTimeCol(default=None)
    build_end = sqlobject.DateTimeCol(default=None)

    def __init__(self, *args, **kwargs):
        sqlobject.SQLObject.__init__(self, *args, **kwargs)
        self.status_lock = status_lock

    def __setattr__(self, name, value):
        if name == "status":
            self.status_changed = sqlobject.DateTimeCol.now()

        sqlobject.SQLObject.__setattr__(self, name, value)

    def dict(self):

        result = {
            "id": self.id,
            "task": "%s/%s" % (self.dist, self.arch),
            "build_host": self.build_host,
            "status": JobStatus.whatis(self.status),
            "dist": self.dist,
            "arch": self.arch,
            "creation_date": try_strftime(self.creation_date),
            "build_start": try_strftime(self.build_start),
            "build_end": try_strftime(self.build_end),
            "status_changed": try_strftime(self.status_changed)
        }
        return result

    def start(self, slave, builder):
        if self.status != JobStatus.WAIT_LOCKED:
            raise ValueError("JobStatus is not WAIT_LOCKED")
        else:
            self.status = JobStatus.BUILDING
            self.build_start = sqlobject.DateTimeCol.now()
            self.build_host = slave.name
            kwargs = self.dict()
            kwargs.update(self.package.dict())
            return slave.build(self.id, builder, kwargs)
예제 #18
0
class UwatchPkgVersion(sqlobject.SQLObject):
  
  id_pkg = sqlobject.IntCol(dbName="ID_PKG")
  gar_path = sqlobject.UnicodeCol(length=255, dbName="PKG_GAR_PATH")
  pkgname = sqlobject.UnicodeCol(length=64, dbName="PKG_NAME")
  catalogname = sqlobject.UnicodeCol(length=64, dbName="PKG_CATALOGNAME")
  gar_version = sqlobject.UnicodeCol(length=255, dbName="PKG_GAR_VERSION")
  upstream_version = sqlobject.UnicodeCol(length=255, dbName="PKG_UPSTREAM_VERSION")
  master_sites = sqlobject.UnicodeCol(length=255, dbName="PKG_UPSTREAM_MASTER_SITES")
  distfiles = sqlobject.UnicodeCol(length=255, dbName="PKG_GAR_DISTFILES")
  regex = sqlobject.UnicodeCol(length=255, dbName="PKG_UFILES_REGEXP")

  class sqlmeta(object):
    table = "UWATCH_PKG_VERSION"
    idName = "id_pkg"
예제 #19
0
class Errors(orm.SQLObject):
    """The class generates an Errors table in which
    all types of errors are pre-stored.

    Args:
        status (str, optional):
        code (int, optional):
        detail (str, optional):

    Returns:
        None
    """
    # status and code is standart HTTP status code
    status = orm.StringCol(default=None)
    code = orm.IntCol(default=None)
    detail = orm.StringCol(default=None)
예제 #20
0
class UserConfig(orm.SQLObject):
    """The class generates a table containing data
    about the user and his settings.

    Args:
        uuid (int, required):
        login (str, required):
        password (str, required):
        hash_password (str, optional)
        username (str, optional):
        isBot (bool, optional): default False
        authId (str, optional):
        email (str, optional):
        avatar (str, optional):
        bio (str, optional):
        salt (str, optional):
        key (str, optional):

    Returns:
        None
    """
    # added alternateID for added class method @byUUID
    # which will return that object
    uuid = orm.IntCol(alternateID=True, unique=True, notNone=True)
    login = orm.StringCol()
    password = orm.StringCol()
    hashPassword = orm.StringCol(default=None)
    username = orm.StringCol(default=None)
    isBot = orm.BoolCol(default=False)
    authId = orm.StringCol(default=None)
    email = orm.StringCol(default=None)
    avatar = orm.BLOBCol(default=None)
    bio = orm.StringCol(default=None)
    salt = orm.BLOBCol(default=None)
    key = orm.BLOBCol(default=None)
    # Connection to the Message table
    message = orm.MultipleJoin('Message')
예제 #21
0
class Srv4FileStats(sqlobject.SQLObject):
    """Represents a srv4 file.

  It focuses on the stats, but it can as well represent just a srv4 file.
  """
    arch = sqlobject.ForeignKey('Architecture', notNone=True)
    basename = sqlobject.UnicodeCol(notNone=True)
    catalogname = sqlobject.UnicodeCol(notNone=True)
    # The data structure can be missing - necessary for fake SUNW
    # packages.
    data_obj = sqlobject.ForeignKey('Srv4FileStatsBlob', notNone=False)
    filename_arch = sqlobject.ForeignKey('Architecture', notNone=True)
    latest = sqlobject.BoolCol(notNone=True)
    maintainer = sqlobject.ForeignKey('Maintainer', notNone=False)
    md5_sum = sqlobject.UnicodeCol(notNone=True, unique=True, length=32)
    size = sqlobject.IntCol()
    mtime = sqlobject.DateTimeCol(notNone=False)
    os_rel = sqlobject.ForeignKey('OsRelease', notNone=True)
    pkginst = sqlobject.ForeignKey('Pkginst', notNone=True)
    registered = sqlobject.BoolCol(notNone=True)
    use_to_generate_catalogs = sqlobject.BoolCol(notNone=True)
    rev = sqlobject.UnicodeCol(notNone=False)
    stats_version = sqlobject.IntCol(notNone=True)
    version_string = sqlobject.UnicodeCol(notNone=True)
    in_catalogs = sqlobject.MultipleJoin('Srv4FileInCatalog',
                                         joinColumn='srv4file_id')
    files = sqlobject.MultipleJoin('CswFile', joinColumn='id')

    def __init__(self, *args, **kwargs):
        super(Srv4FileStats, self).__init__(*args, **kwargs)
        self._cached_pkgstats = None

    def DeleteAllDependentObjects(self):
        data_obj = self.data_obj
        self.data_obj = None
        if data_obj:
            # It could be already missing
            data_obj.destroySelf()
        self.RemoveAllCswFiles()
        self.RemoveAllCheckpkgResults()
        self.RemoveOverrides()

    def RemoveAllCswFiles(self):
        # Removing existing files, using sqlbuilder to use sql-level
        # mechanisms without interacting with Python.
        # http://www.mail-archive.com/[email protected]/msg00520.html
        sqlobject.sqlhub.processConnection.query(
            sqlobject.sqlhub.processConnection.sqlrepr(
                sqlbuilder.Delete(CswFile.sqlmeta.table,
                                  CswFile.q.srv4_file == self)))

    def GetOverridesResult(self):
        return CheckpkgOverride.select(CheckpkgOverride.q.srv4_file == self)

    def GetErrorTagsResult(self, os_rel, arch, catrel):
        assert arch.name != 'all', (
            "Asked for the 'all' architecture, this is not valid "
            "for GetErrorTagsResult().")
        return CheckpkgErrorTag.select(
            sqlobject.AND(CheckpkgErrorTag.q.srv4_file == self,
                          CheckpkgErrorTag.q.os_rel == os_rel,
                          CheckpkgErrorTag.q.arch == arch,
                          CheckpkgErrorTag.q.catrel == catrel))

    def RemoveCheckpkgResults(self, os_rel, arch, catrel):
        logging.debug("%s: RemoveCheckpkgResults(%s, %s, %s)", self, os_rel,
                      arch, catrel)
        sqlobject.sqlhub.processConnection.query(
            sqlobject.sqlhub.processConnection.sqlrepr(
                sqlbuilder.Delete(
                    CheckpkgErrorTag.sqlmeta.table,
                    sqlobject.AND(CheckpkgErrorTag.q.srv4_file == self,
                                  CheckpkgErrorTag.q.os_rel == os_rel,
                                  CheckpkgErrorTag.q.arch == arch,
                                  CheckpkgErrorTag.q.catrel == catrel))))

    def RemoveAllCheckpkgResults(self):
        logging.debug("%s: RemoveAllCheckpkgResults()", self)
        sqlobject.sqlhub.processConnection.query(
            sqlobject.sqlhub.processConnection.sqlrepr(
                sqlbuilder.Delete(CheckpkgErrorTag.sqlmeta.table,
                                  CheckpkgErrorTag.q.srv4_file == self)))

    def RemoveOverrides(self):
        logging.debug("%s: RemoveOverrides()", self)
        sqlobject.sqlhub.processConnection.query(
            sqlobject.sqlhub.processConnection.sqlrepr(
                sqlbuilder.Delete(CheckpkgOverride.sqlmeta.table,
                                  CheckpkgOverride.q.srv4_file == self)))

    def __unicode__(self):
        return (u"Package: %s-%s, %s" %
                (self.catalogname, self.version_string, self.arch.name))

    def GetUnicodeOrNone(self, s):
        """Tries to decode UTF-8.

    If the object does not decode as UTF-8, it's forced to do so, while
    ignoring any potential errors.

    Returns: a unicode object or a None type.
    """
        if s is None:
            return None
        if type(s) != unicode:
            try:
                s = unicode(s, 'utf-8')
            except UnicodeDecodeError, e:
                s = s.decode("utf-8", "ignore")
                s = s + u" (bad unicode detected)"
        return s
예제 #22
0
class Mine(SO.SQLObject):
    x = SO.IntCol()
    y = SO.IntCol()
    chunk = SO.ForeignKey('Chunk')
예제 #23
0
class CswConfig(sqlobject.SQLObject):
  option_key = sqlobject.UnicodeCol(length=255, unique=True)
  float_value = sqlobject.FloatCol(default=None)
  int_value = sqlobject.IntCol(default=None)
  str_value = sqlobject.UnicodeCol(default=None, length=250)
예제 #24
0
class Srv4FileStats(sqlobject.SQLObject):
  """Represents a srv4 file.

  It focuses on the stats, but it can as well represent just a srv4 file.
  """
  arch = sqlobject.ForeignKey('Architecture', notNone=True)
  basename = sqlobject.UnicodeCol(notNone=True, length=250)
  catalogname = sqlobject.UnicodeCol(notNone=True, length=250)
  filename_arch = sqlobject.ForeignKey('Architecture', notNone=True)
  maintainer = sqlobject.ForeignKey('Maintainer', notNone=False)
  md5_sum = sqlobject.UnicodeCol(notNone=True, unique=True, length=32)
  size = sqlobject.IntCol()
  mtime = sqlobject.DateTimeCol(notNone=False)
  os_rel = sqlobject.ForeignKey('OsRelease', notNone=True)
  osrel_str = sqlobject.UnicodeCol(notNone=True, length=9) # "SunOS5.10"
  pkginst = sqlobject.ForeignKey('Pkginst', notNone=True)
  pkginst_str = sqlobject.UnicodeCol(notNone=True, length=255)
  registered_level_one = sqlobject.BoolCol(notNone=True)
  registered_level_two = sqlobject.BoolCol(notNone=True)
  use_to_generate_catalogs = sqlobject.BoolCol(notNone=True)
  rev = sqlobject.UnicodeCol(notNone=False, length=250)
  stats_version = sqlobject.IntCol(notNone=True)
  version_string = sqlobject.UnicodeCol(notNone=True, length=250)
  bundle = sqlobject.UnicodeCol(length=250)
  in_catalogs = sqlobject.MultipleJoin(
          'Srv4FileInCatalog',
          joinColumn='srv4file_id')
  files = sqlobject.MultipleJoin('CswFile',
          joinColumn='id')
  catalog_idx = sqlobject.DatabaseIndex('catalogname')
  basename_idx = sqlobject.DatabaseIndex('basename')
  pkginst_idx = sqlobject.DatabaseIndex('pkginst')

  def __init__(self, *args, **kwargs):
    super(Srv4FileStats, self).__init__(*args, **kwargs)

  def __unicode__(self):
    return u'%s/%s, %s' % (self.pkginst.pkgname, self.catalogname, self.md5_sum)

  def __str__(self):
    return str(unicode(self))

  def DeleteAllDependentObjects(self):
    """Prepares the object to be deleted.

    Use this function with caution.
    """
    self.DeleteDependentObjectsPopulatedFromPackageItself()
    logger.debug('Removing all dependent objects from %s; it will cause the '
                 'package to be removed from all catalogs.', self)
    self.RemoveCatalogAssignments()
    self.RemoveAllCheckpkgResults()

  def DeleteDependentObjectsPopulatedFromPackageItself(self):
    """Removing all the objects that only depend on the package contents.

    It doesn't touch rows that are created for other reasons, e.g. assignments
    of packages to catalogs.
    """
    logger.debug('%s - Deleting objects that only depend on the package '
                 'contents', self)
    self.RemoveAllCswFiles()
    self.RemoveOverrides()
    self.RemoveDepends()
    self.RemoveIncompatibles()

  def RemoveAllCswFiles(self):
    # Removing existing files, using sqlbuilder to use sql-level
    # mechanisms without interacting with Python.
    # http://www.mail-archive.com/[email protected]/msg00520.html
    sqlobject.sqlhub.processConnection.query(
        sqlobject.sqlhub.processConnection.sqlrepr(sqlbuilder.Delete(
          CswFile.sqlmeta.table,
          CswFile.q.srv4_file==self)))

  def RemoveDepends(self):
    sqlobject.sqlhub.processConnection.query(
        sqlobject.sqlhub.processConnection.sqlrepr(sqlbuilder.Delete(
          Srv4DependsOn.sqlmeta.table,
          Srv4DependsOn.q.srv4_file==self)))

  def RemoveIncompatibles(self):
    sqlobject.sqlhub.processConnection.query(
        sqlobject.sqlhub.processConnection.sqlrepr(sqlbuilder.Delete(
          Srv4IncompatibleWith.sqlmeta.table,
          Srv4IncompatibleWith.q.srv4_file==self)))

  def RemoveCatalogAssignments(self):
    sqlobject.sqlhub.processConnection.query(
        sqlobject.sqlhub.processConnection.sqlrepr(sqlbuilder.Delete(
          Srv4FileInCatalog.sqlmeta.table,
          Srv4FileInCatalog.q.srv4file==self)))

  def GetOverridesResult(self):
    return CheckpkgOverride.select(CheckpkgOverride.q.srv4_file==self)

  def GetErrorTagsResult(self, os_rel, arch, catrel):
    assert arch.name != 'all', (
        "Asked for the 'all' architecture, this is not valid "
        "for GetErrorTagsResult().")
    return CheckpkgErrorTag.select(
        sqlobject.AND(
            CheckpkgErrorTag.q.srv4_file==self,
            CheckpkgErrorTag.q.os_rel==os_rel,
            CheckpkgErrorTag.q.arch==arch,
            CheckpkgErrorTag.q.catrel==catrel))

  def RemoveCheckpkgResults(self, os_rel, arch, catrel):
    logger.debug("%s: RemoveCheckpkgResults(%s, %s, %s)",
                  self, os_rel, arch, catrel)
    sqlobject.sqlhub.processConnection.query(
        sqlobject.sqlhub.processConnection.sqlrepr(sqlbuilder.Delete(
          CheckpkgErrorTag.sqlmeta.table,
          sqlobject.AND(
            CheckpkgErrorTag.q.srv4_file==self,
            CheckpkgErrorTag.q.os_rel==os_rel,
            CheckpkgErrorTag.q.arch==arch,
            CheckpkgErrorTag.q.catrel==catrel))))

  def RemoveAllCheckpkgResults(self):
    logger.debug("%s: RemoveAllCheckpkgResults()", self)
    sqlobject.sqlhub.processConnection.query(
        sqlobject.sqlhub.processConnection.sqlrepr(sqlbuilder.Delete(
          CheckpkgErrorTag.sqlmeta.table,
          CheckpkgErrorTag.q.srv4_file==self)))

  def RemoveOverrides(self):
    logger.debug("%s: RemoveOverrides()", self)
    sqlobject.sqlhub.processConnection.query(
        sqlobject.sqlhub.processConnection.sqlrepr(sqlbuilder.Delete(
          CheckpkgOverride.sqlmeta.table,
          CheckpkgOverride.q.srv4_file==self)))

  def GetUnicodeOrNone(self, s):
    """Tries to decode UTF-8.

    If the object does not decode as UTF-8, it's forced to do so, while
    ignoring any potential errors.

    Returns: a unicode object or a None type.
    """
    if s is None:
      return None
    if type(s) != unicode:
      try:
        s = unicode(s, 'utf-8')
      except UnicodeDecodeError, e:
        s = s.decode("utf-8", "ignore")
        s = s + u" (bad unicode detected)"
    return s
예제 #25
0
class Profile(so.SQLObject):
    """
    Models a user profile on Twitter.

    Note that URL columns are named as 'Url', since SQLOlbject converts
    'imageURL' to db column named 'image_ur_l'.

    Twitter screen name and username rules:
        https://help.twitter.com/en/managing-your-account/twitter-username-rules
    We use slightly higher values than the ones there, to be safe.

    Notes on screen name:
    - This should not have unique restriction as users can edit their
        screen name so others can take an older screen name. Or someone
        could delete and recreate their account.
    - Twitter itself enforces uniqueness across case.
    """

    # Profile's ID (integer), as assigned by Twitter when the Profile was
    # created. This is a global ID, rather than an ID specific to our local db.
    guid = so.IntCol(alternateID=True)

    # Profile screen name.
    screenName = so.StringCol(notNull=True, length=30)

    # Profile display Name.
    name = so.StringCol(notNull=True, length=60)

    # Description, as set in profile's bio.
    description = so.StringCol(default=None)

    # Location, as set in profile's bio.
    location = so.StringCol(default=None)

    # Link to the profile's image online. This will only be thumbnail size.
    imageUrl = so.StringCol(default=None, validator=URL)

    # Count of profile's followers.
    followersCount = so.IntCol(notNull=True)

    # Count of profile's statuses (tweets) posted by this profile.
    statusesCount = so.IntCol(notNull=True)

    # Profile's verified status.
    verified = so.BoolCol(notNull=True, default=False)

    # Join the Profile with its created tweets in the Tweet table.
    tweets = so.MultipleJoin("Tweet")

    # Date and time when follower and status counts were last updated.
    modified = so.DateTimeCol(notNull=True, default=so.DateTimeCol.now)
    modifiedIdx = so.DatabaseIndex(modified)

    # Get Category objects which this Profile has been assigned to, if any.
    categories = so.SQLRelatedJoin("Category",
                                   intermediateTable="profile_category",
                                   createRelatedTable=False)

    def set(self, **kwargs):
        """
        Override the update hook to update the modified field if necessary.
        """
        if ("followersCount" in kwargs
                or "statusesCount" in kwargs) and "modified" not in kwargs:
            kwargs["modified"] = so.DateTimeCol.now()
        super(Profile, self).set(**kwargs)

    def getFlatDescription(self):
        """
        Return the description with newline characters replaced with spaces.
        """
        if self.description is not None:
            return lib.text_handling.flattenText(self.description)

        return None

    def getProfileUrl(self):
        """
        Get link to the profile's page online.

        :return: Twitter profile's URL, as a string.
        """
        return "https://twitter.com/{0}".format(self.screenName)

    def getLargeImageUrl(self):
        """
        Get link to a large version profile's image, based on thumbnail URL.

        The image URL comes from the API as '..._normal.jpeg', but
        from API calls on loading a twitter.com page, it is possible to
        see that the image media server allows variations of the last part,
        to return a large image. Such as
         - '..._bigger.jpeg' (which is not much bigger than the normal
                thumbnail)
         - '..._400x400.jpeg' (which is much bigger).

        :return: image URL using 400x400 size parameter, or None if value
            was not set.
        """
        if self.imageUrl:
            return self.imageUrl.replace("_normal", "_400x400")

        return None

    def prettyPrint(self):
        """
        Method to print the attributes of the Profile instance neatly.

        :return: dictionary of data which was printed.
        """
        output = """\
Screen name    : @{screenName}
Name           : {name}
Verified       : {verified}
Followers      : {followers:,d}
Statuses       : {statuses:,d}
DB tweets      : {tweetCount}
Description    : {description}
Profile URL    : {url}
Image URL      : {imageUrl}
Stats modified : {statsModified}
        """
        data = dict(
            screenName=self.screenName,
            name=self.name,
            verified=self.verified,
            followers=self.followersCount,
            statuses=self.statusesCount,
            tweetCount=len(self.tweets),
            description=self.getFlatDescription(),
            url=self.getProfileUrl(),
            imageUrl=self.getLargeImageUrl(),
            statsModified=self.modified,
        )
        print(output.format(**data))

        return data
예제 #26
0
class Tweet(so.SQLObject):
    """
    Models a tweet on Twitter.

    If we are inserting the Tweet in our db, we expect to always have the
    author's profile in the Profile table. If the tweet is a reply, we will
    have references to the target Profile and original Tweet as GUID integers.
    But we are unlikely to have those object stored in our db. Use
    the `.getInReplyToTweet` and `.getInReplyToProfile` methods to see if those
    exist in the db, otherwise use the GUIDs to look up data from the
    Twitter API and then store them locally as db records.

    For relating a Tweet to its author Profile with a foreign key, a
    `setProfileByGuid` method could be implemented to set the profile
    foreign key using a given GUID, but that would require doing a search
    each time. So, when creating a Tweet object or multiple objects for one
    Profile, it is preferable to get the Profile object's ID once
    and then repeately pass that in as an argument for each Tweet object
    that is created for that Profile.

    For ordering, the '-guid' syntax is here is preferred, since
    'guid DESC' results in an error when getting tweets of a Profile object,
    even though doing a query on Tweet class itself is fine.
        `AttributeError: 'Tweet' object has no attribute 'guid DESC'`
    The error is also raised for multiple names e.g. '-guid, message'.
    """
    class sqlmeta:
        # Show recent Tweets (with higher GUID values) first.
        defaultOrder = "-guid"

    # Tweet ID (integer), as assigned by Twitter when the Tweet was posted.
    # This is a global ID, rather than specific to our local db.
    guid = so.IntCol(alternateID=True)

    # Link to Tweet's author in the Profile table. Delete Tweet if
    # the Profile is deleted.
    profile = so.ForeignKey("Profile", notNull=True, cascade=True)
    profileIdx = so.DatabaseIndex(profile)

    # Date and time the tweet was posted.
    createdAt = so.DateTimeCol(notNull=True)
    createdAtIdx = so.DatabaseIndex(createdAt)

    # Tweet message text. Length is not validated since expanded tweets can
    # be longer than the standard 280 (previously 140) characters.
    message = so.StringCol(notNull=True)

    # Count of favorites on this Tweet.
    favoriteCount = so.IntCol(notNull=True)

    # Count of retweets of this Tweet.
    retweetCount = so.IntCol(notNull=True)

    # If the tweet is a reply, the GUID of the Tweet which the reply is
    # directed at (from reply_to_status_id field). This does not require
    # the Tweet to be in the local db.
    inReplyToTweetGuid = so.IntCol(default=None)

    # If the tweet is a reply, the GUID of the Profile which the reply is
    # directed at (from reply_to_user_id field). This does not require
    # the Tweet to be in the local db.
    inReplyToProfileGuid = so.IntCol(default=None)

    # Date and time when favorite and retweet counts where last updated.
    modified = so.DateTimeCol(notNull=True, default=so.DateTimeCol.now)
    modifiedIdx = so.DatabaseIndex(modified)

    # Get Campaign objects which this Profile has been assigned to, if any.
    campaigns = so.SQLRelatedJoin("Campaign",
                                  intermediateTable="tweet_campaign",
                                  createRelatedTable=False)

    def set(self, **kwargs):
        """
        Override the update hook to update the modified field if necessary.
        """
        if ("favoriteCount" in kwargs
                or "retweetCount" in kwargs) and "modified" not in kwargs:
            kwargs["modified"] = so.DateTimeCol.now()
        super(Tweet, self).set(**kwargs)

    def isRT(self):
        return self.message.startswith("RT ")

    def isReply(self):
        return self.inReplyToProfileGuid is not None

    def getFlatMessage(self):
        """
        Return the message with newline characters replaced with spaces.
        """
        return lib.text_handling.flattenText(self.message)

    def getInReplyToTweet(self):
        """
        If this Tweet is a reply, get the original Tweet it was directed at.

        :return: single Tweet object. Return None if this is not a reply. Raise
            an error if the Tweet is not in the local db.
        """
        if self.inReplyToTweetGuid:
            try:
                return Tweet.byGuid(self.inReplyToTweetGuid)
            except SQLObjectNotFound as e:
                raise type(e)(
                    "Could not find Tweet in db with GUID: {0}".format(
                        self.inReplyToTweetGuid))
        return None

    def getInReplyToProfile(self):
        """
        If this Tweet is a reply, get the Profile which it was directed at.

        :return: single Profile object. Return None if this is not a reply.
            Raise an error if the Tweet is not in the local db.
        """
        if self.inReplyToProfileGuid:
            try:
                return Profile.byGuid(self.inReplyToProfileGuid)
            except SQLObjectNotFound as e:
                raise type(e)(
                    "Could not find Profile in db with GUID: {0}".format(
                        self.inReplyToProfileGuid))
        return None

    def getTweetURL(self):
        """
        Return URL for the tweet as a string, using tweet author's screen name
        and the tweet's GUID.
        """
        return "https://twitter.com/{screenName}/status/{tweetID}".format(
            screenName=self.profile.screenName, tweetID=self.guid)

    def prettyPrint(self):
        """
        Method to print the attributes of the Tweet instance neatly.

        :return: dictionary of data which was printed.
        """
        output = """\
Author            : @{screenName} - {name} - {followers:,d} followers
Created at        : {createdAt}
Message           : {message}
Favorites         : {favoriteCount:,d}
Retweets          : {retweetCount:,d}
Reply To User ID  : {replyProf}
Reply To Tweet ID : {replyTweet}
URL               : {url}
Stats modified    : {statsModified}
        """
        author = self.profile
        data = dict(
            screenName=author.screenName,
            createdAt=self.createdAt,
            name=author.name,
            followers=author.followersCount,
            message=self.getFlatMessage(),
            favoriteCount=self.favoriteCount,
            retweetCount=self.retweetCount,
            replyProf=self.inReplyToProfileGuid,
            replyTweet=self.inReplyToTweetGuid,
            url=self.getTweetURL(),
            statsModified=self.modified,
        )
        print(output.format(**data))

        return data

    def report(self):
        """
        Return Tweet and Profile data as dict for writing a CSV report.
        """
        author = self.profile

        return {
            "Screen name": author.screenName,
            "Followers": author.followersCount,
            "Tweet URL": self.getTweetURL(),
            "Tweet ID": self.guid,
            "Tweeted at": str(self.createdAt),
            "Is reply": "Y" if self.isReply() else "N",
            "Is RT": "Y" if self.isRT() else "N",
            "Message": self.message,
            "Favs": self.favoriteCount,
            "RTs": self.retweetCount,
        }
예제 #27
0
class Srv4FileStats(sqlobject.SQLObject):
    """Represents a srv4 file.

  It focuses on the stats, but it can as well represent just a srv4 file.
  """
    arch = sqlobject.ForeignKey('Architecture', notNone=True)
    basename = sqlobject.UnicodeCol(notNone=True)
    catalogname = sqlobject.UnicodeCol(notNone=True)
    # The data structure can be missing - necessary for fake SUNW
    # packages.
    data_obj = sqlobject.ForeignKey('Srv4FileStatsBlob', notNone=False)
    filename_arch = sqlobject.ForeignKey('Architecture', notNone=True)
    latest = sqlobject.BoolCol(notNone=True)
    maintainer = sqlobject.ForeignKey('Maintainer', notNone=False)
    md5_sum = sqlobject.UnicodeCol(notNone=True, unique=True, length=32)
    size = sqlobject.IntCol()
    mtime = sqlobject.DateTimeCol(notNone=False)
    os_rel = sqlobject.ForeignKey('OsRelease', notNone=True)
    pkginst = sqlobject.ForeignKey('Pkginst', notNone=True)
    registered = sqlobject.BoolCol(notNone=True)
    use_to_generate_catalogs = sqlobject.BoolCol(notNone=True)
    rev = sqlobject.UnicodeCol(notNone=False)
    stats_version = sqlobject.IntCol(notNone=True)
    version_string = sqlobject.UnicodeCol(notNone=True)
    in_catalogs = sqlobject.MultipleJoin('Srv4FileInCatalog',
                                         joinColumn='srv4file_id')
    files = sqlobject.MultipleJoin('CswFile', joinColumn='id')

    def __init__(self, *args, **kwargs):
        super(Srv4FileStats, self).__init__(*args, **kwargs)
        self._cached_pkgstats = None

    def DeleteAllDependentObjects(self):
        data_obj = self.data_obj
        self.data_obj = None
        if data_obj:
            # It could be already missing
            data_obj.destroySelf()
        self.RemoveAllCswFiles()
        self.RemoveAllCheckpkgResults()
        self.RemoveOverrides()

    def RemoveAllCswFiles(self):
        # Removing existing files, using sqlbuilder to use sql-level
        # mechanisms without interacting with Python.
        # http://www.mail-archive.com/[email protected]/msg00520.html
        sqlobject.sqlhub.processConnection.query(
            sqlobject.sqlhub.processConnection.sqlrepr(
                sqlbuilder.Delete(CswFile.sqlmeta.table,
                                  CswFile.q.srv4_file == self)))

    def GetOverridesResult(self):
        return CheckpkgOverride.select(CheckpkgOverride.q.srv4_file == self)

    def GetErrorTagsResult(self, os_rel, arch, catrel):
        assert arch.name != 'all', (
            "Asked for the 'all' architecture, this is not valid "
            "for GetErrorTagsResult().")
        return CheckpkgErrorTag.select(
            sqlobject.AND(CheckpkgErrorTag.q.srv4_file == self,
                          CheckpkgErrorTag.q.os_rel == os_rel,
                          CheckpkgErrorTag.q.arch == arch,
                          CheckpkgErrorTag.q.catrel == catrel))

    def RemoveCheckpkgResults(self, os_rel, arch, catrel):
        logging.debug("%s: RemoveCheckpkgResults(%s, %s, %s)", self, os_rel,
                      arch, catrel)
        sqlobject.sqlhub.processConnection.query(
            sqlobject.sqlhub.processConnection.sqlrepr(
                sqlbuilder.Delete(
                    CheckpkgErrorTag.sqlmeta.table,
                    sqlobject.AND(CheckpkgErrorTag.q.srv4_file == self,
                                  CheckpkgErrorTag.q.os_rel == os_rel,
                                  CheckpkgErrorTag.q.arch == arch,
                                  CheckpkgErrorTag.q.catrel == catrel))))

    def RemoveAllCheckpkgResults(self):
        logging.debug("%s: RemoveAllCheckpkgResults()", self)
        sqlobject.sqlhub.processConnection.query(
            sqlobject.sqlhub.processConnection.sqlrepr(
                sqlbuilder.Delete(CheckpkgErrorTag.sqlmeta.table,
                                  CheckpkgErrorTag.q.srv4_file == self)))

    def RemoveOverrides(self):
        logging.debug("%s: RemoveOverrides()", self)
        sqlobject.sqlhub.processConnection.query(
            sqlobject.sqlhub.processConnection.sqlrepr(
                sqlbuilder.Delete(CheckpkgOverride.sqlmeta.table,
                                  CheckpkgOverride.q.srv4_file == self)))

    def __unicode__(self):
        return (u"Package: %s-%s, %s" %
                (self.catalogname, self.version_string, self.arch.name))

    def GetStatsStruct(self):
        if not self._cached_pkgstats:
            self._cached_pkgstats = cPickle.loads(str(self.data_obj.pickle))
        return self._cached_pkgstats

    def _GetBuildSource(self):
        data = self.GetStatsStruct()
        build_src = None
        if "OPENCSW_REPOSITORY" in data["pkginfo"]:
            build_src = data["pkginfo"]["OPENCSW_REPOSITORY"]
        return build_src

    def GetSvnUrl(self):
        build_src = self._GetBuildSource()
        svn_url = None
        if build_src:
            svn_url = re.sub(r'([^@]*).*', r'\1/Makefile', build_src)
        return svn_url

    def GetTracUrl(self):
        build_src = self._GetBuildSource()
        trac_url = None
        if build_src:
            trac_url = re.sub(
                r'https://gar.svn.(sf|sourceforge).net/svnroot/gar/([^@]+)@(.*)',
                r'http://sourceforge.net/apps/trac/gar/browser/\2/Makefile?rev=\3',
                build_src)
        return trac_url

    def GetVendorUrl(self):
        data = self.GetStatsStruct()
        vendor_url = None
        if "VENDOR" in data["pkginfo"]:
            vendor_url = re.split(r"\s+", data["pkginfo"]["VENDOR"])[0]
        return vendor_url

    def GetRestRepr(self):
        mimetype = "application/x-vnd.opencsw.pkg;type=srv4-detail"
        data = {
            'arch': self.arch.name,
            'basename': self.basename,
            # For compatibility with the catalog parser from catalog.py
            'file_basename': self.basename,
            'catalogname': self.catalogname,
            'filename_arch': self.filename_arch.name,
            'maintainer_email': self.maintainer.email,
            'maintainer_full_name': self.maintainer.full_name,
            'md5_sum': self.md5_sum,
            'mtime': unicode(self.mtime),
            'osrel': self.os_rel.short_name,
            'pkgname': self.pkginst.pkgname,
            'rev': self.rev,
            'size': self.size,
            'version_string': self.version_string,
            # For compatibility with the catalog parser from catalog.py
            'version': self.version_string,
            # 'in_catalogs': unicode([unicode(x) for x in self.in_catalogs]),
            'vendor_url': self.GetVendorUrl(),
            'repository_url': self.GetSvnUrl(),
        }
        return mimetype, data
예제 #28
0
class UrlMapping(sqlobject.SQLObject):
    shortUrl = sqlobject.StringCol(length=8, unique=True)
    originalUrl = sqlobject.StringCol()
    ctime = sqlobject.IntCol(default=None)
    shortUrl_index = sqlobject.DatabaseIndex(shortUrl)
    ctime_index = sqlobject.DatabaseIndex(ctime)
예제 #29
0
class Action(SO.SQLObject):
    x = SO.IntCol()
    y = SO.IntCol()
    chunk = SO.ForeignKey('Chunk')
    time = SO.TimestampCol()
    action = SO.EnumCol(enumValues=['DIG', 'SWITCH_FLAG'])
예제 #30
0
class Chunk(SO.SQLObject):
    i = SO.IntCol()
    k = SO.IntCol()
    board = SO.ForeignKey('Board')
    mines = SO.MultipleJoin('Mine')

    def generate_mines(self):
        size = self.board.chunk_size
        #generate square list
        squares = set()

        while len(squares) < self.board.chunk_mines:
            x = random.randrange(size)
            y = random.randrange(size)
            squares.add((x, y))

        #create mines in the squares
        for square in squares:
            Mine(x=square[0], y=square[1], chunk=self)

    def get_display(self):
        size = self.board.chunk_size
        #generate display grid
        display = []
        for y in range(size):
            display.append([])
            for x in range(size):
                display[y].append({
                    'is_mine': False,
                    'count': 0,
                    'is_hidden': True,
                    'flag': False
                })
        #check self mines
        for mine in self.mines:
            display[mine.y][mine.x]['is_mine'] = True
            for x in range(mine.x - 1, mine.x + 2):
                for y in range(mine.y - 1, mine.y + 2):
                    if x >= 0 and x < size and y >= 0 and y < size:
                        display[y][x]['count'] += 1
        #check left mines
        chunk = self.board.get_chunk(i=self.i - 1, k=self.k)
        mines = Mine.selectBy(chunk=chunk, x=size - 1)
        for mine in mines:
            for y in range(mine.y - 1, mine.y + 2):
                if y >= 0 and y < size:
                    display[y][0]['count'] += 1
        #check right mines
        chunk = self.board.get_chunk(i=self.i + 1, k=self.k)
        mines = Mine.selectBy(chunk=chunk, x=0)
        for mine in mines:
            for y in range(mine.y - 1, mine.y + 2):
                if y >= 0 and y < size:
                    display[y][size - 1]['count'] += 1
        #check up mines
        chunk = self.board.get_chunk(i=self.i, k=self.k - 1)
        mines = Mine.selectBy(chunk=chunk, y=size - 1)
        for mine in mines:
            for x in range(mine.x - 1, mine.x + 2):
                if x >= 0 and x < size:
                    display[0][x]['count'] += 1
        #check down mines
        chunk = self.board.get_chunk(i=self.i, k=self.k + 1)
        mines = Mine.selectBy(chunk=chunk, y=0)
        for mine in mines:
            for x in range(mine.x - 1, mine.x + 2):
                if x >= 0 and x < size:
                    display[size - 1][x]['count'] += 1
        #check left_up mines
        chunk = self.board.get_chunk(i=self.i - 1, k=self.k - 1)
        mine = Mine.selectBy(chunk=chunk, x=size - 1, y=size - 1)
        if mine.count():
            display[0][0]['count'] += 1
        #check right_up mines
        chunk = self.board.get_chunk(i=self.i + 1, k=self.k - 1)
        mine = Mine.selectBy(chunk=chunk, x=0, y=size - 1)
        if mine.count():
            display[0][size - 1]['count'] += 1
        #check left_down mines
        chunk = self.board.get_chunk(i=self.i - 1, k=self.k + 1)
        mine = Mine.selectBy(chunk=chunk, x=size - 1, y=0)
        if mine.count():
            display[size - 1][0]['count'] += 1
        #check right_down mines
        chunk = self.board.get_chunk(i=self.i + 1, k=self.k + 1)
        mine = Mine.selectBy(chunk=chunk, x=0, y=0)
        if mine.count():
            display[size - 1][size - 1]['count'] += 1
        #return display
        return display

    def update_display(self, display, max_action):
        #set non hidden mines
        actions = Action.select(
            SO.AND(Action.q.chunk == self, Action.q.id <= max_action))
        for action in actions:
            if action.action == 'DIG':
                display[action.y][action.x]['is_hidden'] = False
            else:
                display[action.y][
                    action.x]['flag'] = not display[action.y][action.x]['flag']
        return display