上下文附加方法异常

时间:2013-10-30 13:39:14

标签: c# mysql entity-framework

好的,我不确定我在这里错过了什么,所以就在这里。我正在使用Entity Framework填充MySQL数据库。我要么更新或添加新记录到数据库。首先,我搜索一条记录,如果它返回null,那么我知道我必须添加记录。如果搜索返回记录,则我对记录进行更改。

这是一个简短的总结。最初我将配置属性保持为默认值并在需要时运行SaveChanges(),但是我读到加速我的程序将它们变为false更好。当我把它关掉时我的问题出现了:

context.Configuration.AutoDetectChangesEnabled = false;
context.Configuration.ValidateOnSaveEnabled = false;

以下是我给您带来麻烦的代码。 运行Attach方法并设置Modified状态后,运行WFContext.SaveChanges()抛出System.Data.Entity.Infrastructure.DbUpdateException。我以为我做得对吗?显然不是......

 if (add)
 {
    WFContext.SecuritiesEntitySet.Add(security);
 }
 else
 {
    WFContext.SecuritiesEntitySet.Attach(security);
    WFContext.Entry(security).State = EntityState.Modified;
 }

我到底错过了什么?

以下是跟踪:

A first chance exception of type 'System.Data.Entity.Infrastructure.DbUpdateException' occurred in EntityFramework.dll
   at System.Data.Entity.Internal.InternalContext.SaveChanges()
   at System.Data.Entity.Internal.LazyInternalContext.SaveChanges()
   at System.Data.Entity.DbContext.SaveChanges()
   at MyContext.SaveChanges() in MyContext.cs:line 24
   at ContextConnection.RecreateWFContext() in ContextConnection.cs:line 26
   at AbstractRecords.CheckRecordCount() in AbstractRecords.cs:line 46
   at SecuritiesRecord.Parser() SecuritiesRecord.cs:line 74
An error occurred while updating the entries. See the inner exception for details.

您在跟踪及其后的内容中简要分析:

  • ContextConnection是一个静态类,用于管理与MyContext的连接。 RecreateWFContext处理当前上下文,然后再次初始化。
  • AbstractRecords提供了所有记录类都可以使用的方法的属性。
  • SecuritiesRecord.Parser解析字符串并加载安全对象中的所有属性。

这是SecurityInfo类,在上面的问题代码示例中由security实例化并引用。

public partial class SecurityInfo
    {
        public System.DateTime ImportDate { get; set; }
        public string CUSIP { get; set; }
        public string Symbol { get; set; }
        public string SecurityType { get; set; }
        public Nullable<System.DateTime> PriceDate { get; set; }
        public Nullable<decimal> PriceClose { get; set; }
        public Nullable<decimal> DividendRate { get; set; }
        public Nullable<System.DateTime> ExDate { get; set; }
        public Nullable<System.DateTime> PayableDate { get; set; }
        public string PaymentFrequency { get; set; }
        public Nullable<System.DateTime> FirstCallDate { get; set; }
        public Nullable<decimal> FirstCallRate { get; set; }
        public Nullable<System.DateTime> SecondCallDate { get; set; }
        public Nullable<decimal> SecondCallRate { get; set; }
        public Nullable<int> Industry { get; set; }
        public Nullable<decimal> EquityDividendRate { get; set; }
        public Nullable<System.DateTime> EquityRecordDate { get; set; }
        public Nullable<System.DateTime> EquityPayableDate { get; set; }
        public Nullable<System.DateTime> EquityExDividendDate { get; set; }
        public string EquitySplitRate { get; set; }
        public string OSISymbol { get; set; }
        public Nullable<System.DateTime> OSIExpirationDate { get; set; }
        public string OSIOptionType { get; set; }
        public Nullable<decimal> OSIStrikePrice { get; set; }
        public Nullable<decimal> OptionContractLotSize { get; set; }
        public Nullable<decimal> AnnualCouponRate { get; set; }
        public Nullable<System.DateTime> MaturityDate { get; set; }
        public Nullable<System.DateTime> PaymentDate { get; set; }
        public Nullable<decimal> GNMAFactor { get; set; }
        public string SPRating { get; set; }
        public string MoodyRating { get; set; }
    }

更新 我拿出来了:

context.Configuration.AutoDetectChangesEnabled = false;
context.Configuration.ValidateOnSaveEnabled = false;

我仍然得到同样的例外。我认为它必须在ContextConnection类中。这是它的样子:

public static class ContextConnection
{
    private static MyContext WFContext;

    public static MyContext GetWFContext()
    {
        return WFContext;
    }

    public static void NewWFContext()
    {
        WFContext = new MyContext();
        //WFContext.Configuration.AutoDetectChangesEnabled = false;
        //WFContext.Configuration.ValidateOnSaveEnabled = false;  
    }
    public static void RecreateWFContext()
    {
        WFContext.SaveChanges();
        DisposeWFContext();
        NewWFContext();
    }

    public static void DisposeWFContext()
    {
        WFContext.Dispose();
    }
}

当程序启动时,我调用ContextConnection.NewWFContext()并在try-catch块的finally部分中调用DisposeWFContext

只是好好衡量。这是AbstractRecords类中的方法,我在100个记录被更改时重新创建上下文:

protected void CheckRecordCount()
{
    RecordsChangedCount++;

    if (RecordsChangedCount == 100)
    {
        ContextConnection.RecreateWFContext();
        RecordsChangedCount = 0;
    }
}

非常感谢任何帮助!

感谢, 贾斯汀

1 个答案:

答案 0 :(得分:1)

我的解决方案

感谢大家帮助我。终于弄明白了昨天。这笔交易是对于某些表格,如证券表格,我检查记录是否已经存在,如果没有,那么我添加记录。如果记录确实存在,那么我更新记录。因此,如果我在每100条记录发生变化后等待将更改推送到数据库,并且我正在检查数据库是否添加了记录,那么您可以看到这可能是一个问题。所以基本上我试图添加两个具有相同唯一键的记录,只有当执行了SaveChanges时,才能确定程序是否存在重复记录并抛出异常。

所以在此期间。我不会在100条记录之后处理我的上下文,而是在我将文本文件导入MySQL数据库之后才会处理它。我将来必须编写一些可以处理添加/更新的逻辑,但现在只是这样做:

context.Configuration.AutoDetectChangesEnabled = false;
context.Configuration.ValidateOnSaveEnabled = false;

这样做可以减少导入天文数据的时间,从大约13分钟缩短到大约1分钟,即可获得9,000条记录。所以现在这已经足够了

感谢您的帮助!这一切都让我想出了这个问题。

贾斯汀

相关问题