【问题标题】:Strange Linq Cast Exception奇怪的 Linq 演员表异常
【发布时间】:2014-09-23 22:56:07
【问题描述】:

我遇到了一个非常奇怪的 Cast Exception。异常发生非常罕见。

这是代码:

    protected Guid GetWebsiteLanguage(Guid websiteId, int languageId)
    {
        Guid websiteLanguagesId = Guid.Empty;
        var websites = from item in DataContext.WebsiteLanguages
                       where item.WebsiteId == websiteId && item.LanguageId == languageId
                       select item.Id;

        if (websites.Count() != 1)
            throw new ArgumentException("Wrong channel parameters.");

        try
        {
            websiteLanguagesId = websites.First();
        }
        catch (Exception ex)
        {
            string errorMessage = websites.First() == null ? "websites.First() is null" : string.Concat("Invalid Guid ", websites.First().ToString());
            throw new Exception(string.Concat(ex.Message, " - Log: ", errorMessage, " - Variables: websiteId = ", websiteId.ToString(), " languageId = ", languageId));
        }

        return websiteLanguagesId;
    }

我得到的例外是:

指定的演员表无效。 - 日志:

无效的指导 ef058612-37db-4b02-aa13-5a528819a5e0

变量: websiteId = db725f45-70fa-4fd0-b344-55bbf17a5c15

语言 ID = 2057

这是 catch 异常的输出。如您所见,我们有一个 GUID,但他仍然给出了强制转换异常......

有时它会在这个函数的 Count() 上出错。然后这是堆栈跟踪:

System.Data.Linq.IExecuteResult 执行(System.Linq.Expressions.Expression,QueryInfo,System.Data.Linq.SqlClient.IObjectReaderFactory,System.Object[],System.Object[],System.Data.Linq。 SqlClient.ICompiledSubQuery[], System.Object)STACKTRACE: 在 System.Data.Linq.SqlClient.SqlProvider.Execute(Expression query, QueryInfo queryInfo, IObjectReaderFactory factory, Object[] parentArgs, Object[] userArgs, ICompiledSubQuery[] subQueries, Object最后一个结果) 在 System.Data.Linq.SqlClient.SqlProvider.ExecuteAll(表达式查询,QueryInfo[] queryInfos,IObjectReaderFactory 工厂,Object[] userArguments,ICompiledSubQuery[] subQueries) 在 System.Data.Linq.SqlClient.SqlProvider.System.Data.Linq.Provider.IProvider.Execute(表达式查询) 在 System.Data.Linq.DataQuery1.System.Linq.IQueryProvider.Execute[S](Expression expression) at System.Linq.Queryable.Count[TSource](IQueryable1 来源) 在 GetWebsiteLanguage(Guid websiteId, Int32 languageId)

当这种情况发生时,唯一的解决方案是进行 iis 应用程序池回收,它会再次运行。

有什么想法吗?

这就是我处理数据上下文的方式

    public MyDataContext DataContext
    {
        get
        {
            //Changed this to make this testable with unit tests
            if (HttpContext.Current != null)
            {
                if (!HttpContext.Current.Items.Contains(DataContextKey))
                    HttpContext.Current.Items.Add(DataContextKey, new MyDataContext(ConnectionString));
                return (MyDataContext)HttpContext.Current.Items[DataContextKey];
            }
            else
            {
                //When context is not available
                if (context == null)
                    context = new MyDataContext(ConnectionString);
                return context;
            }
        }
    }

【问题讨论】:

    标签: linq-to-sql guid .net


    【解决方案1】:

    嗯,我不确定是什么导致了问题。但我明白你无论如何总是只能有一个结果?所以你有没有考虑过根本不使用 Count 。我认为您在代码后半部分的 First() 也不能为空。

    (如果您可以有多个结果,请改用 FirstOrDefault)

    那么为什么不重构为使用 SingleOrDefault()。:

    var websites = (from item in DataContext.WebsiteLanguages 
                       where item.WebsiteId == websiteId && item.LanguageId == languageId 
                       select item.Id).SingleOrDefault(); 
    

    然后继续

    if (websites == null) 
            throw new ArgumentException("Wrong channel parameters."); 
    

    【讨论】:

    • 我不知道这是否解决了问题...因为异常有时会发生在计数上,但有时会在网站上发生。First();表达式..如果 First() 表达式出错,它非常奇怪,它在异常中有一个值。 (如示例所示)
    • 它是否可重现:换句话说,在应用程序池回收后尝试相同的 Guid 是否有效,或者它是否一致不工作?
    • 你是对的,在这种情况下它可能无法解决你的问题(尽管你可能会生成不同的 sql)。但是这样的重构仍然会提高你的性能
    • 应用程序池回收后,相同的 GUID 正在工作。一段时间后(有时是几个月,有时是几周),同样的问题再次出现。
    • 你如何处理你的数据上下文?
    【解决方案2】:

    我遇到了同样的问题,并通过在我的 DBML 中将 Server Data Type 属性设置为 uniqueidentifier 来解决它。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-10-02
      • 1970-01-01
      • 2011-08-19
      • 1970-01-01
      • 2019-11-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多