4

在 Oracle 数据库中,它的 ID 列定义为数字:

在此处输入图像描述

...以及表格的相应序列...:

在此处输入图像描述

如何确保 ID 列获得序列中的下一个值?

using (var db = new MyOracleDb()){
    var user= new User(){ first_name = 'Abe', last_name = 'Lincoln'};
    //Do something here with the sequence and set the ID?
    db.User.Add(user);
    db.SaveChanges();
}

我正在使用最新的 Oracle.ManagedDataAccess 和 Oracle.ManagedDataAccess.EntityFramework + EF6x。

4

4 回答 4

5

这不是 EF 问题,因为 oracle 中没有自动增量。您必须手动获取序列值,或者创建一个触发器来为您设置它。

更新

为了获得序列值,您有两个选择 - 创建一个返回值的存储过程 - 或创建一个调用原始 SQL 的 .Net 函数(实际上不必在函数中,它只是更简单)这个:

Database.SqlQuery<int>("SELECT SEQ_SOMESEQ.NEXTVAL FROM dual");

我个人对 oracle 函数和 EF 有很多问题,所以我会使用原始 sql。

于 2016-11-02T14:54:42.610 回答
3

我创建了一个界面:

public interface IHasSequencer
{
    decimal Id { get; set; }
    string GetSequenser();
}

然后在我的模型中实现它:

[Table("CLN_CLIENTS")]
public class ClnClient : IHasSequencer
{
    public string GetSequenser()
    {
        return "SEQ_CLN_CLIENTS";
    }

    [Key, Column("ID")]
    public decimal Id { get; set; }

    [Column("FIRSTNAME")]
    public string FirstName { get; set; }

    [Column("LASTNAME")]
    public string LastName { get; set; }

    [Column("MIDDLENAME")]
    public string MiidleName { get; set; }
}

并在我的 DbContext 中添加了一些MAGIC重写 SaveChanges() 方法:

 public override int SaveChanges()
    {
        var addedEntries = ChangeTracker.Entries().Where(e => e.State == EntityState.Added);

        foreach (DbEntityEntry entry in addedEntries)
        {
            if (entry.Entity is IHasSequencer)
            {
                var sequencerEntity = entry.Entity as IHasSequencer;
                var nextSeqVal = Database.SqlQuery<Int64>("SELECT " + sequencerEntity.GetSequenser() + ".NEXTVAL FROM DUAL").First();
                sequencerEntity.Id = nextSeqVal;
            }
        }
        return base.SaveChanges();
    }

而已!现在需要排序器 ID 值的模型必须实现小接口。

于 2020-03-19T09:38:20.120 回答
0

仅供参考,使用实体框架时,我遇到了独特约束的问题。对于未来的读者,如果您仍然遇到独特的约束问题。请确保将属性“StoreGeneratedPattern”更改为您的要求。

对我来说,我添加了 MAX(ID) + 1 并将 StoreGeneratedPattern 设置为 Identity 开始工作正常但一段时间后通过抛出相同的唯一约束问题破坏了整个程序,当我检查数据库时绝对不是这种情况。这是大多数开发人员没有注意的事情。

我已将其更改为“无”,因此我可以控制要添加的内容,而不是每隔几天就破坏它的实体框架。实体框架属性图片

于 2018-12-05T20:22:47.973 回答
0

如果您在 Oracle 方面创建触发器,则不必担心代码上的问题。它就像它确实有一个身份一样工作。

于 2019-02-07T06:15:29.680 回答