Mariusmatei
Mariusmatei

Reputation: 13

InvalidOperationException: Unable to resolve service for type 'Data.IRestaurantsData' while attempting to activate

I am new to c# and asp.net core, I follow some tutorials and I get this error when accessing Restaurants page: "InvalidOperationException: Unable to resolve service for type 'Data.IRestaurantsData' while attempting to activate 'OdeToFood.Pages.Restaurants.ListModel' "

Restaurant.cs

namespace Core
{
    public class Restaurant
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public string Location { get; set; }
        public CuisineType Cuisine { get; set; }
    }
}

IRestaurantsData.cs

        namespace Data
    {
    
        public interface IRestaurantsData
        {
            IEnumerable<Restaurant> GetAll();
        }

    public class InMemoryRestaurantsData : IRestaurantsData
    {
        public List<Restaurant> restaurants;
        public InMemoryRestaurantsData()
        {
           restaurants = new List<Restaurant>()
            {
                new Restaurant  { Id = 1, Name = "Pizza", Location = "Milano", Cuisine = CuisineType.Italian },
                new Restaurant  { Id = 2, Name = "Rice", Location = "Mexic", Cuisine = CuisineType.Mexican },
                new Restaurant  { Id = 3, Name = "Chicken", Location = "london", Cuisine = CuisineType.Indian},
            };
        }
        public IEnumerable<Restaurant> GetAll()
        {
        return from r in restaurants
               orderby r.Name
               select r;
        }
    }
}

List.cshtml

    namespace OdeToFood.Pages.Restaurants
{
    public class ListModel : PageModel
    {
        private readonly IRestaurantsData _restaurantsData;
        public IEnumerable<Restaurant> Restaurants;
        public ListModel(IRestaurantsData restaurantsData)
        {
          
            this._restaurantsData = restaurantsData;
        }
        public void OnGet()
        {
            Restaurants = _restaurantsData.GetAll();
        }
    }
}

Startup.cs

using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.HttpsPolicy;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Data;

namespace OdeToFood
{
    public class Startup
    {
        public Startup(IConfiguration configuration)
        {
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {
            services.Configure<CookiePolicyOptions>(options =>
            {
                services.AddSingleton<IRestaurantsData, InMemoryRestaurantsData>();
                // This lambda determines whether user consent for non-essential cookies is needed for a given request.
                options.CheckConsentNeeded = context => true;
                options.MinimumSameSitePolicy = SameSiteMode.None;
            });


            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }
            else
            {
                app.UseExceptionHandler("/Error");
                app.UseHsts();
            }

            app.UseHttpsRedirection();
            app.UseStaticFiles();
            app.UseCookiePolicy();

            app.UseMvc();
        }
    }
}

I just want to know what is wrong and why. Thanks

Upvotes: 1

Views: 699

Answers (1)

Jacek
Jacek

Reputation: 874

You should move that line in Startup.cs ConfigureServices:

services.AddSingleton<IRestaurantsData, InMemoryRestaurantsData>();

to the outer scope, so that your code looks like this:

public void ConfigureServices(IServiceCollection services)
        {
            services.Configure<CookiePolicyOptions>(options =>
            {
                // This lambda determines whether user consent for non-essential cookies is needed for a given request.
                options.CheckConsentNeeded = context => true;
                options.MinimumSameSitePolicy = SameSiteMode.None;
            });

            services.AddSingleton<IRestaurantsData, InMemoryRestaurantsData>();

            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_2_1);
        }

This maneuver allows runtime to execute the line on application startup so that your IRestaurantsData parameter will be injected into your ListModel's constructor properly any time.

Upvotes: 2

Related Questions