经过版本更新,Mini API 的功能逐步完善,早期支持得不太好的 mini API 现在许多特性都可以用了,比如灰常重要的依赖注入。

咱们先来个相当简单的注入测试。来,定义一个服务类,为了偷懒,老周这里就不使用 接口 + 实现类 的方式了。

public class MyService : IDisposable
{
public MyService()
{
Console.WriteLine($"{nameof(MyService)} 隆重开业");
} public void Dispose()
{
Console.WriteLine($"{nameof(MyService)} 即将散伙");
} public void DoSomething()
{
Console.WriteLine("正忙着呢……别闹");
}
}

此服务类提供给外部调用的公共方法是 DoSomething。

接下来在容器中注册一下这个服务。

var builder = WebApplication.CreateBuilder(args);
builder.Services.AddScoped<MyService>();
var app = builder.Build();

毕竟,每个 Web API 的调用都是一次消息往返,所以我选择将服务类注册为范围级别的——请求上下文的范围内存活。

最简单好用的注入方式是让服务类的实例通过参数传入。

app.MapGet("/", (MyService sv) =>
{
// 调用服务类的公共方法
sv.DoSomething();
return "三日成精五日成魔七日成鬼";
});

Web API 测试可以不使用第三方工具,dotnet tool 集合有个叫 httprepl 的工具,可以方便使用。此工具需要安装,命令如下:

dotnet tool install -g microsoft.dotnet-httprepl

安装完成后,直接在命令终端输入 httprepl ,回车。就进入了会话模式。假设应用程序的地址是 https://localhost:7249,可以用 connect 命令建立连接。

connect https://localhost:7249

发起请求时,可以用 get、post、put 等命令,对应 HTTP 的请求方式。在上面的例子中,咱们用的是 MapGet 方法注册的 API,相对路径是 /。

get /

调用成功后会返回文本。

而且,MyService 服务也被调用了。

接下来咱们改一下代码,添加一个参数x。

app.MapGet("/", (int x, MyService sv) =>
{
sv.DoSomething();
return $"你提交的参数是:{x}";
});

在调用 httprepl 工具时,也可以直接将 URL 作为命令行参数传给它,能省去使用 connect 命令。

httprepl https://localhost:7249

然后调用一下 API 。

get /?x=150

得到的响应如下:

从上面的改动可以知道:来自依赖注入的参数能够被识别。当然,咱们也可以明确指定各个参数的来源。

app.MapGet("/", ([FromQuery]int x, [FromServices]MyService sv) =>
{
sv.DoSomething();
return $"你提交的参数是:{x}";
});

再次运行,再次发出请求。

get /?x=399

注入服务在 POST 请求中也可以和作不 body 的参数一起用,例如:

app.MapPost("/send", (Pet p, MyService sv) =>
{
// 调用服务
sv.DoSomething();
string s = string.Format("宠物ID:{0},大名叫{1}", p.ID, p.Name);
// 返回文本
return s;
});

参数 sv 是依赖注入自动赋值的,而参数 p 是 Pet 实例,由HTTP请求的 body 部分提供(默认识别 JSON 格式)。Pet 类定义如下:

public class Pet
{
public int ID { get; set; }
public string? Name { get; set; }
}

这个类结构很简单,两个成员,用来测试的,不用在意。

在 HttpRepl 工具中可以用 post /send -h content-type=application/json -c ... 的格式提交,-h 指定 HTTP 头,-c 指定 body 部分。但是,在命令行中用 -c 参数指定 body 很难写,而且老容易出错。最好的做法是配置一个文本编辑器。在编辑器中输入好内容,保存关闭文件,然后 httprepl 工具会自动提交。编辑的文件是临时文件,由工具生成,我们不用管它,只要在输入好内容后保存就行。

文本编辑器用啥都行,如记事本。当然,最好设置 VS Code。操作如下:

先进入 httprepl 会话:

httprepl

接着配置 editor.command.default 参数:

pref set editor.command.default "C:\Users\Bug-PC\tools\VSCode\Code.exe"

设置项名称后面是 VS Code 的路径。然后,它会提示你最好加上 -w 参数,于是输入执行:

pref set editor.command.default.arguments "-w"

-w 参数是可以等待 VS Code 响应——等它编辑完关闭后返回 httprepl 工具。

现在,在 httprepl 会话中用 connect 命令连接服务器。

connect https://localhost:7249

发送 POST 请求。

post /send -h content-type=application/json

注意 Content Type 是 JSON 数据。执行后会启动 VS Code,然后我们输入:

{
"id": 1234,
"name": "Jack"
}

完成后记得保存文件,并关闭 VS Code。关闭 VS Code 后回到 httprepl 会话,请求自动发送。

如果 mini-API 没有定义接收注入的参数,也可以用 HttpContext 来主动请求服务实例。请看下面代码:

app.MapGet("/", (HttpContext context) =>
{
// 主动请求服务
MyService sv = context.RequestServices.GetRequiredService<MyService>();
sv.DoSomething();
return "我在这里等了你上万年了!";
});

只要在所绑定的委托/方法中提供 HttpContext 类型的参数,就可以自动注入。随后在方法体中就可以直接引用。

这里要注意:此处咱们不能用 app.Services 去请求服务,因为它引用的是根容器(应用程序最开始创建的),不能访问生生命周期为 Scoped 的服务。

我们尝试把服务注册为单实例,看能不能用 app.Services 来获取。

var builder = WebApplication.CreateBuilder(args);
builder.Services.AddSingleton<MyService>();
var app = builder.Build(); app.MapGet("/", () =>
{
// 主动请求服务
MyService sv = app.Services.GetRequiredService<MyService>();
sv.DoSomething(); return "我在这里等了你上万年了!";
});

运行程序后,在 httprepl 中用 get / 命令测试通过。这说明,单例服务是支持通过 app.Services 获取的。不过,MyService 实例要等到应用程序结束时才会释放。

【ASP.NET Core】在 Mini-API 中注入服务的更多相关文章

  1. Asp.Net Core 5 REST API 使用 JWT 身份验证 - Step by Step

    翻译自 Mohamad Lawand 2021年1月22日的文章 <Asp Net Core 5 Rest API Authentication with JWT Step by Step> ...

  2. Asp.Net Core 5 REST API - Step by Step

    翻译自 Mohamad Lawand 2021年1月19日的文章 <Asp.Net Core 5 Rest API Step by Step> [1] 在本文中,我们将创建一个简单的 As ...

  3. 基础教程:视图中的ASP.NET Core 2.0 MVC依赖注入

    问题 如何在ASP.NET Core MVC Views中注入和使用服务. 解 更新 启动 类来为MVC添加服务和中间件. 添加一项服务 添加一个Controller,返回 ViewResult. 添 ...

  4. [ASP.NET Core 3框架揭秘] 依赖注入[4]:一个Mini版的依赖注入框架

    在前面的章节中,我们从纯理论的角度对依赖注入进行了深入论述,我们接下来会对.NET Core依赖注入框架进行单独介绍.为了让读者朋友能够更好地理解.NET Core依赖注入框架的设计与实现,我们按照类 ...

  5. [ASP.NET Core 3框架揭秘] 依赖注入:控制反转

    ASP.NET Core框架建立在一些核心的基础框架之上,这些基础框架包括依赖注入.文件系统.配置选项和诊断日志等.这些框架不仅仅是支撑ASP.NET Core框架的基础,我们在进行应用开发的时候同样 ...

  6. [ASP.NET Core 3框架揭秘] 依赖注入[10]:与第三方依赖注入框架的适配

    .NET Core具有一个承载(Hosting)系统,承载需要在后台长时间运行的服务,一个ASP.NET Core应用仅仅是该系统承载的一种服务而已.承载系统总是采用依赖注入的方式来消费它在服务承载过 ...

  7. 使用ASP.NET Core构建RESTful API的技术指南

    译者荐语:利用周末的时间,本人拜读了长沙.NET技术社区翻译的技术标准<微软RESTFul API指南>,打算按照步骤写一个完整的教程,后来无意中看到了这篇文章,与我要写的主题有不少相似之 ...

  8. ASP.NET Core技术研究-探秘依赖注入框架

    ASP.NET Core在底层内置了一个依赖注入框架,通过依赖注入的方式注册服务.提供服务.依赖注入不仅服务于ASP.NET Core自身,同时也是应用程序的服务提供者. 毫不夸张的说,ASP.NET ...

  9. Asp Net Core 5 REST API 使用 RefreshToken 刷新 JWT - Step by Step

    翻译自 Mohamad Lawand 2021年1月25日的文章 <Refresh JWT with Refresh Tokens in Asp Net Core 5 Rest API Step ...

  10. 温故知新,使用ASP.NET Core创建Web API,永远第一次

    ASP.NET Core简介 ASP.NET Core是一个跨平台的高性能开源框架,用于生成启用云且连接Internet的新式应用. 使用ASP.NET Core,您可以: 生成Web应用和服务.物联 ...

随机推荐

  1. NOIP模拟测试A3 赛后总结

    T1 谜之阶乘 可以发现题目要求我们求的实际上是若干个连续整数 \(c_i\) ,使得 \(\displaystyle \prod c_i = n\),通过打表可以发现这些连续整数的长度 \(d\) ...

  2. CKS 考试题整理 (08)-Pod指定ServiceAccount

    Context 您组织的安全策略包括: ServiceAccount 不得自动挂载 API 凭据 ServiceAccount 名称必须以 "-sa" 结尾 清单文件 /cks/s ...

  3. Dotnet9网站回归Blazor重构,访问速度飞快,交互也更便利了!

    大家好,我是沙漠尽头的狼. Dotnet9网站回归Blazor重构,访问速度确实飞快,同时用上Blazor的交互能力,站长也同步添加了几个在线工具,这篇文章分享下Blazor的重构过程,希望对大家网站 ...

  4. 从头学Java17-Stream API(一)

    Stream API Stream API 是按照map/filter/reduce方法处理内存中数据的最佳工具. 本系列中的教程包含从基本概念一直到collector设计和并行流. 在流上添加中继操 ...

  5. 使用Stable Diffusion生成艺术二维码

    在数字艺术的世界中,二维码已经从单纯的信息承载工具转变为可以展示艺术表达的媒介.这是通过使用Stable Diffusion的技术实现的,它可以将任何二维码转化为独特的艺术作品.接下来,我们将一步步教 ...

  6. 如何给Github上的开源项目提交PR?

    前言 对于一个热爱开源的程序员而言,学会给GitHub上的开源项目提交PR这是迈出开源的第一步.今天我们就来说说如何向GitHub的开源项目提交PR,当然你提交的PR可以是一个项目的需求迭代.也可以是 ...

  7. 华为P9黑屏的解决方案-更换屏幕

    解决办法(系统软件) 1.回退系统版本,b198或者b139固件. 2.升级版本,到最新版本.新版本使用时并没有发现这个问题. 解决方法(系统设置) 点开设置-电池-选择进入超级省电模式,然后退出超级 ...

  8. Nginx获取用户真实IP

    Nginx获取用户真实IP地址 本人在一次项目中,使用Nginx需要获取到用户IP,本来可以很常规的获取的,可现实往往不常规,项目是前后端分离的,部署时,前端使用了Nginx进行了代理并转发,后端也使 ...

  9. Qt 生成应用程序(二)软件多图标与文件操作

    目录 关联某种文件的默认打开方式 assoc ftype 解决方案 设置文件默认图标 应用软件添加多个图标 综合方法 嘿,各位Qt桌面应用开发的同学们(应该Qt大部分应用场景就是这个吧),上一篇文章中 ...

  10. 2023-07-31:用r、e、d三种字符,拼出一个回文子串数量等于x的字符串。 1 <= x <= 10^5。 来自百度。

    2023-07-31:用r.e.d三种字符,拼出一个回文子串数量等于x的字符串. 1 <= x <= 10^5. 来自百度. 答案2023-07-31: 大体步骤如下: 1.初始化一个字符 ...