Hi- We are creating custom applications ( e.g say a Web API ) that would need to access ZERO Domain services, repositories, Dbcontext etc,..
What are the Project references that I would need to add to our custom application.
How do I inject all dependencies?.. I know in the web solution castle windsor takes care of all dependencies through dependency injection
Basically we would need access to all libraries except the application service layer for the custom application. The appSettings from our custom application need to be fed into all these dependencies ( e.g conn string etc,..).
Do you have any sample projects other than the ZERO web solution that access these libraries ?
Please let me know.
Regards, Sesha K
14 Answer(s)
-
0
Hi @SEB_ADMIN,
We don't have a sample but you can easily do it like this;
Create a module class for your new project (see https://aspnetboilerplate.com/Pages/Documents/Module-System) and on this module, depend on the related AspNet Zero modules you want to use. Of cours,e you also need to ference to *.Core and *.EntityFramework projects if you want to depend on their modules.
-
0
Hi- Thanks for the information. I was able to get it working for a Console Application.
But I need to hookup a startup module to my .NET Core Worker service I am creating ( Windows Service ). How do I hook up a start up module to my worker service using a default host builder. For e.g below
** it seems the extension method "AddAbp" is not available for a default Host Builder.**
"CalculatorSchedulerModule" is my custom start up module for my custom worker service and I have set the dependency of that module to Core Module and Entity framework module. I noticed that the extension method is part of namespace "Abp.AspNetCore". How do I reference that in my custom worker service which I am planning to run as a Windows Service. The below code is in "Program.cs". Host.CreateDefaultBuilder(args) .UseWindowsService() .ConfigureServices((hostContext, services) => { services.AddHostedService<CalculatorScheduler>(); ** services.AddAbp<CalculatorSchedulerModule>();** });
-
0
Hi,
You are right. AddAbp is designed for ASP.NET Core. Can't you start your projetc like this https://github.com/aspnetboilerplate/aspnetboilerplate-samples/blob/master/AbpEfConsoleApp/AbpEfConsoleApp/Program.cs using
AbpBootstrapper
? -
0
Hi The bootstrapper works fine for the Console Application. But here I am using a .NET Core Worker Service to be deployed as Windows Service . it uses "DefaultHostBuilder". The key here is how do I define a startup module and hook it into the Host builder. There seem to be no direct way of doing it. How do I inject abp IOC Container and dependencies into my Host Builder ? I can use services.AddSingleton() as in the example below, but I cannot add entire dependency chain individually in this fashion. The only way to add all dependencies through chain of execution of Modules for each assembly which will all be made dependent on my start up module.
Just like a Console Application example, Dont you have an example of Windows Service or Worker Service accessing all Abp's Application, Domain and Entityframework layer components ?. That would be useful..
My key problem is "How do I attach a Startup module to my Worker Service Host Builder". If I am able to do that I can hook dependencies to other Modules ( application, Core etc.) and get all the components into IOC container automatically.
How do I inject the entire dependency container of Abp in the code below ??
Host.CreateDefaultBuilder(args) .UseWindowsService()
.ConfigureServices((hostContext, services) => { services.AddHostedService<CalculatorScheduler>(); services.AddSingleton<ICalculatorProfileJob, CalculatorProfileJob>(); });
-
0
Hi,
Can you try this ?
.ConfigureServices((hostContext, services) => { var abpBootstrapper = AbpBootstrapper.Create<TStartupModule>(optionsAction); services.AddSingleton(abpBootstrapper); WindsorRegistrationHelper.CreateServiceProvider(abpBootstrapper.IocManager.IocContainer, services); services.AddHostedService<CalculatorScheduler>(); services.AddSingleton<ICalculatorProfileJob, CalculatorProfileJob>(); });
-
0
I tried this but it is still complaining on dependency injection for CalculatorProfileJob. it is a domain service under "core" Project and it has dependencies injected into it ( like repositories). Looks like I have to inject the entire dependency hiearchy chain here which is not correct. Is there a way out ?.
You can try this just by creating a new .NET Core Worker service project and injecting any of Abp domain services into it
I guess the bootstrapper is still not taking care of dependency injection for the HostedService.
-
0
System.AggregateException HResult=0x80131500 Message=Some services are not able to be constructed (Error while validating the service descriptor 'ServiceType: Microsoft.Extensions.Hosting.IHostedService Lifetime: Singleton ImplementationType: CalculatorSchedulerService.CalculatorScheduler': Unable to resolve service for type 'Abp.Domain.Repositories.IRepository
2[SEB.FPE.Calculators.CalculatorProfile,System.Int32]' while attempting to activate 'SEB.FPE.Calculators.Jobs.CalculatorProfileJob'.) (Error while validating the service descriptor 'ServiceType: SEB.FPE.Calculators.Jobs.ICalculatorProfileJob Lifetime: Singleton ImplementationType: SEB.FPE.Calculators.Jobs.CalculatorProfileJob': Unable to resolve service for type 'Abp.Domain.Repositories.IRepository
2[SEB.FPE.Calculators.CalculatorProfile,System.Int32]' while attempting to activate 'SEB.FPE.Calculators.Jobs.CalculatorProfileJob'.) Source=Microsoft.Extensions.DependencyInjection StackTrace: at Microsoft.Extensions.DependencyInjection.ServiceProvider..ctor(IEnumerable1 serviceDescriptors, ServiceProviderOptions options) at Microsoft.Extensions.DependencyInjection.ServiceCollectionContainerBuilderExtensions.BuildServiceProvider(IServiceCollection services, ServiceProviderOptions options) at Microsoft.Extensions.DependencyInjection.DefaultServiceProviderFactory.CreateServiceProvider(IServiceCollection containerBuilder) at Microsoft.Extensions.Hosting.Internal.ServiceFactoryAdapter
1.CreateServiceProvider(Object containerBuilder) at Microsoft.Extensions.Hosting.HostBuilder.CreateServiceProvider() at Microsoft.Extensions.Hosting.HostBuilder.Build() at CalculatorSchedulerService.Program.Main(String[] args) in C:\Users\sesha.krishnamurthy\Source\repos\FPE\FPE\aspnet-core\src\CalculatorSchedulerService\Program.cs:line 41This exception was originally thrown at this call stack: [External Code]
Inner Exception 1: InvalidOperationException: Error while validating the service descriptor 'ServiceType: Microsoft.Extensions.Hosting.IHostedService Lifetime: Singleton ImplementationType: CalculatorSchedulerService.CalculatorScheduler': Unable to resolve service for type 'Abp.Domain.Repositories.IRepository`2[SEB.FPE.Calculators.CalculatorProfile,System.Int32]' while attempting to activate 'SEB.FPE.Calculators.Jobs.CalculatorProfileJob'.
Inner Exception 2: InvalidOperationException: Unable to resolve service for type 'Abp.Domain.Repositories.IRepository`2[SEB.FPE.Calculators.CalculatorProfile,System.Int32]' while attempting to activate 'SEB.FPE.Calculators.Jobs.CalculatorProfileJob'.
-
0
-
0
Hi- The following code solved the DI Problem. Can you please check but I am getting a different error explained below. I will also post the code that causes the problem
public static IHostBuilder CreateHostBuilder(string[] args) { var abpBootstrapper = AbpBootstrapper.Create<CalculatorSchedulerModule>(); abpBootstrapper.Initialize(); return Host.CreateDefaultBuilder(args) .UseWindowsService() .UseCastleWindsor(abpBootstrapper.IocManager.IocContainer) .ConfigureServices((hostContext, services) => { services.AddHostedService<CalculatorScheduler>(); }); }
** Cannot access a disposed object. A common cause of this error is disposing a context that was resolved from dependency injection and then later trying to use the same context instance elsewhere in your application. This may occur if you are calling Dispose() on the context, or wrapping the context in a using statement. If you are using dependency injection, you should let the dependency injection container take care of disposing context instances. Object name: 'FPEDbContext'.**
-
0
public class CalculatorScheduler : BackgroundService { private readonly ILogger<CalculatorScheduler> _logger; private readonly ICalculatorProfileJob _job; private readonly IRepository<CalculatorSchedule, int> _schedule; private Timer _timer; public CalculatorScheduler(ILogger<CalculatorScheduler> logger, ICalculatorProfileJob job, IRepository<CalculatorSchedule, int> schedule ) { _logger = logger; _job = job; _schedule = schedule; } protected override async Task ExecuteAsync(CancellationToken stoppingToken) { while (!stoppingToken.IsCancellationRequested) { _logger.LogInformation("Worker running at: {time}", DateTimeOffset.Now); await Task.Delay(1000, stoppingToken); } } public override Task StartAsync(CancellationToken cancellationToken) { _timer = new Timer(CheckSchedule, null, 0, Convert.ToInt32(TimeSpan.FromSeconds(30).TotalMilliseconds)); return Task.CompletedTask; } public override Task StopAsync(CancellationToken cancellationToken) { _logger.LogInformation("Worker stopping at: {time}", DateTimeOffset.Now); _timer?.Change(Timeout.Infinite, 0); return Task.CompletedTask; } private void CheckSchedule(object state) { List<CalculatorSchedule> lstSchedule = this._schedule.GetAll().ToList(); foreach (CalculatorSchedule sched in lstSchedule) _job.ExecuteJob(sched); } }
-
0
the error happens on the below line in method "CheckSchedule". List<CalculatorSchedule> lstSchedule = this._schedule.GetAll().ToList();
-
1
Change
.GetAll().ToList()
to.GetAllList()
, or begin your own unit of work.Reference: aspnetboilerplate/aspnetboilerplate#3946 (comment 430319419)
-
1
Thankyou. That solved the problem.
-
0
@SEB_ADMIN and @aaron can you please share a link for the source code. I want to access application services directly into console application. Thank you