12

I have been using dependency injection inside a constructor which has been working great. I have recently learned of the [Inject] attribute, but cannot seem to get it to work. Maybe it's not compatible or perhaps I am misusing it.

Registering it as a service in Startup.cs:

services.AddScoped<IUserProfileService, UserProfileService>();

Using it as a property with the [Inject] attribute:

[Microsoft.AspNetCore.Components.Inject]
private IUserProfileService _UserProfileService { get; set; }

When _UserProfileService is called upon, it has not been initialized and is still null. If I switch back to injecting it in the constructor, it works. Am I misusing the attribute or is it simply not possible?

ASP.Net Core 3.1, using Blazor

3

1 Answer 1

20

The [Inject] attribute is solely applied to Blazor Components. Property injection will not be applied to registrations made to the IServiceCollection, even if you mark those properties with [Inject]. The built-in DI Container is not capable of applying property injection.

The sole reason for the existence of the InjectAttribute is to use the @inject tag in Razor pages. When you use the @inject tag, Blazor will generate a public property on your Blazor Component that is marked with [Inject].

Although Property Injection is described as a valid pattern for practicing DI in DIPP&P (section 4.4), the book also warns about the downsides of Property Injection, and the authors (Mark Seemann and I) state that:

When building applications [...] we never use Property Injection, and you should do so sparingly. Even though you might have a Local Default for a Dependency, Constructor Injection still provides you with a better alternative. Constructor Injection is simpler and more robust. You might think you need Property Injection to work around a cyclic Dependency, but that’s a code smell, as we’ll explain in chapter 6.

So, whenever possible, refrain from using Property Injection and use Constructor Injection as your sole way to provide dependencies to a consumer.

Sign up to request clarification or add additional context in comments.

2 Comments

I have a base class Base and sub classes Sub1, Sub2, …, SubN, and I want to add a injected property to Base, then I have to change all constructors of all Subs to forward that new property. Is there a standard pattern to work around this using Constructor Injection?
Hi @Panke, it's hard to give specific guidance with such generic example, but in general, you should prevent using base classes i.c.w. DI and prefer using Composition over Inheritance instead. There are many design principles, patterns, and refactorings that help with this. e.g. The SOLID principles, patterns like the decorator pattern, and refactorings like Facade Services.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.