在基于.Net(Core)6框架开发的程序中,是通过Swagger中间件来实现前后端的分离和之间数据的相互交互操作的,即vue前端项目与相对应的.Net(Core)6后端项目分离实现核心是Swagger中间件,且该中间件的配置和定义实现都在.Net(Core)6后端项目中进行,本章讲述怎样通过Swagger中间件构建,能够让与相对应vue前端项目进行渲染显示的后端项目。
Vusal studio 构建支持Swagger中间件项目有两种方式:1、一种是直接通过“ASP.NET Core Web API”模板直接构建,该模板会直接包含Swagger中间件,2、另一种是通过“ASP.NET Core MVC(模型-视图-控制器)”模板,间接构建,由于该模板不接包含Swagger中间件,所以需要通过特定的配置定义以使项目包含Swagger中间件,本人为了程序的开发效率,通过第2种方式使项目包含Swagger中间件。如果下图所示:
在使用“ASP.NET Core MVC(模型-视图-控制器)”模板,间接构建项目时,由于该模板不接包含Swagger中间件,所以必须先通过Nugut引用Swagger中间件,使用构建项目包含Swagger中间件,如果下图所示:
1 数据交换类EFCoreContext
///
/// 【EFCore上下文】
///
///
/// 摘要:
/// 获取/设置学生实体的数据库设置实例,用于实现指定实体与数据库指定表的CURD操作。
///
public class EFCoreContext : DbContext
{
#region 拷贝构造方法
///
/// 【拷贝构造方法】
///
///
/// 摘要:
/// 基类构造通过该构造方法中的参数实例,连接到指定数据库(SQL Server)数据库软件中数据库。
///
public EFCoreContext(DbContextOptions
{
//如果(SQL Server)数据库软件中没有指定的数据库, 当通过Code First模式时,在第1次生成数据库时,则通过下1行语句结合数据库连接字符串,在(SQL Server)数据库软件中生成指定的数据库数据库、表、字段和约束规则。
Database.EnsureCreated();
/*
如果(SQL Server)数据库软件中没有指定的数据库, 当通过Code First模式时,在第1次生成数据库时,则也通过下行执行迁移和更新命令行的结合数据库连接字符串,在(SQL Server)数据库软件中生成指定的数据库数据库、表、字段和约束规则。
Add-Migration Initialize(Initialize:自动生成的迁移类名,这里特指:20220803125612_Initialize.cs):
Update-Database Initialize(通过自动生成的迁移类中的定义,自动在指定的数据库软件中生成指定的数据库、表、字段和约束规则)
*/
}
#endregion
#region 属性
///
/// 【角色数据库设置】
///
///
/// 摘要:
/// 获取/设置角色实体的数据库设置实例,用于实现当前程序【Web】.【领域】.【用户集】.【角色】实体与“[UserVue].[SysRole]”表之间的CURD的交互操作,并把这些数据存储到数据库设置实例中(内存)。
///
public DbSet
///
/// 【用户数据库设置】
///
///
/// 摘要:
/// 获取/设置用户实体的数据库设置实例,用于实现当前程序【Web】.【领域】.【用户集】.【用户】实体与“[UserVue].[SysUser]”表之间的CURD的交互操作,并把这些数据存储到数据库设置实例中(内存)。
///
public DbSet
///
/// 【菜单数据库设置】
///
///
/// 摘要:
/// 获取/设置菜单实体的数据库设置实例,用于实现当前程序【Web】.【领域】.【用户集】.【菜单】实体与“[UserVue].[SysMenu]”表之间的CURD的交互操作,并把这些数据存储到数据库设置实例中(内存)。
///
public DbSet
///
/// 【控件器行为方法数据库设置】
///
///
/// 摘要:
/// 获取/设置控件器行为方法实体的数据库设置实例,用于实现当前程序【Web】.【领域】.【用户集】.【控件器行为方法】实体与“[UserVue].[SysAction]”表之间的CURD的交互操作,并把这些数据存储到数据库设置实例中(内存)。
///
public DbSet
///
/// 【用户角色映射数据库设置】
///
///
/// 摘要:
/// 获取/设置用户角色映射实体的数据库设置实例,用于实现当前程序【Web】.【领域】.【用户集】.【用户角色映射】实体与“[UserVue].[SysUserRole]”表之间的CURD的交互操作,并把这些数据存储到数据库设置实例中(内存)。
///
public DbSet
///
/// 【角色菜单映射】
///
///
/// 摘要:
/// 获取/设置角色菜单映射实体的数据库设置实例,用于实现当前程序【Web】.【领域】.【用户集】.【角色菜单映射】实体与“[UserVue].[SysRoleMenu]”表之间的CURD的交互操作,并把这些数据存储到数据库设置实例中(内存)。
///
public DbSet
#endregion
#region 方法--私有/保护--覆写
/// name="builder">模型生成器实例,用于把当前程序中实体和属性所定义的约束规则,映射到数据库指定表及其字段上。
///
/// 【模型生成执行...】
///
///
/// 摘要:
/// 该方法把当前程序中实体和属性所定义的约束规则,映射到数据库指定表及其字段上。
///
protected override void OnModelCreating(ModelBuilder builder)
{
//角色表约束规则,映射定义。
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
//用户表约束规则,映射定义。
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
//菜单表约束规则,映射定义。
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
//通过该映射定义,去除菜单表与控制器行为方法表之间的级联约束规则。
builder.Entity
//控制器行为方法表约束规则,映射定义。
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
builder.Entity
//通过该映射定义,去除菜单表与控制器行为方法表之间的级联约束规则。
builder.Entity
//用户角色映射表约束规则,映射定义。
builder.Entity
builder.Entity
builder.Entity
builder.Entity
//角色菜单映射表约束规则,映射定义。
builder.Entity
builder.Entity
builder.Entity
builder.Entity
base.OnModelCreating(builder);
}
#endregion
}
2 SysRole
///
/// 【角色--类】
///
///
/// 摘要:
/// 通过该实体类及其属性成员,用于实现当前程序【Web】.【领域】.【用户集】.【角色】实体与“[UserVue].[SysRole]”表之间的CURD的交互操作,并把这些数据存储到数据库设置实例中(内存)。
///
public class SysRole
{
///
/// 【编号】
///
///
/// 摘要:
/// 获取/设置角色实体1个指定实例的整型编号值。
///
public int Id { get; set; }
///
/// 【角色名称】
///
///
/// 摘要:
/// 获取/设置1个指定角色的名称。
///
public string RoleName { get; set; }
///
/// 【描述】
///
///
/// 摘要:
/// 获取/设置1个指定角色的描述信息。
///
public string Description { get; set; }
///
/// 【排序】
///
///
/// 摘要:
/// 获取/设置1个指定角色实例在所有角色实例中的排序顺序整型值。
///
public int OrderSort { get; set; }
///
/// 【启用?】
///
///
/// 摘要:
/// 获取/设置1个值false(禁用)/true(默认值,启用),该值指示角色实体1个指定实例是否处于启用状态。
///
public bool Enabled { get; set; }
///
/// 【已经删除?】
///
///
/// 摘要:
/// 获取/设置1个值false(默认值,未逻辑删除)/true(已经处于逻辑删除状态),该值指示角色实体1个指定实例是否已经处于逻辑删除状态。
///
public bool? IsDeleted { get; set; }
///
/// 【创建者编号】
///
///
/// 摘要:
/// 获取/设置创建角色实体1个指定实例的创建者的整型编号值,即用户实体1个指定实例的整型编号值。
///
public int? CreateId { get; set; }
///
/// 【创建者名称】
///
///
/// 摘要:
/// 获取/设置创建角色实体1个指定实例的创建者的名称,即1个指定用户的名称。
///
public string CreateBy { get; set; }
///
/// 【创建时间】
///
///
/// 摘要:
/// 获取/设置角色实体1个指定实例第1次被持久化到角色表中的时间。
///
public DateTime? CreateTime { get; set; } = DateTime.Now;
///
/// 【修改者编号】
///
///
/// 摘要:
/// 获取/设置角色实体1个指定实例最后1次被修改后,修改者的整型编号值,即用户实体1个指定实例的整型编号值。
///
public int? ModifyId { get; set; }
///
/// 【修改者名称】
///
///
/// 摘要:
/// 获取/设建角色实体1个指定实例最后1次被修改后,修改者的名称,即1个指定用户的名称。
///
public string ModifyBy { get; set; }
///
/// 【修改时间】
///
///
/// 摘要:
/// 获取/设置角色实体1个指定实例最后1次被修改后,持久化到角色表中的时间。
///
public DateTime? ModifyTime { get; set; } = DateTime.Now;
}
3 模型类
3.1 PageModel
///
///
/// 【页模型】
///
///
/// 摘要:
/// 通过该类的属性成员对指定实体中的所有实例进行存储,这些实例数据为页面的渲染显示提供数据支撑。
///
public class PageModel<T>
{
#region 拷贝构造方法
///
/// 【拷贝构造方法】
///
///
/// 摘要:
/// 通过该拷贝构造方法为该类中的列表属性成员分配内存空间。
///
public PageModel(List
{
data = dataList;
}
#endregion
#region 属性
///
/// 【数据】
///
/// 摘要:
/// 获取/设置列表实例,该实例用于存储指定实体中的所有实例。
///
///
public List
#endregion
}
3.2 MessageModel
///
///
/// 【消息模型】
///
///
/// 摘要:
/// 通过该类的属性成员对指定实体中的所有实例进行存储,和指定控制器行方法的执行结果信息行存储,这些实例数据和执行结果信息行为页面的渲染显示提供数据支撑。
///
public class MessageModel<T>
{
#region 属性
///
/// 【 状态】
///
///
/// 摘要:
/// 获取/设置指定控制器行方法的执行结果状态整值,默认值:200(执行成功状态)。
///
public int status { get; set; } = 200;
///
/// 【成功?】
///
///
/// 摘要:
/// 获取/设置1个值false(默认值,执行失败)/true(执行成功),该值指示指定控制器行方法的执行结果状态。
///
public bool success { get; set; } = false;
///
/// 【信息】
///
///
/// 摘要:
/// 获取/设置指定控制器行方法的执行结果信息。
///
public string msg { get; set; } = "";
///
/// 【应答】
///
/// 摘要:
/// 获取/设置列表实例,该实例用于存储指定实体中的所有实例。
///
///
public T response { get; set; }
#endregion
}
4 通过定义配置使项目支持Swagger
4.1 通过Program.cs中的定义支持Swagger
4.1.1 “*.csproj”配置
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<TargetFramework>net6.0TargetFramework>
<Nullable>annotationsNullable>
<ImplicitUsings>enableImplicitUsings>
<GenerateDocumentationFile>trueGenerateDocumentationFile>
PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="6.0.9">
<PrivateAssets>allPrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitiveIncludeAssets>
PackageReference>
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.9" />
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.4.0" />
ItemGroup>
Project>
4.1.2 内置依赖注入定义支持Swagger
//通过AddSwaggerGen依赖注入中间方法,把Swagger中间件注入到.Net(Core)6框架默认容器中。
builder.Services.AddSwaggerGen(c =>
{
c.SwaggerDoc("v1", new OpenApiInfo { Title = "EmptyTemplate.Api", Version = "v1" });
//从"Web.xml"文件中获取指定的注释信。
var xmlFile = $"{Assembly.GetExecutingAssembly().GetName().Name}.xml";
var xmlPath = Path.Combine(AppContext.BaseDirectory, xmlFile);
//把控件器行为方法中的注视信息加载到"Swagger/index.html"页面中的控件器行为方法进行渲染显示。
//注意:如果不在“*.csproj”文件中启用“
c.IncludeXmlComments(xmlPath, true);
});
4.1.3 内置管道集成支持Swagger
//通过UseSwagger、UseSwaggerUI管道中间方法,把Swagger中间件集成到.Net(Core)6框架中,以使用当前程序能够在前台页面能够以“Swagger”方式进行后台的相关操作(例如:“/Swagger/index.html”)。
app.UseSwagger();
app.UseSwaggerUI();
5 API控制器与控制器行为方法(RoleController)定义
///
/// 角色管理
///
[Route("[controller]/[action]")]
[ApiController]
public class RoleController : Controller
{
#region 拷贝构造方法
///
/// 【EFCore上下文实例】
///
///
/// 摘要:
/// 声明角色实体的数据库设置实例, 该实例通过EFCore数据交换中间件实现当前程序与指定数据库之间的CURD操作。
///
private readonly EFCoreContext _context;
/// name="context">模型生成器实例,用于把当前程序中实体和属性所定义的约束规则,映射到数据库指定表及其字段上。
///
/// 【拷贝构造方法】
///
///
/// 摘要:
/// 基类构造通过该构造方法中的参数实例,连接到指定数据库(SQL Server)数据库软件中数据库。
///
public RoleController(EFCoreContext context)
{
_context = context;
}
#endregion
#region CRUD操作
///
/// 【获取所有角色】
///
///
/// 摘要:
/// 以异步方式,通过该方法获取角色表中的所有角色实例,并把所有角色实例及其操作结果存储到消息模型实例中,为页面的渲染显示提供数据支撑。
///
///
/// 消息模型实例,为页面的渲染显示提供数据支撑。
///
[HttpGet]
public async Task
{
var data = await _context.SysRoleDbSet.ToListAsync();
var d1 = new PageModel
return new MessageModel
{
msg = "获取成功",
success = true,
response = d1,
};
}
///
/// 【添加角色】
///
///
/// 摘要:
/// 以异步方式,通过该方法获把1个指定的角色实例持久化到数据库的角色表中,并把该角色实例及其操作结果存储到消息模型实例中,以为页面的渲染显示提供数据支撑。
///
///
/// 消息模型实例,为页面的渲染显示提供数据支撑。
///
[HttpPost]
public async Task
{
await _context.SysRoleDbSet.AddRangeAsync(role);
await _context.SaveChangesAsync();
var m = role;
var data = new MessageModel<string>();
data.success = m.Id > 0;
if (data.success)
{
data.response = m.Id.ToString();
data.msg = "添加成功";
}
return data;
}
#endregion
}
注意:必须在控制器类上定义标记: [Route("[controller]/[action]")]、[ApiController],能够实现前端项目对后端项目的交互操作,同时控制器类行为方法返回的是的指定模型类的实例数据,而非IactionResult实例。
6配置与定义跨域(Cors)操作
跨域(Cors)操作的目的是:后端“appsettings.json”文件中配置的域名及其端口集中,是否包含有vue前端项目的访问域名及其端口,如果配置域名及其端口集中,不包含后端项目的访问域名及其端口,且在“Program.cs” 文件进行了限定定义,那么vue前端是不能与.Net(Core)6后端项目进行交互操作的。
6.1 在appsettings.json中配置跨域(Cors)交互限定
// 跨域(Cors)配置的域名及其端口集,该端口集中是否包含有vue前端项目的访问域名及其端口,如果配置域名及其端口集中,不包含后端项目的访问域名及其端口,
//且在“Program.cs” 文件进行了限定定义,那么vue前端是不能与.Net(Core)6后端项目进行交互操作的。
"Cors": {
"PolicyName": "CorsIpAccess", //vue前端是不能与.Net(Core)6后端项目进行交互操作的策略名称。
"EnableAllIPs": false, //当为true时,开放所有IP均可访问。
//跨域(Cors)配置的域名及其端口集,用来限定vue前端的访问及其交互操作。
"IPs": "http://localhost:8080,http://localhost:8081,,http://localhost:8082,,http://localhost:8083,http://localhost:8021"
},
6.2 在Program.cs中定义跨域(Cors)交互限定
6.2.1 内置依赖注入定义跨域(Cors)交互限定
//通过AddCors依赖注入中间方法,把Cors(跨域)中间件注入到.Net(Core)6框架默认容器中。
//Cors(跨域)操作是如果“appsettings.json”文件中配置的所有域名中,至少有1个与“vue”前台项目相匹配域名时,则“vue”前台项目就从当前后台项目中获取相关数据,从而实现页面的渲染显示。
builder.Services.AddCors(c =>
{
//限定“appsettings.json”文件中配置的所有域名中,至少有1个与“vue”前台项目相匹配域名,才能上“vue”前台项目就从当前后台项目中获取相关数据,从而实现页面的渲染显示。
if (!Convert.ToBoolean(builder.Configuration["Cors:EnableAllIPs"]))
{
c.AddPolicy(builder.Configuration["Cors:PolicyName"],
policy =>
{
policy
.WithOrigins(builder.Configuration["Cors:IPs"].Split(','))
.AllowAnyHeader()
.AllowAnyMethod();
});
}
else
{
//不做限定,“vue”前台项目能够直接从当前后台项目中获取相关数据,从而实现页面的渲染显示
c.AddPolicy(builder.Configuration["Cors:PolicyName"],
policy =>
{
policy
.SetIsOriginAllowed((host) => true)
.AllowAnyMethod()
.AllowAnyHeader()
.AllowCredentials();
});
}
});
6.2.2 内置管道集成支持跨域(Cors)交互限定
app.UseCors(app.Configuration["Cors:PolicyName"]);
7 发布与部署
.Net(Core)6后端项目必须在最后进行发布部署操作,并通过IIS配置相应的网站后,才能实现vue前端项目与后端项目中的数据进行交互操作,并在vue前端项目中进行渲染显示。关于后端项目必须在最后进行发布部署操作,并通过IIS配置相应的网站,请查看本人的文章:“https://blog.csdn.net/zhoujian_911/article/details/126864660”。
对以上功能更为具体实现和注释见:22-09-22-02_UserVue(Vue服务器(后)端Swagger定义实现与发布部署)