在使用 Entity Framework 数据库优先在表上插入行之前,如何从 PL/SQL 执行触发器?

Posted

技术标签:

【中文标题】在使用 Entity Framework 数据库优先在表上插入行之前,如何从 PL/SQL 执行触发器?【英文标题】:How to execute a trigger from PL/SQL before inserting a row on a table with Entity Framework database-first? 【发布时间】:2017-04-24 14:02:58 【问题描述】:

我在 PL/SQL 中创建了一个触发器,当在表中插入一行之前触发,这通过 Oracle 序列增加值,然后作为主键插入到表中。

这是我的 PL/SQL 触发代码:

create or replace trigger FUT_SYS_USER_BE_I
before insert on FUT_SYS_USER referencing old as O new as N
for each row
  declare
  --local variables here
  begin
    if :N.SYS_USER_ID is null then
      :N.SYS_USER_ID := SYS_USER_SEQ.NEXTVAL;
    end if;
  end FUT_SYS_USER_BE_I;

但是这个触发器永远不会执行,因为当我插入一行时,主键 SYS_USER_ID 永远不会增加并保存零值。

这是我的 C# 代码:

using(DemoDBEntities db = new DemoDBEntities())

        FUT_SYS_USER SU = new FUT_SYS_USER();
        SU.LOGIN_NAME = user.LoginName;
        SU.PASSWORD_ENCRYPTED_TEXT = user.Password;
        SU.ROW_CREATED_SYSUSER_ID = user.SYSUserID > 0 ? user.SYSUserID : 1;
        SU.ROW_MODIFIED_SYSUSER_ID = user.SYSUserID > 0 ? user.SYSUserID : 1; 
        SU.ROW_CREATED_DATETIME = DateTime.Now;
        SU.ROW_MODIFIED_DATETIME = DateTime.Now;

        db.FUT_SYS_USER.Add(SU);
        db.SaveChanges();

关于如何解决此问题的任何想法?

【问题讨论】:

我对oracle不太熟悉,但是它的主键没有自动递增功能吗? 我的猜测是 SYS_USER_ID 被实体框架填充为 0,此时该值不再为空,并且触发器通过将 SYS_USER_ID 设置为序列的值。检查您是否可以将SYS_USER_ID 显式传递为NULL,以更改触发器中IF 语句的逻辑。是的,@Kurev,Oracle 提供了一个 Identity 列,即自 12.1.0.1 以来的自动增量功能 您必须先创建一个序列,然后使用 SYS_USER_SEQ.NEXTVAL 递增该值。 在 Oracle 12.1 之前,您可以像示例中那样在行级触发器中对其进行编码,这看起来不错,只是在同一个 PK 中允许两个不同的键序列是自找麻烦。跨度> 【参考方案1】:

您需要告诉 EF 这是由数据库填充的列。如果您打开了.edmx 设计器,请选择有问题的列,然后查看其属性。您正在寻找的是属性 StoreGeneratedPattern,它可以设置为“None”(默认值)、“Computed”或“Identity”。

我不确定哪一个可以在 Oracle 中工作,但在 SQL Server 中,对于 identity 列(在插入行时由 SQL Server 自动递增),我总是设置 StoreGeneratedPattern=Identity -在这种情况下,EF 不会为此列向数据库发送值,然后您的触发器应该会执行它的工作。

【讨论】:

【参考方案2】:

您需要在该列的 .edmx 模型属性中为键列 (SYS_USER_ID) 将 StoreGeneratedPattern 设置为 Identity。如果将来您从 .edmx 模型中删除表并重新创建,则需要再次设置。

【讨论】:

以上是关于在使用 Entity Framework 数据库优先在表上插入行之前,如何从 PL/SQL 执行触发器?的主要内容,如果未能解决你的问题,请参考以下文章

在Oracle中使用Entity Framework 6 CodeFirst

Entity Framework Code First

使用 Entity Framework

在服务器中使用 Entity Framework 的 Migration 更新数据库

实体未使用 Entity Framework 6 在数据库中更新

Entity Framework学习-实体框架中的code-first迁移