多数据库上下文项目结构

在现代软件开发中,随着项目规模的扩大,数据库架构往往变得复杂。为了更好地管理和维护数据库,经常需要将数据库架构分割成多个部分,每个部分由不同的团队负责。Entity Framework Core(EF Core) 提供了一种灵活的方式来实现这一点。本文将介绍如何在.NET Core项目中使用EF Core来构建包含多个数据库上下文的项目结构

创建MVC Web API项目

首先,需要创建一个MVC Web API Core项目,这个项目将用于后续的数据库上下文操作。项目命名为MultipleDbContexts。创建项目后,需要引用一系列NuGet包。引用完成后,项目的MultipleDbContexts.csproj文件如下所示:

<Project Sdk="Microsoft.NET.Sdk.Web"> <PropertyGroup> <TargetFramework>netcoreapp2.0</TargetFramework> </PropertyGroup> <ItemGroup> <Folder Include="wwwroot\" /> </ItemGroup> <ItemGroup> <PackageReference Include="Microsoft.AspNetCore.All" Version="2.0.6" /> <PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="2.0.2" /> <PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="2.0.2" /> <PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer.Design" Version="2.0.0-preview1-final" /> </ItemGroup> <ItemGroup> <DotNetCliToolReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Tools" Version="2.0.3" /> <DotNetCliToolReference Include="Microsoft.EntityFrameworkCore.Tools" Version="2.0.2" /> <DotNetCliToolReference Include="Microsoft.EntityFrameworkCore.Tools.DotNet" Version="2.0.2" /> </ItemGroup> </Project>

接下来,需要创建一个新的数据库。可以使用免费的SQL Server Express或SQL Server for Developers。创建一个新的空数据库,并命名为multipleDbContexts。

配置数据库连接字符串

为了使用数据库,需要在appsettings.json文件中添加连接字符串,如下所示:

{ "connectionString": "Server=host\\instance;Database=multipleDbContexts;Trusted_Connection=True;", "Logging": { // ... } }

创建数据库上下文项目

接下来,需要创建两个数据库上下文项目:MultipleDbContexts.Users和MultipleDbContexts.Products。这两个项目将分别负责不同的数据库表。

MultipleDbContexts.Users项目将包含UsersDbContext,它将引用Users.User和Users.Role表。首先,需要添加一个新的类库到解决方案中,并在入口项目中引用它。MultipleDbContexts.Users类库需要引用EF的NuGet包,添加完所有需要的包后,MultipleDbContexts.Users.csproj文件如下所示:

<Project Sdk="Microsoft.NET.Sdk"> <PropertyGroup> <TargetFramework>netcoreapp2.0</TargetFramework> </PropertyGroup> <ItemGroup> <PackageReference Include="Microsoft.AspNetCore.All" Version="2.0.6" /> <PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="2.0.2" /> <PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="2.0.2" /> <PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer.Design" Version="2.0.0-preview1-final" /> </ItemGroup> <ItemGroup> <DotNetCliToolReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Tools" Version="2.0.3" /> <DotNetCliToolReference Include="Microsoft.EntityFrameworkCore.Tools" Version="2.0.2" /> <DotNetCliToolReference Include="Microsoft.EntityFrameworkCore.Tools.DotNet" Version="2.0.2" /> </ItemGroup> </Project>

类似地,需要创建MultipleDbContexts.Products类库,并引用相同的NuGet包,然后从入口项目设置引用。

添加表模型

现在需要在MultipleDbContexts.Products和MultipleDbContexts.Users项目中添加表模型。

MultipleDbContexts.Products项目包含以下文件:

public class Products { public int Id { get; set; } [MaxLength(60)] public string Name { get; set; } [MaxLength(600)] public string ImageUrl { get; set; } } public class ProductsDbContext : DbContext { private readonly IConfiguration _config; public ProductsDbContext(IConfiguration config, DbContextOptions<ProductsDbContext> options) : base(options) { _config = config ?? throw new System.ArgumentNullException(nameof(config)); } public DbSet<Products> Products { get; set; } protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) { optionsBuilder.UseSqlServer(_config["connectionString"], options => { options.MigrationsHistoryTable("__UsersMigrationsHistory", "Products"); }); } }

MultipleDbContexts.Users项目包含以下文件:

public class RoleModel { [Key, MaxLength(60)] public string Key { get; set; } [Required, MaxLength(250)] public string Description { get; set; } } public class UserModel { [Key] public int Id { get; set; } [Required, MaxLength(50)] public string Email { get; set; } [StringLength(500)] public string AboutUser { get; set; } } public class UsersDbContext : DbContext { private readonly IConfiguration _config; public UsersDbContext(IConfiguration config, DbContextOptions<UsersDbContext> options) : base(options) { _config = config ?? throw new System.ArgumentNullException(nameof(config)); } public DbSet<UserModel> Users { get; set; } public DbSet<RoleModel> Roles { get; set; } protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder) { optionsBuilder.UseSqlServer(_config["connectionString"], options => { options.MigrationsHistoryTable("__UsersMigrationsHistory", "Users"); }); } }

配置服务容器

现在需要在Startup.cs文件中将数据库上下文添加到依赖注入(DI)容器中:

public void ConfigureServices(IServiceCollection services) { services.AddDbContext<UsersDbContext>(options => { options.UseSqlServer(Configuration["connectionString"], sqlServerOptions => { sqlServerOptions.MigrationsAssembly("MultipleDbContexts.Users"); }); }); services.AddDbContext<ProductsDbContext>(options => { options.UseSqlServer(Configuration["connectionString"], sqlServerOptions => { sqlServerOptions.MigrationsAssembly("MultipleDbContexts.Products"); }); }); services.AddMvc(); }

迁移数据库

为了使迁移工作,需要在使用dotnet ef命令时指定入口项目,这可以通过-s参数实现。还需要指定正在应用迁移的上下文,这可以通过--context参数实现。

dotnet ef migrations add products -s ../MultipleDbContexts/ --context ProductsDbContext dotnet ef database update -s ../MultipleDbContexts/ --context ProductsDbContext

对于MultipleDbContexts.Users项目,也需要执行类似的命令。

dotnet ef migrations add users -s ../MultipleDbContexts/ --context UsersDbContext dotnet ef database update -s ../MultipleDbContexts/ --context UsersDbContext

测试数据

现在数据库应该已经有了表。让添加一些测试数据,执行以下SQL语句:

INSERT INTO [Users].[User] (AboutUser, Email) VALUES ('About user', 'me@example.com') INSERT INTO [Users].[Role] ([Key], [Description]) VALUES ('Admin', 'Super Admin') INSERT INTO Products.Product (ImageUrl, Name) VALUES ('/products/teapot.png', 'Teapot')

确保一切正常工作

现在一切都应该就绪,编辑ValuesController以使用数据库上下文:

[Route("api/[controller]")] public class ValuesController : Controller { // GET api/values [HttpGet] public object Get([FromServices] UsersDbContext usersDb, [FromServices] ProductsDbContext productsDb) { return new { usersDb.Users, usersDb.Roles, productsDb.Products }; } } { "users": [ { "id": 1, "email": "me@example.com", "aboutUser": "About user" } ], "roles": [ { "key": "Admin", "description": "Super Admin" } ], "products": [ { "id": 1, "name": "Teapot", "imageUrl": "/products/teapot.png" } ] }
沪ICP备2024098111号-1
上海秋旦网络科技中心:上海市奉贤区金大公路8218号1幢 联系电话:17898875485