C# 无法使用DI登录AuthorizationFilter
我仍然没有依赖注入,而且我是.NETCore的新手(使用3.1.5)。我已经为WebAPI创建了一个AuthorizationFilter。我仍然不明白如何将Nlog传递给属性 我有以下作为我的授权过滤器C# 无法使用DI登录AuthorizationFilter,c#,.net-core,dependency-injection,asp.net-core-webapi,nlog,C#,.net Core,Dependency Injection,Asp.net Core Webapi,Nlog,我仍然没有依赖注入,而且我是.NETCore的新手(使用3.1.5)。我已经为WebAPI创建了一个AuthorizationFilter。我仍然不明白如何将Nlog传递给属性 我有以下作为我的授权过滤器 public class TokenAttribute : Attribute, IAuthorizationFilter { private readonly ILogger _logger; public TokenAttribute(ILogge
public class TokenAttribute : Attribute, IAuthorizationFilter
{
private readonly ILogger _logger;
public TokenAttribute(ILogger logger)
{
_logger = logger;
}
public void OnAuthorization(AuthorizationFilterContext context)
{
_logger.LogInformation("Authorizing");
//Get the values from the Request Header
context.HttpContext.Request.Headers.TryGetValue("Api-Token", out var token);
context.HttpContext.Request.Headers.TryGetValue("Customer", out var customer);
//Query to look up Customer and Token
using (var ctx = new ModelContext())
{
var results = ctx.Token.FromSqlRaw(sbQuery.ToString()).ToList();
if (results == null || results.Count == 0)
{
context.Result = new BadRequestObjectResult("Invalid Token");
return;
}
return;
}
}
}
}
但是,我的令牌属性出现错误。如果我将它作为[Token]
保留,我会抱怨一条消息:“没有与所需的形式参数相对应的参数”
。我之所以会这样,是因为Token属性的构造函数正在寻找一个ILogger
[Token]
[AcceptVerbs(WebRequestMethods.Http.Get, WebRequestMethods.Http.Post)]
public ShiftRequest Post([FromBody] ShiftRequest m)
{
_logger.LogInformation("Calling POST command.");
然后,如果我尝试将_logger传递给它所抱怨的令牌属性,它会抱怨“非静态字段'ShiftController._logger'”
需要对象引用
[ApiController]
[Route("[controller]")]
public class ShiftController : ControllerBase
{
private IConfiguration _config;
private readonly ILogger<ShiftController> _logger;
public ShiftController(ILogger<ShiftController> logger, IConfiguration config)
{
_config = config;
_logger = logger;
}
[Token(_logger)]
[AcceptVerbs(WebRequestMethods.Http.Get, WebRequestMethods.Http.Post)]
public ShiftRequest Post([FromBody] ShiftRequest m)
{
_logger.LogInformation("Calling POST command.");
在这种情况下,不需要对
属性
进行子类化。对于授权筛选器,可以通过操作上的[ServiceFilter(type)]
属性添加这些筛选器。使用ServiceFilter
属性时,通过ASP.NET Core的内置服务提供程序
在您的代码中,这看起来类似于[ServiceFilter(typeof(TokenAttribute))]
,不过作为个人建议,将其命名为TokenAuthorizationFilter
可能更合适
请注意,您必须将您的
TokenAttribute
注册为Startup.cs中的服务,或者注册到正在进行HTTP管道设置的任何位置。谢谢。我创建了一个新的TokenAuthorizationFilter,然后按照文档进行操作,并让它编译和遍历代码。它不再记录日志,所以我必须检查我的NLog设置,但至少我可以调试代码。我会说,像我这样使用授权的一个积极因素导致它在API代码之前进入过滤器。对于ServiceFilter,它先通过API代码,然后再通过过滤器,这是一种倒退。也许我误解了你的意思,但是一旦请求到达服务器端,授权过滤器是首先运行的。在授权筛选器完成之前,实际操作代码不会运行。我猜您错误地使用了IResultFilter,它在后面运行,而不是上面推荐的IAuthorizationFilter。授权确实首先发生,但我根据文章切换到IResultFilter。如果使用IResultFilter,它将在API代码之后运行。然后我返回到IAuthorizationFilter,现在它在API代码之前首先触发。我把结果放在原来的帖子里。NLog现在根本不起作用,所以我下一步就得试着与之抗争。太好了!很高兴听到你明白了:)。
public class TokenAuthorizationFilter : IAuthorizationFilter
{
private readonly ILogger<TokenAuthorizationFilter> _logger;
public TokenAuthorizationFilter(ILogger<TokenAuthorizationFilter> logger)
{
_logger = logger;
}
public void OnAuthorization(AuthorizationFilterContext context)
{
_logger.LogInformation("Authorizing Token");
//Get the values from the Request Header
context.HttpContext.Request.Headers.TryGetValue("Api-Token", out var token);
context.HttpContext.Request.Headers.TryGetValue("Customer", out var customer);
//Query to check username and password
using (var ctx = new ModelContext())
{
var results = ctx.Token.FromSqlRaw(sbQuery.ToString()).ToList();
if (results == null || results.Count == 0)
{
context.Result = new BadRequestObjectResult("Invalid Token");
return;
}
if (!context.ModelState.IsValid)
{
context.Result = new BadRequestObjectResult(context.ModelState);
}
return;
}
}
public void ConfigureServices(IServiceCollection services)
{
services.AddScoped<TokenAuthorizationFilter>();
services.AddControllersWithViews();
}
[ServiceFilter(typeof(TokenAuthorizationFilter))]
[AcceptVerbs(WebRequestMethods.Http.Get, WebRequestMethods.Http.Post)]
public ShiftRequest Post([FromBody] ShiftRequest m)
{
_logger.LogInformation("Calling POST command.");