如何从HttpRequestMessage中获取Controller对应的Action方法名称
解决方案
核心思路
路由匹配完成后请求对象会携带路由数据,你只需要从路由数据中提取action对应的取值即可,不同框架版本实现方式略有差异:
1. ASP.NET Web API (.NET Framework 场景)
首先引入所需命名空间:
using System.Web.Http.Routing;
修改你的SendAsync方法,在路由匹配完成后(即await base.SendAsync执行后)添加取值逻辑:
public class RequestAndResponseHandler : DelegatingHandler { protected override async Task<HttpResponseMessage> SendAsync( HttpRequestMessage request, CancellationToken cancellationToken) { if (request.Content != null) { string requestBody = await request.Content.ReadAsStringAsync(); Trace.WriteLine(requestBody); } var response = await base.SendAsync(request, cancellationToken); if (response.Content != null) { var responseBody = await response.Content.ReadAsStringAsync(); Trace.WriteLine(responseBody); } // 新增获取接口方法名逻辑 var routeData = request.GetRouteData(); string actionName = string.Empty; if (routeData?.Values.TryGetValue("action", out var actionObj) == true) { actionName = actionObj.ToString(); // 此处拿到的actionName就是你需要的"getitem" Trace.WriteLine($"接口方法名:{actionName}"); } return response; } }
2. ASP.NET Core / .NET 5+ 场景
方法1:使用WebApi兼容包
先安装NuGet包Microsoft.AspNetCore.Mvc.WebApiCompatShim,后续逻辑和.NET Framework场景完全一致。
方法2:直接从HttpContext获取路由数据
无需额外安装包,引入命名空间:
using Microsoft.AspNetCore.Routing; using Microsoft.AspNetCore.Mvc.Controllers;
修改取值逻辑即可:
var routeData = request.HttpContext.GetRouteData(); string actionName = string.Empty; if (routeData?.Values.TryGetValue("action", out var actionObj) == true) { actionName = actionObj.ToString(); } // 如果是特性路由场景,想拿到实际的Action方法名不受路由模板影响,可以用下面的方式 var actionDescriptor = request.HttpContext.GetEndpoint()?.Metadata.GetMetadata<ControllerActionDescriptor>(); if (actionDescriptor != null) { actionName = actionDescriptor.ActionName; // 还可获取Controller名称 var controllerName = actionDescriptor.ControllerName; }
注意事项
如果你需要在base.SendAsync执行前(接口逻辑执行前)拿到方法名,需要确保你的DelegatingHandler注册顺序在路由中间件之后,否则路由数据还未生成无法获取到对应值。
内容的提问来源于stack exchange,提问作者kenzolek
相关产品推荐
相关产品推荐

