.NET 8 微服务从0到1实战指南
项目概述
本教程完整演示了如何使用 .NET 8 从零搭建一个微服务架构,包含 API 网关、认证服务、产品服务和订单服务四个核心组件。
架构设计
服务组成
| 服务名称 | 端口 | 技术栈 | 主要职责 |
|---|---|---|---|
| API 网关 | 5001 | Ocelot | 统一入口、路由转发、集中认证 |
| 认证服务 | 5002 | JWT | 用户认证、Token 颁发 |
| 订单服务 | 5003 | .NET 8 WebAPI | 订单业务逻辑 |
| 产品服务 | 5004 | .NET 8 WebAPI | 产品信息管理 |
架构流程图
客户端 → API网关(5001) → 路由分发 ├→ 认证服务(5002): /gateway/auth/* ├→ 产品服务(5004): /gateway/products/* └→ 订单服务(5003): /gateway/orders/*
详细实现步骤
第一步:环境准备与项目创建
1. 创建解决方案
dotnet new sln -n MicroservicesDemo
cd MicroservicesDemo
# 创建四个微服务项目
dotnet new webapi -n APIGateway
dotnet new webapi -n AuthService
dotnet new webapi -n ProductService
dotnet new webapi -n OrderService
# 添加到解决方案
dotnet sln add APIGateway/APIGateway.csproj
dotnet sln add AuthService/AuthService.csproj
dotnet sln add ProductService/ProductService.csproj
dotnet sln add OrderService/OrderService.csproj
2. 配置各服务端口
修改每个项目的 Properties/launchSettings.json:
- APIGateway: 5001
- AuthService: 5002
- OrderService: 5003
- ProductService: 5004
第二步:配置 API 网关 (Ocelot)
1. 安装 Ocelot
dotnet add APIGateway package Ocelot
json
{
"Routes": [
{
"DownstreamPathTemplate": "/api/Product",
"DownstreamScheme": "http",
"DownstreamHostAndPorts": [
{
"Host": "localhost",
"Port": 5004
}
],
"UpstreamPathTemplate": "/gateway/products",
"UpstreamHttpMethod": [ "GET", "POST" ],
"AuthenticationOptions": {
"AuthenticationProviderKey": "Bearer"
}
},
{
"DownstreamPathTemplate": "/api/Order",
"DownstreamScheme": "http",
"DownstreamHostAndPorts": [
{
"Host": "localhost",
"Port": 5003
}
],
"UpstreamPathTemplate": "/gateway/orders",
"UpstreamHttpMethod": [ "GET", "POST" ],
"AuthenticationOptions": {
"AuthenticationProviderKey": "Bearer"
}
},
{
"DownstreamPathTemplate": "/api/Auth/login",
"DownstreamScheme": "http",
"DownstreamHostAndPorts": [
{
"Host": "localhost",
"Port": 5002
}
],
"UpstreamPathTemplate": "/gateway/auth/login",
"UpstreamHttpMethod": [ "POST" ]
}
],
"GlobalConfiguration": {
"BaseUrl": "http://localhost:5001"
}
}
3. 配置网关程序 Program.cs
csharp
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddControllers();
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
// 加载 Ocelot 配置
builder.Configuration.AddJsonFile("ocelot.json", optional: false, reloadOnChange: true);
// 配置 JWT 认证
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddJwtBearer("Bearer", options =>
{
options.RequireHttpsMetadata = false;
options.TokenValidationParameters = new TokenValidationParameters
{
ValidateIssuer = true,
ValidateAudience = true,
ValidateLifetime = true,
ValidateIssuerSigningKey = true,
ValidIssuer = "AuthService",
ValidAudience = "MicroservicesDemo",
IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes("ThisIsMySuperSecretKeyForJWTTokenGenerationInMicroservicesDemo2024!"))
};
});
builder.Services.AddAuthorization();
builder.Services.AddOcelot();
var app = builder.Build();
if (app.Environment.IsDevelopment())
{
app.UseSwagger();
app.UseSwaggerUI();
}
app.UseAuthentication();
app.UseAuthorization();
// Ocelot 必须在最后
await app.UseOcelot();
app.Run();
第三步:实现认证服务
1. 安装 JWT 包
bash
dotnet add AuthService package Microsoft.AspNetCore.Authentication.JwtBearer
dotnet add AuthService package System.IdentityModel.Tokens.Jwt
2. 配置认证服务 Program.cs
csharp
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddControllers();
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
// 配置 JWT 认证
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddJwtBearer(options =>
{
options.RequireHttpsMetadata = false;
options.TokenValidationParameters = new TokenValidationParameters
{
ValidateIssuer = true,
ValidateAudience = true,
ValidateLifetime = true,
ValidateIssuerSigningKey = true,
ValidIssuer = "AuthService",
ValidAudience = "MicroservicesDemo",
IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes("YourSecretKey"))
};
});
builder.Services.AddAuthorization();
var app = builder.Build();
// ... 中间件配置
app.Run();
3. 实现登录控制器 AuthController.cs
csharp
[ApiController]
[Route("api/[controller]")]
public class AuthController : ControllerBase
{
[HttpPost("login")]
public IActionResult Login([FromBody] LoginModel model)
{
if (model.Username == "demo" && model.Password == "password")
{
// JWT Token 生成逻辑
var token = GenerateJwtToken(model.Username);
return Ok(new { Token = token });
}
return Unauthorized();
}
private string GenerateJwtToken(string username)
{
// Token 生成实现
}
}
第四步:实现业务服务
产品服务 ProductController.cs
csharp
[ApiController]
[Route("api/[controller]")]
public class ProductController : ControllerBase
{
private static readonly List<Product> _products = new()
{
new Product { Id = 1, Name = "Laptop", Price = 55000 },
new Product { Id = 2, Name = "Mobile", Price = 18000 }
};
[HttpGet]
public IActionResult Get() => Ok(_products);
[HttpGet("{id}")]
public IActionResult GetById(int id)
{
var product = _products.Find(p => p.Id == id);
return product == null ? NotFound() : Ok(product);
}
}
订单服务 OrderController.cs
csharp
[ApiController]
[Route("api/[controller]")]
public class OrderController : ControllerBase
{
private readonly IProductServiceClient _productServiceClient;
public OrderController(IProductServiceClient productServiceClient)
{
_productServiceClient = productServiceClient;
}
[HttpPost]
public async Task<IActionResult> Post([FromBody] CreateOrderRequest request)
{
// 调用产品服务验证产品
var product = await _productServiceClient.GetProductByIdAsync(request.ProductId);
if (product == null)
return BadRequest(new { message = "产品不存在" });
// 创建订单逻辑
var order = new Order { /* ... */ };
return CreatedAtAction(nameof(Get), order);
}
}
第五步:实现服务间通信
1. 配置 HttpClient
在 OrderService/Program.cs 中:
csharp
builder.Services.AddHttpClient("ProductService", client =>
{
client.BaseAddress = new Uri("http://localhost:5004/");
});
builder.Services.AddScoped<IProductServiceClient, ProductServiceClient>();
2. 实现服务客户端 ProductServiceClient.cs
csharp
public class ProductServiceClient : IProductServiceClient
{
private readonly HttpClient _httpClient;
public ProductServiceClient(IHttpClientFactory httpClientFactory)
{
_httpClient = httpClientFactory.CreateClient("ProductService");
}
public async Task<Product> GetProductByIdAsync(int productId)
{
var response = await _httpClient.GetAsync($"/api/Product/{productId}");
if (response.IsSuccessStatusCode)
{
var content = await response.Content.ReadAsStringAsync();
return JsonSerializer.Deserialize<Product>(content);
}
return null;
}
}
测试流程
1. 启动所有服务
bash
dotnet run --project APIGateway
dotnet run --project AuthService
dotnet run --project OrderService
dotnet run --project ProductService
2. 完整测试流程
bash
# 1. 获取 Token
POST http://localhost:5001/gateway/auth/login
{
"username": "demo",
"password": "password"
}
# 2. 访问产品列表(需要认证)
GET http://localhost:5001/gateway/products
Authorization: Bearer <your-token>
# 3. 创建订单(服务间调用)
POST http://localhost:5001/gateway/orders
Authorization: Bearer <your-token>
{
"productId": 1,
"quantity": 2
}
关键问题与解决方案
1. Ocelot 路由配置
问题: 路由重复或路径不匹配 解决: 确保 DownstreamPathTemplate 与控制器路由完全匹配
2. 中间件顺序
问题: 404 或认证失败 解决: 确保中间件顺序正确:
csharp
app.UseSwagger();
app.UseSwaggerUI();
app.UseAuthentication();
app.UseAuthorization();
await app.UseOcelot(); // 必须在最后
3. 服务间通信
问题: HttpClient 配置错误 解决: 正确注册命名 HttpClient 和依赖注入
核心要点总结
- 网关配置: Ocelot 作为统一入口,负责路由和认证
- 认证流程: JWT Token 的生成和验证
- 服务隔离: 每个服务独立部署和运行
- 服务通信: 通过 HttpClient 实现服务间调用
- 配置管理: 每个服务有自己的配置和端口
扩展方向
这个基础架构可以进一步扩展:
- 服务发现: 集成 Consul 或 Eureka
- 配置中心: 使用 Spring Cloud Config
- 熔断器: 集成 Polly 实现弹性调用
- 监控追踪: 集成 OpenTelemetry
- 容器化: 使用 Docker 部署
- 消息队列: 集成 RabbitMQ 或 Azure Service Bus
成果验证
完成本教程后,你将拥有:
- ✅ 完整的微服务架构
- ✅ JWT 认证系统
- ✅ API 网关路由
- ✅ 服务间通信
- ✅ 可扩展的项目结构