Chr*_*sic 4 c# dependency-injection hangfire
当计划作为RecurringJob运行时,是否可以让Hangfire使用配置JobActivator实例化对象?
该方法的签名似乎强制静态只使用:
public static void AddOrUpdate<T>(
string recurringJobId,
Expression<Action<T>> methodCall,
Run Code Online (Sandbox Code Playgroud)
关于我如何"滥用"静电来支持通道事物,我有几个想法,但我觉得我可能会遗漏一些东西.有没有一个设计决定,hangfire只支持chron工作中的静态?
J W*_*nia 14
不确定它何时被添加,但我刚刚在我当前的项目中做了类似的事情并且它工作正常.EmailBackgroundTask是一个非静态类,这是一个非静态方法.该类有4个依赖项通过Hangfire.Unity DI包注入.
RecurringJob.AddOrUpdate<EmailBackgroundTask>(x=>x.SendPeriodicEmail(),Cron.MinuteInterval(5));
Run Code Online (Sandbox Code Playgroud)
快速回答是否定的,默认作业激活器仅适用于无参数构造函数或静态方法。我(在 VB.net 中)快速而肮脏地做了一些事情,看看是否可以让它工作并在下面展示。
通过使用“AddOrUpdate”,您告诉 Hangfire 创建 T 的实例,然后访问 T 的方法,因此此签名适用于实例成员,而不是静态。如果您使用其他“AddOrUpdate”方法签名之一而不带通用参数,则它将需要一个 static。
现在有趣的部分是:如果类型 T 没有无参数默认构造函数,那么正如您所说,使用默认 jobactivator 将会失败。
您现在可以在此处使用自定义 jobactivator 为任务的构造函数提供依赖项。如果您创建自己的继承自 JobActivator 的类,那么您可以为您的作业提供依赖项。
这是我的 VB 代码:
Imports Hangfire
Imports System.Reflection
Public Class JobActivationContainer
Inherits JobActivator
Private Property ParameterMap As Dictionary(Of Type, [Delegate])
Private Function CompareParameterToMap(p As ParameterInfo) As Boolean
Dim result = ParameterMap.ContainsKey(p.ParameterType)
Return result
End Function
Public Overrides Function ActivateJob(jobType As Type) As Object
Dim candidateCtor As Reflection.ConstructorInfo = Nothing
'Loop through ctor's and find the most specific ctor where map has all types.
jobType.
GetConstructors.
ToList.
ForEach(
Sub(i)
If i.GetParameters.ToList.
TrueForAll(AddressOf CompareParameterToMap) Then
If candidateCtor Is Nothing Then candidateCtor = i
If i IsNot candidateCtor AndAlso i.GetParameters.Count > candidateCtor.GetParameters.Count Then candidateCtor = i
End If
End Sub
)
If candidateCtor Is Nothing Then
'If the ctor is null, use default activator.
Return MyBase.ActivateJob(jobType)
Else
'Create a list of the parameters in order and activate
Dim ctorParameters As New List(Of Object)
candidateCtor.GetParameters.ToList.ForEach(Sub(i) ctorParameters.Add(ParameterMap(i.ParameterType).DynamicInvoke()))
Return Activator.CreateInstance(jobType, ctorParameters.ToArray)
End If
End Function
Public Sub RegisterDependency(Of T)(factory As Func(Of T))
If Not ParameterMap.ContainsKey(GetType(T)) Then ParameterMap.Add(GetType(T), factory)
End Sub
Public Sub New()
ParameterMap = New Dictionary(Of Type, [Delegate])
End Sub
End Class
Run Code Online (Sandbox Code Playgroud)
我知道这并没有回答如何“滥用”静态的问题,但它确实展示了如何为hangfire滚动你自己的IoC容器,或者按照手册使用已经支持的IoC之一:http:/ /hangfirechinese.readthedocs.org/en/latest/background-methods/using-ioc-containers.html
注意:我计划使用适当的 IoC,我上面的代码纯粹是学术性的,需要大量的工作!
| 归档时间: |
|
| 查看次数: |
2515 次 |
| 最近记录: |