A little bit late to the party, but wanted to chime in with some more details.
The issue lies in StructureMap that says this: https://structuremap.github.io/registration/constructor-selection/
If there are multiple public constructor functions on a concrete class, StructureMap's default behavior is to select the "greediest" constructor, i.e., the constructor function with the most parameters.
So if we peek into Hangfire.Client.BackgroundJobFactory : IBackgroundJobFactory
, we'll find there a constructor with this declaration:
internal BackgroundJobFactory(
[NotNull] IJobFilterProvider filterProvider,
[NotNull] IBackgroundJobFactory innerFactory)
Although it's not a public constructor, it's accessible to StructureMap, and it somehow chooses this constructor to be the one for IBackgroundJobFactory
.
@ErpaDerp's solution works because now StructureMap is explicitly excluded from scanning Hangfire.Core.dll assembly.
However, you can work around this issue in another way, described in the same StructureMap documentation page. In your Registry
, or call to container.Configure
force SM to select the greediest public constructor:
For<IBackgroundJobFactory>()
.Use<BackgroundJobFactory>()
.SelectConstructor(() => new BackgroundJobFactory(null));
This way you won't have to change your scanning policies, and StructureMap won't trip with Hangfire's AspNetCore registration.