Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/331.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/sql-server/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何用实体框架实现读写分离_C#_Sql Server_Entity Framework_Replication - Fatal编程技术网

C# 如何用实体框架实现读写分离

C# 如何用实体框架实现读写分离,c#,sql-server,entity-framework,replication,C#,Sql Server,Entity Framework,Replication,我有一个使用“主/从复制”的数据库设置。我可能有一个主人和(至少)一个奴隶ℕ 奴隶。为了简单起见,从这里开始,我将讨论一个主设备,一个从设备,因为确定使用哪个从设备包括一些与当前实际问题无关的业务逻辑 以下是安装示意图(带有ℕ 奴隶): 在应用程序(当前使用)中,我有以下简化代码: 抽象类BaseRepo { 私有只读字符串_readconn; 私有只读字符串_writecon; 公共BaseRepo(字符串读连接、字符串写连接) { _readconn=readConnection;//实际

我有一个使用“主/从复制”的数据库设置。我可能有一个主人和(至少)一个奴隶ℕ 奴隶。为了简单起见,从这里开始,我将讨论一个主设备,一个从设备,因为确定使用哪个从设备包括一些与当前实际问题无关的业务逻辑

以下是安装示意图(带有ℕ 奴隶):

在应用程序(当前使用)中,我有以下简化代码:

抽象类BaseRepo
{
私有只读字符串_readconn;
私有只读字符串_writecon;
公共BaseRepo(字符串读连接、字符串写连接)
{
_readconn=readConnection;//实际上是IEnumerable forℕ 奴隶
_writecon=writeConnection;
}
专用SqlConnection GetOpenConnection(字符串cnstring)
{
var c=新的SqlConnection(cnstring);
c、 Open();
返回c;
}
公共SqlConnection GetOpenReadConnection()
{
返回此.GetOpenConnection(_readconn);
//实际上,我们使用一些业务逻辑来确定要使用哪一个从机
}
公共SqlConnection GetOpenWriteConnection()
{
返回此.GetOpenConnection(\u writecon);
}
}
类CustomerRepo:BaseRepo
{
//…为了简洁起见,请省略。。。
//“读取”功能使用“读取”连接
公共IEnumerable列表客户()
{
使用(var c=this.GetOpenReadConnection())
{
返回c.Query(“按名称从客户订单中选择*);
}
}
//“写入”函数使用“写入”连接
公共作废更新客户(客户客户)
{
使用(var c=this.GetOpenWriteConnection())
{
c、 执行(“更新客户集名称=@name,其中id=@id”,cust);
}
}
}
我的问题是,;假设我想使用实体框架(“代码优先”,如果相关的话)而不是简洁;我如何才能最好地实现同样的理念;对“主”数据库执行插入/更新/删除,对从(或任何从)数据库执行选择。EF是否支持这种情况?我需要做些什么才能让它工作



其他信息:我已经在SQL Server级别使用“只读”和“只读”用户作为“最后一道防线”,以防止DAL中出现任何错误。我要寻找的是一种限制我的DAL的方法,以避免由于“不允许”操作而必须捕获SQL Server异常,以及在发现所需操作不允许之前必须首先转到(不正确的)SQL Server。我可以使用和现在一样的方法;在方法本身中实例化/使用正确的DbContext(上例中为listcustomers/updatecustomer)。我明白了。但这意味着我必须为每个“实体”上的每个“CRUD”操作创建一个“包装器”函数,这就是为什么我首先要从dapper迁移到EF;只需公开一个数据库集,并让EF处理changetracking/SQL查询等。现在,希望还能够找出每个操作要使用的连接字符串。

按照其他人的建议,默认情况下创建一个读/写上下文,然后创建一个从中继承的只读上下文。 如果您愿意,也要确保在部分类中实现接受另一个配置的构造函数

public partial class CustomerEntities : DbContext
{
    protected CustomerEntities(string nameOrConnectionString):base(nameOrConnectionString)
    {         
    }
}

public class ReadonlyCustomerEntities : CustomerEntities
{
    public ReadonlyCustomerEntities ()
        : base("name=ReadonlyCustomerEntities")
    {          
    }

    public override int SaveChanges()
    {
        // Throw if they try to call this
        throw new InvalidOperationException("This context is read-only.");
    }
}

我想最简单的方法是为每种情况提供不同的连接字符串。因此,解决方案不在实体框架级别上,而是在SQL本身级别上。另外,请继续使用整洁,godspeed@misha130你能澄清一下吗?你认为“情况类型”是什么?您将什么定义为“在SQL本身的杠杆上”?您确实需要在运行时更改连接字符串。实体框架确实提供了这种功能。这个问题会告诉你怎么做!您可以创建覆盖
SaveChanges
的上下文,当某些条件为false时,该上下文不调用
base.SaveChanges
。但我不知道你能保证这一切。可能基于数据库名称中的某些命名约定?