Plone/SQLAlchemy/orm如何重新映射/取消映射类?

2024-06-10 22:39:25 发布

您现在位置:Python中文网/ 问答频道 /正文

使用orm,我将类映射到Plone站点的表。但是,当我需要更改引擎正在使用的dsn时,我遇到了问题,我认为由于我的方法,我需要在重新初始化映射时重新映射一个类。你知道吗

class DBManager(Persistant):

    implements(IDBManager)

    def __init__(self):
        self._engine = None
        #...
    #...

    def engine(self):
        if self._engine is None:
            self.initEngine()
        return self._engine

    def initEngine(self):
        self._engine = sa.create_engine(self.dsn,convert_unicode=True,encoding='utf-8')

        metadata = sa.MetaData(self._engine)

        tables = []

        for k,v in self.tableNamePairs():
            tables[k] = sa.Table(v,metadata,autoload=True)

        for k,v in self.tableClassPairings():
            orm.mapper(v,tables[k])

    def reinit(self):
        if self._engine:
            self._engine.dispose() #right function?

        self.initEngine()

下面是一个表类的示例。你知道吗

class IMyType(model.Schema):

    form.hidden(My_ID='hidden')
    My_ID = schema.Int(title=u"My Type ID",
                   description=u"Primary Key",
               )

    title = schema.TextLine(title="My Type Title",
                        description = u"Title of MyType"
               )

class MyType(object):

    implements(IMyType)

    My_ID = None
    title = None

    def __init__(self,My_ID,title):
        self.My_ID = My_ID
        self.title = title

不幸的是,当从reinit调用initEngine时,它在尝试映射时会出错->;orm.mapper映射器(五、表[k])

我得到的错误是:

ArgumentError: Class '<class 'my.type.tables.my_type.MyType'>' already has a primary mapper defined.  Use non_primary=True to create a non primary Mapper.  clear_mappers() will remove *all* current mappers from all classes.

这个错误似乎意味着我需要取消类的映射。 很不幸,清除映射器不是一个解决方案。它不仅可以摆脱我不想摆脱的映射器,而且应该只在根据文档进行测试的少数情况下使用。你知道吗

停止并重新启动我正在处理的站点实例是我当前正在做的事情,但是我只想更改DSN而不必重新启动实例。你知道吗

我是否需要将映射器存储在一个列表中,并以某种方式将它们设置为“无”? 我试过类似的方法,但没什么效果。你知道吗

def __init__(self):
    #...
    self.mappers = []

def initEngine(self):
    #...
    for k,v in self.tableClassPairings():
        self.mappers.append(orm.mapper(v,tables[k]))

def reinit(self):
    for i in self.mappers:
        i = None
    #...
    self.initEngine()

是否可以停止或重新映射实例?你知道吗


Tags: inselfnoneidfortablestitlemy