目录

1. Web Api 程序包引用

2. Web Api 的创建与Http类型的介绍

2.1ASP.Net Core Web API项目的创建

2.2 API接口的创建

2.3HttpGet和HttpPost类型的区别

3.接口权限设置

4.HttpGet方法和HttpPOst方法

5.前端中用HttpGet/Poset获取接口数据

6.EF框架——配置数据库链接字符串(即将数据库中的表导入项目中)

7.Web Api和EF结合的增删改查需注意的部分代码

8. 当web返回给窗体如下特殊字符串时,在web端的program 的main函数中加入以下代码:

1. Web Api 程序包引用

Entity Framework (EF) Core 是轻量化、可扩展、开源和跨平台版的常用 Entity Framework 数据访问技术。

EF Core 可用作对象关系映射程序 (O/RM),这可以实现以下两点:

  • 使 .NET 开发人员能够使用 .NET 对象处理数据库。
  • 无需再像通常那样编写大部分数据访问代码。

准备工作:

1.创建项目:打开Visual Studio2022,选择ASP.NET Core Web应用空项目基于.Net6 创建
2.安装Nuet程序包——项目——依赖项——管理NuGet程序包(版本等级尽量一样)

Microsoft.EntityFrameworkCore.SqlServer (适用于EF Core SQL Server 提供程序)
Microsoft.EntityFrameworkCore.Design(适用于EF Core .NET Core CLI 工具 )
Microsoft.EntityFrameworkCore.Tools(适用于 EF Core 的包管理器控制台工具)

Microsoft.EntityFrameworkCore.Design

2. Web Api 的创建与Http类型的介绍

2.1ASP.Net Core Web API项目的创建

1.通过vs建立一个ASP.Net Core Web API项目;(如果没有在搜索模板中找到它,就将模板栏滑动到最后,点击蓝色字体安装多个工具和功能),然后选中如图2所示2,再安装。

2.2 API接口的创建

生成项目后,解决方案会自动生成 Controllers 文件夹,里面存放的就是接口;

创建:

需要注意得是:命名方法一般为 名字+后缀 Controller;(不影响接口的名字,还是前部分样式) 最大字体为接口名称

创建方式:

1.创建 API控制器

点击文件夹右键添加 控制器 选则 通用API Api控制器,之后生成如下二代码,此时的接口还是不能用的;

2.需要声明接口[ApiController] 和一级接口路径[Route(“Test”)]

(声明接口是必须的,声明接口路径最好还是带上–可以起个和接口名一样的路径好用);

3.正式定义接口和接口类型;

在这里直介绍[HttpGet(“getUsers”)]和[HttpPost(“getUsers”)]两种接口类型 格式:接口类型+方法

注意:接口类型()中填写的是二级路径(自定义),效果如上白蓝色图 蓝色GET 是类型,Test一级路径getUser就是二级路径即接口类型中的路径 ;

完整代码:

 [ApiController] //声明是一个API接口[Route("Test")] //路由:api接口的路径public class TestController : Controller{/// /// 获取所有人员数据/// /// [HttpGet("getUsers")]public List GetUsers(){List list = UserManager.CreateUsers();return list;}}

2.3HttpGet和HttpPost类型的区别

1.传入参数不同

HttpGet:传入个体基本类型 如:(int,string 可传多个);

HttpPost:传入的是主题参数,当然也可以传入个体参数;

[HttpGet("getUserById")]public User GetUserById(int id){return UserManager.GetUserById(id);}//User 是一个内容[HttpPost("add")]public User Add(User user){//List users = new List();return UserManager.Add(user);}

2.HttpGet接口执行后 返回的 Request URL路径可以在通过浏览器打开,如下图:

执行的就是get 网址,和执行效果图 图一相对应

运行效果图

执行效果图

3.接口权限设置

1.创建一个类,并继承ActionFilterAttribute

2.重写方法:OnActionExecuting 和OnActionExecuted 方法

public class Intercept : ActionFilterAttribute{//在请求接口之前 public override void OnActionExecuting(ActionExecutingContext context){}//在请求接口之后 public override void OnActionExecuted(ActionExecutedContext context){ }}

3.在OnActionExecuting 方法中设置权限和Token

注:接口权限只有后半部分,通过id,和路径判断权限表中是否有对应的数据(看个人习惯,可以将存入表中数据当为赋予权限,当返回不为空就是有权限;也可以认为存入表中的数据是禁止权限,这样返回不为空,说明没有权限)

 public override void OnActionExecuting(ActionExecutingContext context){Debug.Write("拦截之前");//获取请求路径string path = context.HttpContext.Request.Path;Debug.Write("请求路径:" + path);//当登录是请求路径的时候不用拦截if (path != "/baseuser/login"){//----------------------------登录Token拦截-------------------------//此时获取前端参数,没有用到前端,单纯的接口,用此方法获取token值//object" />

4.上述设置中用到的封装方法GetIdByToken(),GetFilteData_ByApiPath()

 //写在登录接口中,将token和id存入UserData.AddToken(token, data.Id);//---------------------有关token的方法--------------------- /// // 存放所有登录的Token值,键:token值,值:人员id public static readonly Dictionary Tokens = new Dictionary(); // 添加一个Taken 值public static void AddToken(string token, int id){Tokens[token] = id;}public static int GetIdByToken(string token){//通过taken寻找对应的 id 人员if (Tokens.ContainsKey(token)){return Tokens[token];}else{return -1;}}//----------------------通过获取的接口地址查询权限表,看返回结果是否为空----------- //1.缓存的权限集合存放权限,所以需要有权限数据类,即权限包含了什么public static List filterDatas = new List();/// /// 3.通过id或者接口路径来获取权限/// /// 用户id/// 接口地址/// public static FilterData GetFilteData_ByApiPath(int userid, string apipath){string str = $"{userid}_{apipath}";//数据肯定是唯一的//判断是否符合权限信息FilterData data = filterDatas.FirstOrDefault(x => x.UserIdAndApiPath == str);if (data != null){return data;}//如果没有则需要产生,且存入缓存集合WebApiContext context = null;try{context = new WebApiContext();//从数据库中查照符合的BaseRoot? baseRoot = context.BaseRoots.FirstOrDefault(x => x.UserId == userid && x.ApiPath == apipath);if (baseRoot == null){return null;}//存在就存入缓存集合中data = new FilterData();data.Id = baseRoot.Id;data.UserId = baseRoot.UserId;data.ApiPath = baseRoot.ApiPath;data.FilterName = baseRoot.RootName;filterDatas.Add(data);return data;}catch (Exception ex){Debug.WriteLine($"查询数据失败:{ex.Message}");return null;}finally{context?.Dispose();}}public class FilterData{public int Id { get; set; }//idpublic int UserId { get; set; }//人员idpublic string ApiPath { get; set; }//操作接口路径public string? FilterName { get; set; }//权限名称public string UserIdAndApiPath{get => $"{UserId}_{ApiPath}";}}

4.HttpGet方法和HttpPOst方法

 public class ApiHttp{private static string Token { get; set; } = "123456";/// /// get请求方法/// /// 地址/// 参数/// 请求超时时间,以毫秒为单位/// public static string ApiGet(string path,string param,int timeout){//path:http://127.0.0.1:5000//param:id=1&name=张三//参数+路径:http://127.0.0.1:5000?id=1&name=张三string pathAndParam = path;if (!string.IsNullOrEmpty(param)){pathAndParam += "?" + param;}//创建一个HttpWebRequest对象,用来请求后台HttpWebRequest request = (HttpWebRequest)WebRequest.Create(pathAndParam);request.Method = "GET"; //请求方式:GET,POST,PUT, DELETErequest.Timeout = timeout; //请求超时时间request.ContentType = "application/json;UTF-8"; //设置类型5request.Headers.Add("token", Token); //请求头WebResponse response = request.GetResponse(); //相当于后台返回的对象Stream stream = response.GetResponseStream(); //response流StreamReader sr = new StreamReader(stream, Encoding.UTF8);string json = sr.ReadToEnd(); //读取接口返回的数据//释放对象response.Close();sr.Close();stream.Close();return json;}/// /// post请求方法/// /// 请求路径/// 参数/// 主题内容/// 请求超时时间,以毫秒位单位/// publicstatic string ApiPost(string path, string param, string body, int timeout = 5000){string pathAndParam = path;if (!string.IsNullOrEmpty(param)){pathAndParam += "?" + param;}//创建一个HttpWebRequest对象,用来请求后台HttpWebRequest request = (HttpWebRequest)WebRequest.Create(pathAndParam);request.Method = "POST";request.Timeout = timeout;request.ContentType = "application/json;UTF-8"; //设置类型; //设置类型request.Headers.Add("token", Token); //请求头//把主体内容添加到请求数据中if (!string.IsNullOrEmpty(body)){byte[] buffer = Encoding.UTF8.GetBytes(body);request.ContentLength = buffer.Length; //主体内容的字节长度Stream requestStream = request.GetRequestStream(); //存放请求的数据requestStream.Write(buffer, 0, buffer.Length); //把主体内容写到流中}WebResponse response = request.GetResponse();Stream responseStream = response.GetResponseStream();StreamReader sr = new StreamReader(responseStream, Encoding.UTF8);string json = sr.ReadToEnd();return json;}public class JsonData{public int Code { get; set; }public string Message { get; set; }//public List<Dictionary> Data { get; set; }//public List Data { get; set; }public T Data { get; set; }}}}

5.前端中用HttpGet/Poset获取接口数据

 //接口地址string HttpPath { get; set; } = "http://127.0.0.1:5000";//和图中没有对应,需要自己注意//get string json = Http.ApiHttp.ApiGet($"{HttpPath}/TAH/TAH", null, 50000);//Post string json = ApiPost($"{HttpPath}/baseuser/updata", null, $"{body}");

注意:对应的参数在4中有说明,方法中对应的地址形式实际是下图中对应的地址,要仔细了解方法中是如何形成接口对应的地址的

6.EF框架——配置数据库链接字符串(即将数据库中的表导入项目中)

视图 ——其他窗口——程序包管理器控制台 输入以下指令,将数据库中的表导入程序中

Scaffold-DbContext -Force "Server=192.168.218.26;Database=zy04_db4;uid=zy04;Password=123456;" Microsoft.EntityFrameworkCore.SqlServer -OutputDir Models -Context WebApiContext
  • server:数据库所在的主机ip地址
  • DataBase:数据库名称
  • uid:用户名
  • PassWorf:密码
  • Models:存放自动创建的实体类的文件夹(可以自己命名)
  • WebApiContext:直接操作数据库的类名(可以自己命名)
  • 有了WebApiContext类之后,不用再写连接数据库的逻辑了,只需要实例对应的数据表就可以操作如:
  • WebApiContext con=new WebAiContext();List list=con.BaseUsers.ToList();//查询所有

7.Web Api和EF结合的增删改查需注意的部分代码

1.通过***查找:FirstOrDefault

WebApiContext context = null;context = new WebApiContext();BaseUser user = context.BaseUsers.FirstOrDefault(x => x.Id == id);

2.增删改之后,需要保存

context.BaseRoles.Update(role);context.BaseRoles.Add(role);context.BaseRoles.Remove(role);context.SaveChanges();

8. 当web返回给窗体如下特殊字符串时,在web端的program 的main函数中加入以下代码:

亲测有用:

builder.Services.AddControllersWithViews().AddJsonOptions(options =>{options.JsonSerializerOptions.Encoder = JavaScriptEncoder.Create(UnicodeRanges.All);});