Changeset 796 for trunk/pgdb.py


Ignore:
Timestamp:
Jan 28, 2016, 4:25:36 PM (4 years ago)
Author:
cito
Message:

Enrich type_code strings in the DB API 2

The type codes now carry e.g. the information whether a type is a record.
This allows to provide a RECORD type object that compares equal to all
kinds of records, similar to the already existing ARRAY type object.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/pgdb.py

    r792 r796  
    159159
    160160
    161 TypeInfo = namedtuple('TypeInfo',
    162     ['oid', 'name', 'len', 'type', 'category', 'delim', 'relid'])
     161class TypeCode(str):
     162    """Class representing the type_code used by the DB-API 2.0.
     163
     164    TypeCode objects are strings equal to the PostgreSQL type name,
     165    but carry some additional information.
     166    """
     167
     168    @classmethod
     169    def create(cls, oid, name, len, type, category, delim, relid):
     170        """Create a type code for a PostgreSQL data type."""
     171        self = cls(name)
     172        self.oid = oid
     173        self.len = len
     174        self.type = type
     175        self.category = category
     176        self.delim = delim
     177        self.relid = relid
     178        return self
    163179
    164180ColumnInfo = namedtuple('ColumnInfo', ['name', 'type'])
     
    168184    """Cache for database types.
    169185
    170     This cache maps type OIDs and names to TypeInfo tuples containing
     186    This cache maps type OIDs and names to TypeCode strings containing
    171187    important information on the associated database type.
    172188    """
     
    196212        if not res:
    197213            raise KeyError('Type %s could not be found' % key)
    198         res = list(res[0])
    199         res[0] = int(res[0])
    200         res[2] = int(res[2])
    201         res[6] = int(res[6])
    202         res = TypeInfo(*res)
    203         self[res.oid] = self[res.name] = res
    204         return res
     214        res = res[0]
     215        type_code = TypeCode.create(int(res[0]), res[1],
     216            int(res[2]), res[3], res[4], res[5], int(res[6]))
     217        self[type_code.oid] = self[str(type_code)] = type_code
     218        return type_code
    205219
    206220    def get(self, key, default=None):
     
    255269        if isinstance(key, int):
    256270            try:
    257                 typ = self[key].name
     271                typ = self[key]
    258272            except KeyError:
    259273                return None
     
    368382        """Make the description tuple for the given field info."""
    369383        name, typ, size, mod = info[1:]
    370         type_info = self.type_cache[typ]
    371         type_code = type_info.name
     384        type_code = self.type_cache[typ]
    372385        if mod > 0:
    373386            mod -= 4
     
    10431056
    10441057
     1058class RecordType:
     1059    """Type class for PostgreSQL record types."""
     1060
     1061    def __eq__(self, other):
     1062        if isinstance(other, TypeCode):
     1063            return other.type == 'c'
     1064        elif isinstance(other, basestring):
     1065            return other == 'record'
     1066        else:
     1067            return isinstance(other, RecordType)
     1068
     1069    def __ne__(self, other):
     1070        if isinstance(other, TypeCode):
     1071            return other.type != 'c'
     1072        elif isinstance(other, basestring):
     1073            return other != 'record'
     1074        else:
     1075            return not isinstance(other, RecordType)
     1076
     1077
    10451078# Mandatory type objects defined by DB-API 2 specs:
    10461079
     
    10721105ARRAY = ArrayType()
    10731106
     1107# Type object for records (encompassing all composite types):
     1108
     1109RECORD = RecordType()
     1110
    10741111
    10751112# Mandatory type helpers defined by DB-API 2 specs:
Note: See TracChangeset for help on using the changeset viewer.