def clauseQuote(s): if type(s) is type(""): if s.startswith('-'): desc = True s = s[1:] else: desc = False assert sqlbuilder.sqlIdentifier(s), "Strings in clauses are expected to be column identifiers. I got: %r" % s if select.sourceClass._SO_columnDict.has_key(s): s = select.sourceClass._SO_columnDict[s].dbName if desc: return sqlbuilder.DESC(sqlbuilder.SQLConstant(s)) else: return sqlbuilder.SQLConstant(s) else: return s
def __init__(self, name, soClass, dbName=None, default=NoDefault, foreignKey=None, alternateID=False, alternateMethodName=None, constraints=None, notNull=NoDefault, notNone=NoDefault, unique=NoDefault, sqlType=None, columnDef=None, validator=None, immutable=False, cascade=None, lazy=False, noCache=False, forceDBName=False, origName=None): # This isn't strictly true, since we *could* use backquotes or # " or something (database-specific) around column names, but # why would anyone *want* to use a name like that? # @@: I suppose we could actually add backquotes to the # dbName if we needed to... if not forceDBName: assert sqlbuilder.sqlIdentifier(name), 'Name must be SQL-safe (letters, numbers, underscores): %s (or use forceDBName=True)' \ % repr(name) assert name != 'id', 'The column name "id" is reserved for SQLObject use (and is implicitly created).' assert name, "You must provide a name for all columns" self.columnDef = columnDef self.immutable = immutable # cascade can be one of: # None: no constraint is generated # True: a CASCADE constraint is generated # False: a RESTRICT constraint is generated self.cascade = cascade if type(constraints) not in (type([]), type(())): constraints = [constraints] self.constraints = self.autoConstraints() + constraints self.notNone = False if notNull is not NoDefault: self.notNone = notNull assert notNone is NoDefault or \ (not notNone) == (not notNull), \ "The notNull and notNone arguments are aliases, and must not conflict. You gave notNull=%r, notNone=%r" % (notNull, notNone) elif notNone is not NoDefault: self.notNone = notNone if self.notNone: self.constraints = [consts.notNull] + self.constraints self.name = name self.soClass = None self._default = default self.customSQLType = sqlType self.foreignKey = foreignKey if self.foreignKey: #assert self.name.upper().endswith('ID'), "All foreign key columns must end with 'ID' (%s)" % repr(self.name) if not self.name.upper().endswith('ID'): self.foreignName = self.name self.name = self.name + "ID" else: self.foreignName = self.name[:-2] else: self.foreignName = None # if they don't give us a specific database name for # the column, we separate the mixedCase into mixed_case # and assume that. if dbName is None: self.dbName = soClass._style.pythonAttrToDBColumn(self.name) else: self.dbName = dbName # alternateID means that this is a unique column that # can be used to identify rows self.alternateID = alternateID if self.alternateID and alternateMethodName is None: self.alternateMethodName = 'by' + self.name[0].capitalize() + self.name[1:] else: self.alternateMethodName = alternateMethodName if unique is NoDefault: self.unique = alternateID else: self.unique = unique self.validator = validator self.noCache = noCache self.lazy = lazy # this is in case of ForeignKey, where we rename the column # and append an ID self.origName = origName or name
def __init__(self, name, soClass, creationOrder, dbName=None, default=NoDefault, foreignKey=None, alternateID=False, alternateMethodName=None, constraints=None, notNull=NoDefault, notNone=NoDefault, unique=NoDefault, sqlType=None, columnDef=None, validator=None, immutable=False, cascade=None, lazy=False, noCache=False, forceDBName=False, title=None, tags=[], origName=None, extra_vars=None): super(SOCol, self).__init__() # This isn't strictly true, since we *could* use backquotes or # " or something (database-specific) around column names, but # why would anyone *want* to use a name like that? # @@: I suppose we could actually add backquotes to the # dbName if we needed to... if not forceDBName: assert sqlbuilder.sqlIdentifier(name), 'Name must be SQL-safe (letters, numbers, underscores): %s (or use forceDBName=True)' \ % repr(name) assert name != 'id', 'The column name "id" is reserved for SQLObject use (and is implicitly created).' assert name, "You must provide a name for all columns" self.columnDef = columnDef self.creationOrder = creationOrder self.immutable = immutable # cascade can be one of: # None: no constraint is generated # True: a CASCADE constraint is generated # False: a RESTRICT constraint is generated # 'null': a SET NULL trigger is generated if isinstance(cascade, str): assert cascade == 'null', ( "The only string value allowed for cascade is 'null' (you gave: %r)" % cascade) self.cascade = cascade if type(constraints) not in (type([]), type(())): constraints = [constraints] self.constraints = self.autoConstraints() + constraints self.notNone = False if notNull is not NoDefault: self.notNone = notNull assert notNone is NoDefault or \ (not notNone) == (not notNull), \ "The notNull and notNone arguments are aliases, and must not conflict. You gave notNull=%r, notNone=%r" % (notNull, notNone) elif notNone is not NoDefault: self.notNone = notNone if self.notNone: self.constraints = [consts.notNull] + self.constraints self.name = name self.soClass = soClass self._default = default self.customSQLType = sqlType # deal with foreign keys self.foreignKey = foreignKey if self.foreignKey: if origName is not None: idname = soClass.sqlmeta.style.instanceAttrToIDAttr(origName) else: idname = soClass.sqlmeta.style.instanceAttrToIDAttr(name) if self.name != idname: self.foreignName = self.name self.name = idname else: self.foreignName = soClass.sqlmeta.style.instanceIDAttrToAttr(self.name) else: self.foreignName = None # if they don't give us a specific database name for # the column, we separate the mixedCase into mixed_case # and assume that. if dbName is None: self.dbName = soClass.sqlmeta.style.pythonAttrToDBColumn(self.name) else: self.dbName = dbName # alternateID means that this is a unique column that # can be used to identify rows self.alternateID = alternateID if self.alternateID and alternateMethodName is None: self.alternateMethodName = 'by' + self.name[0].capitalize() + self.name[1:] else: self.alternateMethodName = alternateMethodName if unique is NoDefault: self.unique = alternateID else: self.unique = unique _validators = self.createValidators() if _validators: if validator: _validators.append(validator) self.validator = SQLValidator.join(_validators[0], *_validators[1:]) else: self.validator = validator self.noCache = noCache self.lazy = lazy # this is in case of ForeignKey, where we rename the column # and append an ID self.origName = origName or name self.title = title self.tags = tags if extra_vars: for name, value in extra_vars.items(): setattr(self, name, value)