标签: dbcontext

同一服务器上的两个 DbContext 抛出:此平台不支持分布式事务

我无法弄清楚为什么 TransactionScope 正在启动分布式事务(未在 SQL Server 上配置)。我想改用本地事务,当两个数据库位于同一个 SQL Server 实例中时可以使用本地事务。我的代码有什么问题,我该如何修复它?我可以强制 Transaction Scope 首先尝试本地事务吗?

数据库

在此输入图像描述

应用程序设置.json

{
  "ConnectionStrings": {
    "DefaultConnection": "Data Source=DESKTOP;Initial Catalog=test;Integrated Security=True",
    "Test2Connection": "Data Source=DESKTOP;Initial Catalog=test2;Integrated Security=True"
  }
}
Run Code Online (Sandbox Code Playgroud)

startup.cs注册 TestContext 和 Test2Context

services.AddDbContext<TestContext>(options =>
 options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")));

services.AddDbContext<Test2Context>(options =>
 options.UseSqlServer(Configuration.GetConnectionString("Test2Connection")));

services.AddTransient<ICustomerRepository, CustomerRepository>();
services.AddTransient<IMaterialRepository, MaterialRepository>();

// This service inject TestContext and Test2Context
services.AddTransient<ICustomerService, CustomerService>();

services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
Run Code Online (Sandbox Code Playgroud)

使用 TestContext 的CustomerRepository

public class CustomerRepository : ICustomerRepository
    {
        private readonly TestContext _context;
        public CustomerRepository(TestContext context)
        {
            _context = context;
        }
        public Customer Retrieve(int id) …
Run Code Online (Sandbox Code Playgroud)

sql-server transactionscope distributed-transactions dbcontext entity-framework-core

4
推荐指数
1
解决办法
4872
查看次数

DBContext 中具有 DBContextFactory 的作用域服务无法从根提供程序解析

我想注册一个作用域ICurrentUserService,然后在 DbContext 中使用它来设置CreatedBy每个实体的属性。我希望它具有作用域,因为它使用 currentHttpContext从声明中获取用户 id,并且 HttpContext 根据定义具有作用域。

services.AddTransient<ICurrentUserService, CurrentUserService>();
Run Code Online (Sandbox Code Playgroud)

但是,当我尝试将其与 DbContextFactory 一起使用时,如下所示:

services.AddDbContextFactory<MyDbContext>(options =>
    options.UseSqlServer(config.ConnectionStrings.MSSQLConnection, x =>
        {
            x.MigrationsHistoryTable("...");
            x.MigrationsAssembly("...");
        }));

services.AddScoped<IMyDbContext>(provider => provider.GetRequiredService<IDbContextFactory<MyDbContext>>().CreateDbContext());
services.AddScoped<MyDbContext>(provider => provider.GetRequiredService<IDbContextFactory<MyDbContext>>().CreateDbContext());
Run Code Online (Sandbox Code Playgroud)

我收到错误

无法从根提供程序解析作用域服务“SomeNamespace.ICurrentUserService”。

我可以将其更改为 Transient,但这似乎是错误的,并且当我想模拟它并且每个类都会获得一个新实例时,这可能会成为稍后测试的问题。

我实际上不确定为什么 Scoped 在这里不起作用。DbContextFactory 已注册为 Singleton,但 Context 也被解析为 Scoped。

dependency-injection dbcontext entity-framework-core .net-core

4
推荐指数
1
解决办法
2891
查看次数

如何防止在 Entity Framework Core 6 中创建迁移并将其应用于指定的 dbContext?

我使用两个数据库上下文进行读取写入,指向相同的数据库模式。

ReadDbContextWriteDbContext有自己的读取写入模型。

由于这两种上下文配置中的关系、表名以及最后的数据库都是相同的,因此只有其中之一可以构建数据库。

有没有办法禁用为指定数据库上下文应用创建的迁移的能力?更进一步,是否有可能禁止迁移创建?

我尝试添加Database.SetInitializer<TContext>(null)到 DbContext 构造函数,但这似乎在 EF Core 6 中不起作用。

为了更好地理解,您可以查看下面的代码。

读取数据库上下文

internal sealed class ReadDbContext : DbContext
{
    public DbSet<UserReadModel> Users => Set<UserReadModel>();
    public DbSet<RoleReadModel> Roles => Set<RoleReadModel>();
    public DbSet<PermissionReadModel> Permissions => Set<PermissionReadModel>();

    public ReadDbContext(DbContextOptions<ReadDbContext> options) : base(options)
    {
    }

    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        modelBuilder.HasDefaultSchema("user-manager");

        var configuration = new ReadConfiguration();

        modelBuilder.ApplyConfiguration<UserReadModel>(configuration);
        modelBuilder.ApplyConfiguration<RoleReadModel>(configuration);
        modelBuilder.ApplyConfiguration<PermissionReadModel>(configuration);
    }
}
Run Code Online (Sandbox Code Playgroud)

写数据库上下文

internal sealed class WriteDbContext : DbContext
{ …
Run Code Online (Sandbox Code Playgroud)

c# dbcontext entity-framework-core entity-framework-migrations

4
推荐指数
1
解决办法
1534
查看次数

“无法访问已处置的上下文实例。” 从存储库调用方法时出错

我正在尝试从服务调用存储库中的方法。

上下文、存储库和服务都被定义为范围服务。

这是我首先调用的方法:

  public async void ReceiveWebhook(HttpContext httpContext)
    {
        // some unimportant checks here

        var productPurchaseRequest = new ProductPurchaseRequest
        {
            Amount = Convert.ToInt32(result?.Quantity),
            Timestamp = DateTime.Now,
            ProductType = productType,
            PaymentProviderOrderId = Convert.ToInt32(result?.OrderId),
            PaymentProviderProductId = Convert.ToInt32(result?.ProductId),
            PaymentProviderTransactionId = result?.TransactionId!,
            PaymentModel = PaymentModel.Subscription,
            PhoneNumber = result?.Passthrough!
            //todo: change payment model
        };
        var bought = await _productProvisioningRepository.PurchaseProduct(productPurchaseRequest);

    }
Run Code Online (Sandbox Code Playgroud)

这是方法:PurchaseProduct()在存储库中:

    public async Task<bool> PurchaseProduct(ProductPurchaseRequest productPurchaseRequest)
    {
        await using var transactionScope = await _context.Database.BeginTransactionAsync();
        
        var query = from u in _context.signumid_user
            where u.PhoneNumber …
Run Code Online (Sandbox Code Playgroud)

.net c# entity-framework dbcontext .net-core

4
推荐指数
1
解决办法
3564
查看次数

使用配置调用“AddDbContext”,但上下文类型仅声明无参数构造函数

我在开发项目时遇到错误。

我的代码如下..

错误信息 :

System.ArgumentException:使用配置调用“AddDbContext”,但上下文类型“NoteDbContext”仅声明无参数构造函数。这意味着传递给“AddDbContext”的配置将永远不会被使用。如果配置传递给“AddDbContext”,则“NoteDbContext”应该声明一个接受 DbContextOptions 的构造函数,并且必须将其传递给 DbContext 的基本构造函数。

数据库上下文

public class NoteDbContext : DbContext
{
    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        base.OnConfiguring(optionsBuilder);
        optionsBuilder.UseSqlServer(
            "Server=DESKTOP-BELVBNK\\SQLEXPRESS;" +
            "DataBase=NoteAppDB;Trusted_Connection=True;");
    }

    public DbSet<Entities.Note> Notes { get; set; }
}
Run Code Online (Sandbox Code Playgroud)

ASP.Net 项目 - 启动

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllersWithViews();
    services.AddDbContext<NoteDbContext>(options =>
        options.UseSqlServer(Configuration.GetConnectionString("NoteAppDB")));
}
Run Code Online (Sandbox Code Playgroud)

我搜索了这些错误的解决方案,但找不到。

asp.net dependency-injection dbcontext asp.net-core-mvc

4
推荐指数
1
解决办法
2924
查看次数

EF5 Code First标识列错误

我有类层次结构,如下所示:

class BaseType
{
  [Key]
  [DatabaseGeneratedAttribute(DatabaseGeneratedOption.Identity)]
  public int Id { get; set; }

  [DataType(DataType.Text)]
  [StringLength(100)]
  public string CreatedBy { get; set; }

  [DataType(DataType.DateTime)]
  public DateTime? CreatedDate { get; set; }
....
}

class Group : BaseType
{
  public string Name { get; set; }
}
Run Code Online (Sandbox Code Playgroud)

这是OnModelCreating方法的上下文:

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    modelBuilder.Entity<MCQGroup>()
        .HasKey(t0 => t0.Id)
        .Map(m => m.ToTable("groups"))
        .HasMany(t1 => t1.Sections)
        .WithMany(t2 => t2.Groups)
        .Map(m =>
          m.MapLeftKey("group_id")
          .MapRightKey("section_id")
          .ToTable("groups_to_sections"));
  ...........
  }
Run Code Online (Sandbox Code Playgroud)

我没有使用自动表格生成或迁移.相反,我有许多脚本来创建数据库(实际上,我在第一次运行时使用自动生成,之后脚本创建的表包括webdata_*表).这是由多个上下文引起的,在这种情况下,表自动生成存在许多问题.

这是SQL脚本:

-- Tables creation

CREATE TABLE [groups] …
Run Code Online (Sandbox Code Playgroud)

identity entity-framework dbcontext

3
推荐指数
1
解决办法
7693
查看次数

检索单个字段值时的FirstOrDefault()

这类事总是让我烦恼,所以我想我会从聪明的人那里寻找一种"更好的方式".

我有一个查询,我想返回单个字段的值,这是一个int值.

int thivalue = (from q in context.tablename    
    where q.ID == id
    orderby q.fieldname descending
    select q).FirstOrDefault().fieldname;
Run Code Online (Sandbox Code Playgroud)

问题是查询可能没有返回结果,在这种情况下我希望thisvalue为0.

当然,如果没有结果,我会尝试访问不存在的字段.所以我的选择似乎是a)返回行(我不需要),所以我可以测试null并从那里开始,或者b)在它周围包装一个try catch并将值设置为0,其中看起来有点笨重.

我想也许DefaultIfEmpty()会帮助我,但似乎不是我想要的只是单个值.

那么这样做的正确方法是什么?当我只需要一个单独的值时,我只是顽固地想要不返回整行吗?

附录:(如果有人有兴趣)

在他的回答中,berkeleybross给了我两个明显相同的选择.但只有第二个给了我正确的结果.OrderByDescending似乎有些不对劲.使用Glimpse我查看了每个查询.

    var nextSequence =  db.PaneContents
                       .Where(q=>q.QuizPaneID == quizPaneId)
                       .OrderByDescending(q=>q.Sequence)
                       .Select (q=>q.Sequence)
                       .DefaultIfEmpty()
                       .First();
Run Code Online (Sandbox Code Playgroud)

产生了这个查询:

SELECT 
CASE WHEN ([Limit1].[C1] IS NULL) THEN 0 ELSE [Limit1].[Sequence] END AS [C1]
FROM ( SELECT TOP (1) 
    [Project1].[Sequence] AS [Sequence], 
    [Project1].[C1] AS [C1]
    FROM  ( SELECT 1 AS X ) AS [SingleRowTable1]
    LEFT OUTER JOIN  (SELECT 
        [Extent1].[Sequence] AS [Sequence], …
Run Code Online (Sandbox Code Playgroud)

entity-framework-4 dbcontext asp.net-mvc-4

3
推荐指数
1
解决办法
1万
查看次数

有没有正确的方法来使用db上下文类?

我想知道在使用Web站点的上下文类连接到db时,性能和一般最佳实践的差异是什么.考虑这两种不同的方法时,最好的方法是什么:

public class Repository()
{
    Private Context context;

    public List<User> GetUsers()
    {
        return this.context.Users.ToList();
    }
Run Code Online (Sandbox Code Playgroud)

要么

public class Repository()
{        
    public List<User> GetUsers()
    {
        using (Context context = new context())
        {
            return context.Users.ToList(); 
        }
    }
 }
Run Code Online (Sandbox Code Playgroud)

如果它将结果作为a List或as 返回是否重要IEnumerable

c# entity-framework dbcontext

3
推荐指数
1
解决办法
1051
查看次数

为MVC控制器声明DbContext

在线查看一些MVC示例,我看到通常在控制器中DbContext变量被声明为私有成员变量(即全局)并且可以被所有方法访问.

但是,我最近遇到了一篇关于ASP.NET身份的文章,并且在控制器中注意到,DbContext是在每个方法中声明的(需要它).

这种方法有安全上的好处吗?或许限制安全对象的生命周期以获得更好的整体安全性?!?!

如果没有,那么我看到第一种方法更有效,其中数据库上下文在控制器加载时被实例化.

以下是我能找到的关于DbContext的全部内容,但没有什么可以真正回答我的问题.

DbContext声明 - 框架4.1 - MVC 3.0

MVC,DbContext和多线程

asp.net-mvc dbcontext

3
推荐指数
1
解决办法
2044
查看次数

将测试双打与DbEntityEntry和DbPropertyEntry一起使用

在MSDN中使用了EF6中新的测试双打.VS2013与Moq和nUnit.一切都很好,直到我不得不这样做:

var myFoo = context.Foos.Find(id);

然后:

myFoo.Name = "Bar";

然后 :

context.Entry(myFoo).Property("Name").IsModified = true;

此时是我收到错误的地方:

附加信息:无法为属性"名称"调用成员"IsModified",因为上下文中不存在"Foo"类型的实体.要向上下文添加实体,请调用DbSet的Add或Attach方法.

虽然,当我用AddWatch检查上下文中的'Foos'时,我可以在运行测试之前看到我添加的所有项目.所以他们在那里.

我从文章中创建了FakeDbSet(或TestDbSet).我将每个FakeDbSet放在构造函数中的FakeContext中,每个构造函数都被初始化.像这样:

Foos = new FakeDbSet<Foo>();

我的问题是,是否可以使用测试双精度场景使用FakeDbSet和FakeContext,以便从测试双重访问DbEntityEntry和DBPropertyEntry?谢谢!

testing moq dbcontext entity-framework-6

3
推荐指数
1
解决办法
1717
查看次数