0

1.我的存储库类中有这个方法

public class VariablesRepository : IVariablesRepository
    {
         readonly DBContextClass _context = DBContextClass.Current;
         public Variables Find(string name)
         {
           return _context.Variables.FirstOrDefault(c =>   c.Name.ToLower().Equals(name.ToLower())) ?? new Variables();
         }
    }

2.我也有这个静态类

public class Defaults {
        private static VariablesRepository _variablesRepository;
        static Defaults() {
            _variablesRepository = new VariablesRepository();
        }
    public class MOSScheduleTypes
    {
       private static int _tryValue;

       public static readonly int OneTime = int.TryParse(_variablesRepository.Find("MOSScheduleTypes.OneTime").Value, out _tryValue)
                                                       ? _tryValue
                                                       : 1;
    }
}

3.现在如果我在代码中的某个地方这样做:例如

if(someValue == Defaults.MOSScheduleTypes.OneTime) 
{ 
  //some code here.... 
}

我收到错误:操作无法完成,因为 DbContext 已被释放

4

3 回答 3

1

该错误是由正在处理的数据上下文引起的。由于您没有显示任何用于处理...任何内容的代码,这意味着在其他地方有一些代码正在处理相同的数据上下文。

请注意,数据上下文被设计为短暂存在的;看到您保留数据上下文以供以后使用是代码异味,尤其是在似乎长期存在的静态变量中。

而不是在需要时立即获取当前数据上下文。由于您不会将数据上下文存储为 的实例字段VariablesRepository,因此该方法也可以设为静态(它没有要使用的实例数据)。

public class VariablesRepository : IVariablesRepository
{
     public static Variables Find(string name)
     {
       return DBContextClass.Current.Variables.FirstOrDefault(c =>   c.Name.Equals(name, StringComparison.InvariantCultureIgnoreCase)) ?? new Variables();
     }
}

public class Defaults
{
    public class MOSScheduleTypes
    {
        private static int _tryValue;

        public static readonly int OneTime = int.TryParse(VariablesRepository.Find("MOSScheduleTypes.OneTime").Value, out _tryValue)
                                                        ? _tryValue
                                                        : 1;
    }
}
于 2013-05-07T17:22:23.957 回答
0

好的,通过使用原始 ado.net 代码解决了这个问题,所以我只是将 find 方法从实体框架 linq 代码更改为原始 ado.net 数据访问代码。错误不再出现,如果有人使用实体框架有更好的解决方案,请分享。重写了find方法,代码如下:

public Variables Find(string name)
        {
            var objVariable = new Variables();

            using (var conn = new SqlConnection(ConfigurationManager.ConnectionStrings["ConnectionStringValue"].ToString()))
            {
                conn.Open();

                var sql = @" select top 1 * 
                            from SomeTable 
                            where Column1 = @Name";

                try
                {
                    var cmd = new SqlCommand(sql, conn);
                    cmd.CommandType = CommandType.Text;

                    cmd.Parameters.Add("@Name", SqlDbType.NVarChar).Value = name;

                    SqlDataReader dr = cmd.ExecuteReader();
                    if (dr.HasRows)
                    {
                        if (dr.Read())
                        {
                            objVariable.Column1 = dr["Column1"].ToString();
                            objVariable.Column2 = dr["Column2"].ToString();
                        }
                    }

                }
                catch (Exception ex)
                {
                    throw new Exception(ex.Message);
                }
            }

            return objVariable;

        }
于 2013-05-10T08:42:20.627 回答
0

原因是您的 LINQ 查询被延迟,换句话说,它不在您的“VariablesRepository”中运行,而仅在调用代码中运行。所以DBContext在执行的时候就已经被处理掉了。您可以通过添加 .ToList() 来强制它立即执行,以便更改

return _context.Variables.FirstOrDefault(c =>   c.Name.ToLower().Equals(name.ToLower())) ?? new Variables();

return _context.Variables.ToList().FirstOrDefault(c =>   c.Name.ToLower().Equals(name.ToLower())) ?? new Variables();
于 2015-02-17T15:01:07.983 回答