当前位置: 首页 > 面试题库 >

在sqlachemy中触发

耿玄裳
2023-03-14
问题内容

我有两个通过外键关联的表,它们在这里使用声明式映射

class Task(DeclarativeBase):
    __tablename__ = 'task'
    id = Column(Integer, primary_key=True)
    state = Column(Integer, default=0)
    obs_id = Column(Integer, ForeignKey('obs.id'), nullable=False)

class Obs(DeclarativeBase):
    __tablename__ = 'obs'
    id = Column(Integer, primary_key=True)
    state = Column(Integer, default=0)

因此,当obs.state更改为值2时,我想更新相关的task.state。目前,我正在手工操作(使用称为task的关系)

obs.state = 2
obs.task.state = 2

但是我更喜欢使用触发器来做到这一点。我检查了这在sqlite中有效

CREATE TRIGGER update_task_state UPDATE OF state ON obs
  BEGIN
    UPDATE task SET state = 2 WHERE (obs_id = old.id) and (new.state = 2);
  END;

但是我找不到如何在sqlalchemy中表达这一点。我已多次阅读插入更新默认值,但找不到方法。我不知道是否有可能。


问题答案:

您可以使用DDL类在数据库中创建触发器:

update_task_state = DDL('''\
CREATE TRIGGER update_task_state UPDATE OF state ON obs
  BEGIN
    UPDATE task SET state = 2 WHERE (obs_id = old.id) and (new.state = 2);
  END;''')
event.listen(Obs.__table__, 'after_create', update_task_state)

这是最可靠的方法:当不使用ORM时,它适用于批量更新,甚至适用于应用程序之外的更新。但是也有缺点:

  • 您必须注意触发器是否存在并且是最新的;
  • 它不是可移植的,因此如果您更改数据库,则必须重写它。
  • 除非您使它过期(例如,使用某些事件处理程序),否则SQLAlchemy不会更改已加载对象的新状态。

以下是不太可靠的解决方案(仅在ORM级别上进行更改时才起作用),但解决方案要简单得多:

from sqlalchemy.orm import validates

class Obs(DeclarativeBase):
    __tablename__ = 'obs'
    id = Column(Integer, primary_key=True)
    state = Column(Integer, default=0)
    @validates('state')
    def update_state(self, key, value):
        self.task.state = value
        return value

我的两个示例都以一种方式工作,即它们在obs更改时更新任务,但在任务更新时不触摸obs。您必须再添加一个触发器或事件处理程序,以支持双向更改传播。



 类似资料:
  • 万事俱备,只欠东风,因为NutIoc中的Bean是完全懒加载模式的,不获取就不生成,不初始化,所以,为了触发计划任务的加载,我们需要改动一下, 把原本的 // 获取quartz的Scheduler,这样就自动触发了计划任务的启动 ioc.get(Scheduler.class); 改成 // 获取NutQuartzCronJobFactory从而触

  • 我已经在我的网站上设置了GTM,我有一个在以下条件下触发的触发器 触发器的GTM条件 当我测试标签时,它不会启动。我检查了元素的值为 那么,当我使用regex或contains操作符时,为什么GTM不起作用呢。还有其他人面临过这个问题吗? 此页上几乎没有触发器(https://luminaryproperties.co.uk/venturing-into-your-first-off-plan/?

  • 问题内容: 我正在尝试在应用程序中使用AngularJS,并在某种程度上取得了成功。 我能够获取数据并将其显示给用户。我有一个按钮,我想通过该按钮发布DELETE请求。下面是我的代码。 这是获取信息并将其显示给用户的功能。 数据已获取并正确显示。 但是,单击删除按钮后,不会触发其中的代码。在GoogleChrome浏览器的开发人员工具中,我可以看到为代码生成了有效值,但未触发代码。从我尝试去掉花括

  • 问题内容: 我不知道如何使用JQuery,因此我需要一种仅可以使用JavaScript触发动画的方法。 当用户滚动页面时,我需要调用/触发CSS动画。 问题答案: 触发CSS动画的最简单方法是 添加或删除类 -如何使用纯Javascript执行此操作,您可以在此处阅读: 如果您确实使用jQuery(在基本用法上应该很容易学习),则只需使用/即可。 然后,您要做的就是设置到给定元素的过渡,如下所示:

  • 问题内容: 我有一个顾客。 当将新行添加到此客户表时,如果新行的(主键)已经在客户表中,则我想使用其他字段对现有(旧)行进行更新。()。 否则(如果不在表中)插入新行。我知道我可以使用触发器在mssql中做到这一点。有没有一种方法可以在mysql中做到这一点。 问题答案: MySQL没有触发器,但是它具有REPLACE和INSERT … ON DUPLICATE KEY UPDATE (请参阅文档

  • 请帮助我解决以下问题 我需要创建一个名为的触发器,每当“contact”表更新时就会触发该触发器。在更新联系人详细信息之后,这个触发器将把org_name和action插入到表中。受影响日志表中的操作名称为。 id整数org_name varchar2(255)street_address1 varchar2(255)street_address2 varchar2(255)城市varchar2(