在 C# 中注入对属性构造函数的依赖
Injecting a dependency to constructor of an attribute in C#
我有以下属性:
public class MultipleInteractivitiesAttribute : CheckBaseAttribute
{
private readonly IInteractivityService _interactivityService;
public MultipleInteractivitiesAttribute(IInteractivityService interactivityService)
{
_interactivityService = interactivityService;
}
public override Task<bool> ExecuteCheckAsync(CommandContext ctx, bool help)
{
var userId = ctx.User.Id;
var cmdName = ctx.Command.QualifiedName;
return Task.FromResult(!_interactivityService.CheckForUserInteractivity(userId, cmdName));
}
}
下面的 class 有一个我使用属性的方法。
public class RecruitmentModule : BaseCommandModule
{
private readonly IInteractivityService _interactivityService;
public RecruitmentModule(IInteractivityService interactivityService)
{
_interactivityService = interactivityService;
}
[Command("apply"), MultipleInteractivities()]
public async Task Apply(CommandContext ctx)
{
// some code here
}
}
现在,当我在 Apply
方法上方使用 MultipleInteractivities
作为属性时遇到问题。它希望我将参数传递给它的构造函数。
现在,因为我已经在 RecruitmentModule
class 的构造函数中注入了 IInteractivityService
。我尝试将其作为参数传递给我的 MultipleInteractivities
属性。
像这样:
[Command("apply"), MultipleInteractivities(_interactivityService)]
但是,这会产生以下错误:
Cannot access non-static field '_interactivityService' in static context
所以我尝试在 RecruitmentModule
class 中使 _interactivityService
字段静态化,如下所示:
private static IInteractivityService _interactivityService;
现在,当它作为参数传递给我的 MultipleInteractivities
属性时,出现以下错误。
Attribute constructor parameter 'interactivityService' has type 'DiscordBot.Core.Interfaces.IInteractivityService', which is not a valid attribute parameter type
如何将 IInteractivityService
传递给我的 MultipleInteractivitiesAttribute
而不会出现错误。
您不需要(and shouldn't) inject the dependency into the attribute constructor. Instead, the CommandContext
has a Services
属性 返回可用于解决依赖关系的 IServiceProvider
:
public class MultipleInteractivitiesAttribute : CheckBaseAttribute
{
public override Task<bool> ExecuteCheckAsync(CommandContext ctx, bool help)
{
var userId = ctx.User.Id;
var cmdName = ctx.Command.QualifiedName;
var interactivityService = ctx.Services.GetService<IInteractivityService>();
return Task.FromResult(!interactivityService.CheckForUserInteractivity(userId, cmdName));
}
}
我有以下属性:
public class MultipleInteractivitiesAttribute : CheckBaseAttribute
{
private readonly IInteractivityService _interactivityService;
public MultipleInteractivitiesAttribute(IInteractivityService interactivityService)
{
_interactivityService = interactivityService;
}
public override Task<bool> ExecuteCheckAsync(CommandContext ctx, bool help)
{
var userId = ctx.User.Id;
var cmdName = ctx.Command.QualifiedName;
return Task.FromResult(!_interactivityService.CheckForUserInteractivity(userId, cmdName));
}
}
下面的 class 有一个我使用属性的方法。
public class RecruitmentModule : BaseCommandModule
{
private readonly IInteractivityService _interactivityService;
public RecruitmentModule(IInteractivityService interactivityService)
{
_interactivityService = interactivityService;
}
[Command("apply"), MultipleInteractivities()]
public async Task Apply(CommandContext ctx)
{
// some code here
}
}
现在,当我在 Apply
方法上方使用 MultipleInteractivities
作为属性时遇到问题。它希望我将参数传递给它的构造函数。
现在,因为我已经在 RecruitmentModule
class 的构造函数中注入了 IInteractivityService
。我尝试将其作为参数传递给我的 MultipleInteractivities
属性。
像这样:
[Command("apply"), MultipleInteractivities(_interactivityService)]
但是,这会产生以下错误:
Cannot access non-static field '_interactivityService' in static context
所以我尝试在 RecruitmentModule
class 中使 _interactivityService
字段静态化,如下所示:
private static IInteractivityService _interactivityService;
现在,当它作为参数传递给我的 MultipleInteractivities
属性时,出现以下错误。
Attribute constructor parameter 'interactivityService' has type 'DiscordBot.Core.Interfaces.IInteractivityService', which is not a valid attribute parameter type
如何将 IInteractivityService
传递给我的 MultipleInteractivitiesAttribute
而不会出现错误。
您不需要(and shouldn't) inject the dependency into the attribute constructor. Instead, the CommandContext
has a Services
属性 返回可用于解决依赖关系的 IServiceProvider
:
public class MultipleInteractivitiesAttribute : CheckBaseAttribute
{
public override Task<bool> ExecuteCheckAsync(CommandContext ctx, bool help)
{
var userId = ctx.User.Id;
var cmdName = ctx.Command.QualifiedName;
var interactivityService = ctx.Services.GetService<IInteractivityService>();
return Task.FromResult(!interactivityService.CheckForUserInteractivity(userId, cmdName));
}
}