1

I'm trying to setup dependency injection in my Xamarin Forms application. I have got constructor injection all working with Simple Injector. However, when I start to use Entity Framework I am struggling with the following issue.

I register my AppDbContext (inherits from DbContext) with the following lines:

 _container.Register<AppDbContext>(() => {
                return new AppDbContext(new DbContextOptionsBuilder<AppDbContext>().UseSqlServer(connectionString).Options);
            });

This throws the error below:

-[Disposable Transient Component] AppDbContext is registered as transient, but implements IDisposable...

So I then change the lines above to:

_container.Register<AppDbContext>(() => {
                return new AppDbContext(new DbContextOptionsBuilder<AppDbContext>().UseSqlServer(connectionString).Options);
            }, Lifestyle.Scoped);

And also set the defaultscopedlifestyle to the below:

_container.Options.DefaultScopedLifestyle = new ThreadScopedLifestyle();

This throws the below error:

AppDbContext is registered using the 'Thread Scoped' lifestyle, but the instance is requested outside the context of an active (Thread Scoped) scope.

Finally I change the defaultscopedlifestyle to the only other option I can find:

_container.Options.DefaultScopedLifestyle = new AsyncScopedLifestyle();

But then I receive this error below:

AppDbContext is registered using the 'Async Scoped' lifestyle, but the instance is requested outside the context of an active (Async Scoped) scope. Please see https://simpleinjector.org/scoped for more information about how apply lifestyles and manage scopes.

All I need to do is to register the AppDbContext so that it can be used with entity framework. I use the following line in my MVC project which shares the same shared class library:

services.AddDbContext<AppDbContext>

So I need to be able to do the above line with simple injector.

Hope this is enough information, if you need to know anything else feel free to ask.

Update 5th Feb One of my repositories: public class HolidayBookingRepository : IHolidayBookingRepository {
private readonly AppDbContext context;

    public HolidayBookingRepository(AppDbContext context) 
    {
        this.context = context;
    }
    public  async Task<HolidayBooking> GetById(int Id)
    {
        return await context.HolidayBooking.AsNoTracking().Where(h =>h.HolidayBookingId == Id).FirstOrDefaultAsync<HolidayBooking>();
    }
}

My ViewModel:

IHolidayBookingRepository _holidayRepo;
public HomePageViewModel(IHolidayBookingRepository holidayRepo)
{
    _holidayRepo = holidayRepo;        
}
public override async void OnAppearingAsync()
{
    try
    {
        base.OnAppearingAsync();
        HolidayBooking booking = await _holidayRepo.GetById(42);
        Console.WriteLine(booking.Comment);
    }
    catch(Exception ex)
    {
    }
}
Ryan Gaudion
  • 695
  • 1
  • 8
  • 22
  • 2
    You miss an important part and understanding of lifestyle management. Please read the manual on scoping [here](https://simpleinjector.readthedocs.io/en/latest/lifetimes.html#async-scoped-lifestyle-async-await). If you have any questions after reading this we'll be happy to help you. – Ric .Net Feb 04 '20 at 18:13
  • @Ric.Net thank you for your comment. I have read the above and it has helped me understand scoping a bit more. However, I'm not sure which option to use for Xamarin. Would you be able to help me with this? – Ryan Gaudion Feb 05 '20 at 11:00
  • 1
    With Asp.Net Simple Injector can hook to the framework and starts a scope automatically when a request comes in. With Xamarin, or any non request framework like Windows Forms, WPF and UWP you'll have to start and dispose the scope yourself. Within this you can use the DbContext. I could help you but I need more code of you use the DbContext in your services/handlers/repositories – Ric .Net Feb 05 '20 at 11:08
  • @Ric.Net please find extra code above. If you need anything else, let me know. – Ryan Gaudion Feb 05 '20 at 11:25
  • 2
    I think this answer is spot on for your question: https://stackoverflow.com/a/29808487/3294832 – Ric .Net Feb 05 '20 at 22:03
  • @Ric.Net thank you for linking that post. I read through it all and it shone some light on the issue. After reading both links above, am I okay to use a singleton for my Xamarin as the app will not be open for more than a day? If not than please can you elaborate the answer above to fit into my Xamarin scenario. Thank you for your help so far! – Ryan Gaudion Feb 06 '20 at 09:18
  • @Ric.Net, I'm still struggling with this issue, any update on how how to set it up correctly for Xamarin Forms? – Ryan Gaudion Mar 09 '20 at 16:52

0 Answers0