Python sqlalchemy查找表

Python sqlalchemy查找表,python,sqlalchemy,Python,Sqlalchemy,嗨,我有一张3NF格式的桌子 ftype_table = Table( 'FTYPE', Column('ftypeid', Integer, primary_key=True), Column('typename', String(50)), base.metadata, schema='TEMP') file_table = Table( 'FILE', base.metadata, Column('fileid', Integ

嗨,我有一张3NF格式的桌子

ftype_table = Table(
    'FTYPE',
    Column('ftypeid', Integer, primary_key=True),
    Column('typename', String(50)),
    base.metadata,
    schema='TEMP')
file_table = Table(
    'FILE',
    base.metadata,
    Column('fileid', Integer, primary_key=True),
    Column('datatypeid', Integer, ForeignKey(ftype_table.c.datatypeid)),
    Column('size', Integer),
    schema='TEMP')                                                                
和制图员

class File(object): pass
class FileType(object): pass
mapper(File, file_table, properties={'filetype': relation(FileType)})
mapper(FileType, file_table)
假设Ftype表包含1:TXT 2:AVI 3:PPT

如果我创建这样的文件对象,我将执行以下操作:

file=File()
file.size=10
file.filetype= FileType('PPT')
Session.save(file)
Session.flush()
文件表包含fileid:xxx,size:10,datatypeid:3

不幸的是,一个条目被添加到文件类型表中,这个id被传播到文件表中

有没有一种聪明的方法可以通过sqlalchemy实现上述功能,而无需对FileType表进行查询以查看条目是否存在


谢谢

只需创建文件类型对象的缓存,以便仅在第一次使用给定文件类型时才进行数据库查找:

class FileTypeCache(dict): def __missing__(self, key): obj = self[key] = Session.query(FileType).filter_by(typename=key).one() return obj filetype_cache = FileTypeCache() file=File() file.size=10 file.filetype= filetype_cache['PPT'] 类FileTypeCache(dict): def________;缺失(自身,钥匙): obj=self[key]=Session.query(FileType).filter_by(typename=key).one() 返回obj filetype_cache=FileTypeCache() file=file() file.size=10 file.filetype=filetype\u缓存['PPT']
应该行得通,模数输入。

UniqueObject配方是这里的标准答案:。其思想是使用
\uuuuu元类\uuuuu.call()
文件覆盖
文件的创建。\uuuuuu new\uuuuuuuuuo()
从DB或缓存返回已经存在的对象(如果对象还不存在,那么初始DB查找显然是不可避免的,除非使用围绕MySQL的REPLACE构建的东西)


编辑:由于我一直在研究使用配方,我重新编写了独特的对象配方,使其更具可移植性,并针对0.5/0.6进行了更新。

由于声明性的_base和zzzeek代码不适用于sqlalchemy 0.4,我 使用以下缓存,以便新对象在数据库中不存在时也保持唯一

class FileTypeCache(dict):
    def __missing__(self, key):
        try:
          obj = self[key] = Session.query(FileType).filter_by(typename=key).one()
          return obj
        except InvalidRequestError:
          return obj=self[key]= FileType(key)
          return obj
覆盖文件类型的eq

class FileType(object):
    def __init__(self, typename)
       self.typename=typename
    def __eq__(self):
        if isinstance(other, FileType):
            return self.typename == other.typename
        else:
            return False

这是正确的方向,但是1)
\uuuuuuuuuu缺少\uuuuuuuuu
不会用新值更新缓存,2)手动缓存的对象从会话中删除时应小心处理。哎呀,修复了缓存逻辑。谢谢你的注意。看起来很棒。不幸的是,我使用的是db2,一直使用sqlalchemy 0.4.0,有0.4.0版本吗