public async Task AddProductToCart()
        {
            var rmqUri = new Uri("amqp://*****:*****@localhost:5672/vhost");

            var services = new ServiceCollection();

            services.AddTransient <IProductRepository, FakeProductRepository>();
            using var resolver = EventFlowOptions.New
                                 .UseServiceCollection(services)
                                 .AddDefaults(typeof(CartContext).Assembly)
                                 .UseEntityFrameworkEventStore <CartContext>()
                                 .ConfigureEntityFramework(EntityFrameworkConfiguration.New)
                                 .AddDbContextProvider <CartContext, MySqlCartContextProvider>()
                                 .AddEvents(typeof(ProductAddedEvent))
                                 .AddCommands(typeof(AddProductCommand))
                                 .AddCommandHandlers(typeof(AddProductCommandHandler))
                                 .PublishToRabbitMq(RabbitMqConfiguration.With(rmqUri))
                                 .CreateResolver();

            var commandBus     = resolver.Resolve <ICommandBus>();
            var aggregateStore = resolver.Resolve <IAggregateStore>();

            CartId cartId = CartId.NewCartId();
            await commandBus.PublishAsync(
                new AddProductCommand(cartId, new ProductId(Guid.Empty)),
                CancellationToken.None);

            Cart cart = await aggregateStore.LoadAsync <Cart, CartId>(cartId, CancellationToken.None);

            Assert.AreEqual(1, cart.Products.Count);
        }
Пример #2
0
 // This method gets called by the runtime. Use this method to add services to the container.
 public void ConfigureServices(IServiceCollection services)
 {
     services.AddMvc();
     services.AddControllers();
     ConfigureSwagger(services);
     services.AddAutoMapper(typeof(Startup));
     services.AddEventFlow(ef =>
     {
         var envconfig = EnvironmentConfiguration.Bind(Configuration);
         services.AddSingleton(envconfig);
         ef.AddDefaults(typeof(Startup).Assembly);
         //ef.Configure(cfg => cfg.IsAsynchronousSubscribersEnabled = true);
         ef.PublishToRabbitMq(
             RabbitMqConfiguration.With(new Uri(envconfig.RabbitMqConnection),
                                        true, 5, envconfig.RabbitExchange));
         ef.AddAspNetCore();
         //ef.UseHangfireJobScheduler();
         ef.UseConsoleLog();
         ef.RegisterModule <DomainModule>();
         ef.RegisterModule <AccountingReadModelModule>();
         ef.RegisterServices(s =>
         {
             s.Register <ICustomerCommandService, CustomerCommandService>();
             s.Register <IAccountCommandService, AccountCommandService>();
             s.Register <ITransactionCommandService, TransactionCommandService>();
         });
     });
 }
Пример #3
0
        // This method gets called by the runtime. Use this method to add services to the container.
        public IServiceProvider ConfigureServices(IServiceCollection services)
        {
            var eventStoreUri = new Uri("tcp://localhost:1113", UriKind.Absolute);
            var rabbmitMqUri  = new Uri("amqp://localhost", UriKind.Absolute);
            var mongoUrl      = "mongodb://localhost:27017";

            services.AddMvc();
            var builder   = new ContainerBuilder();
            var container = EventFlowOptions.New
                            .UseAutofacContainerBuilder(builder)
                            .ConfigureMongoDb(mongoUrl, "pages")
                            .PublishToRabbitMq(RabbitMqConfiguration.With(rabbmitMqUri))
                            //.ConfigureElasticsearch(new Uri("http://localhost:9200"))
                            //.UseElasticsearchReadModel<StoryReadModel>()
                            .UseEventStoreEventStore(eventStoreUri)
                            .UseInMemorySnapshotStore()
                            .AddDefaults(Assembly)
                            .UseMongoDbReadModel <UserReadModel>()
                            .AddMetadataProvider <AddGuidMetadataProvider>()
                            .AddAspNetCoreMetadataProviders();

            builder.Populate(services);
            ApplicationContainer = builder.Build();
            return(new AutofacServiceProvider(ApplicationContainer));
        }
Пример #4
0
        public static async Task Main(string[] args)
        {
            var builder = new HostBuilder()
                          .ConfigureAppConfiguration((host, config) => {
                config.SetBasePath(Directory.GetCurrentDirectory());
                config.AddJsonFile("appsettings.json", true, true);
                config.AddJsonFile($"appsettings.{host.HostingEnvironment.EnvironmentName}.json", true, true);
                config.AddEnvironmentVariables();
            })
                          .ConfigureServices(
                (hostcontext, services) => {
                var envconfig = EnvironmentConfiguration.Bind(hostcontext.Configuration);
                services.AddSingleton(envconfig);

                EventFlowOptions.New
                .Configure(cfg => cfg.IsAsynchronousSubscribersEnabled = true)
                .UseServiceCollection(services)
                .AddAspNetCoreMetadataProviders()
                .PublishToRabbitMq(RabbitMqConfiguration.With(new Uri($"{envconfig.RabbitMqConnection}"),
                                                              true, 5, envconfig.RabbitExchange))
                .RegisterModule <DomainModule>()

                //
                // subscribe services changed
                //
                .AddAsynchronousSubscriber <VehicleAggregate, VehicleId, LocationUpdatedEvent, RabbitMqConsumePersistanceService>()
                .RegisterServices(s => {
                    s.Register <IHostedService, RabbitConsumePersistenceService>(Lifetime.Singleton);
                    s.Register <IHostedService, RabbitMqConsumePersistanceService>(Lifetime.Singleton);
                });
            })
                          .ConfigureLogging((hostingContext, logging) => { });

            await builder.RunConsoleAsync();
        }
Пример #5
0
        public IServiceProvider ConfigureServices(IServiceCollection services)
        {
            services.AddControllers();
            services.AddSwaggerGen(x =>
            {
                x.SwaggerDoc("v1", new OpenApiInfo {
                    Title = "Read Api Eventflow Demo - API", Version = "v1"
                });
            });

            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_3_0);

            string           elasticSearchUrl = Environment.GetEnvironmentVariable("ELASTICSEARCHURL");
            ContainerBuilder containerBuilder = new ContainerBuilder();
            Uri node = new Uri(elasticSearchUrl);
            ConnectionSettings settings = new ConnectionSettings(node);

            settings.DisableDirectStreaming();

            ElasticClient elasticClient      = new ElasticClient(settings);
            string        rabbitMqConnection = Environment.GetEnvironmentVariable("RABBITMQCONNECTION");

            Options = EventFlowOptions.New
                      .UseAutofacContainerBuilder(containerBuilder)
                      .AddDefaults(typeof(Employee).Assembly)
                      .ConfigureElasticsearch(() => elasticClient)
                      .RegisterServices(sr => sr.Register <IScopedContext, ScopedContext>(Lifetime.Scoped))
                      .RegisterServices(sr => sr.RegisterType(typeof(EmployeeLocator)))
                      .UseElasticsearchReadModel <EmployeeReadModel, EmployeeLocator>()
                      .RegisterServices(sr => sr.RegisterType(typeof(TransactionLocator)))
                      .UseElasticsearchReadModel <TransactionReadModel, TransactionLocator>()
                      .AddQueryHandlers(typeof(ESTransactionGetQueryHandler), typeof(ESEmployeeGetQueryHandler))
                      .AddAsynchronousSubscriber <EmployeeAggregate, EmployeeId, EmployeeAddedEvent, AddNewEmployeeSubscriber>()
                      .AddSubscribers(typeof(AllEventsSubscriber))
                      .Configure(c => c.IsAsynchronousSubscribersEnabled = true)
                      .Configure(c => c.ThrowSubscriberExceptions        = true)
                      .SubscribeToRabbitMq(
                RabbitMqConfiguration.With(new Uri(rabbitMqConnection),
                                           true, 5, "eventflow"))

                      .AddAspNetCore();

            containerBuilder.Populate(services);
            var container = containerBuilder.Build();

            using (var scope = container.BeginLifetimeScope())
            {
                var subscriber           = scope.Resolve <IRabbitMqSubscriber>();
                var configuration        = scope.Resolve <IRabbitMqConfiguration>();
                var domainEventPublisher = scope.Resolve <IDomainEventPublisher>();
                subscriber.SubscribeAsync(configuration.Exchange, configuration.Exchange + "Queue", EventFlowOptionsRabbitMqExtensions.Listen,
                                          domainEventPublisher, cancellationToken: CancellationToken.None).Wait();
            }

            var _tenantIndex = new ElasticSearchIndex(elasticSearchUrl);

            _tenantIndex.CreateIndex("employeeindex", elasticSearchUrl);
            services.AddSingleton(_tenantIndex.ElasticClient);
            return(new AutofacServiceProvider(container));
        }
Пример #6
0
        private IRootResolver BuildResolver(Exchange exchange, Func <IEventFlowOptions, IEventFlowOptions> configure = null)
        {
            configure = configure ?? (e => e);

            return(configure(EventFlowOptions.New
                             .PublishToRabbitMq(RabbitMqConfiguration.With(_uri, false, exchange: exchange.Value))
                             .AddDefaults(EventFlowTestHelpers.Assembly))
                   .CreateResolver(false));
        }
Пример #7
0
        private IRootResolver BuildResolver(Exchange exchange, Func <IEventFlowOptions, IEventFlowOptions> configure = null)
        {
            configure = configure ?? (e => e);

            return(configure(EventFlowOptions.New
                             .PublishToRabbitMq(RabbitMqConfiguration.With(_uri, false, exchange: exchange.Value))
                             .AddDefaults(EventFlowTestHelpers.Assembly))
                   .RegisterServices(sr => sr.Register <IScopedContext, ScopedContext>(Lifetime.Scoped))
                   .CreateResolver(false));
        }
Пример #8
0
        public IServiceProvider ConfigureServices(IServiceCollection services)
        {
            services.AddControllers();
            services.AddSwaggerGen(x =>
            {
                x.SwaggerDoc("v1", new OpenApiInfo {
                    Title = "Eventflow Demo - API", Version = "v1"
                });
                x.OperationFilter <SwaggerAuthorizationHeaderParameterOperationFilter>();
            });

            services.AddMvc().SetCompatibilityVersion(CompatibilityVersion.Version_3_0);
            ContainerBuilder containerBuilder   = new ContainerBuilder();
            string           rabbitMqConnection = Environment.GetEnvironmentVariable("RABBITMQCONNECTION");
            string           elasticSearchUrl   = Environment.GetEnvironmentVariable("ELASTICSEARCHURL");

            Uri node = new Uri(elasticSearchUrl);
            ConnectionSettings settings = new ConnectionSettings(node);
            var dataRetrieval           = new DataRetrieval()
            {
                Enabled = true
            };

            settings.DisableDirectStreaming();

            ElasticClient elasticClient = new ElasticClient(settings);

            EventFlowOptions.New
            .UseAutofacContainerBuilder(containerBuilder)
            .AddDefaults(typeof(Employee).Assembly)
            .ConfigureEventStore()
            .ConfigureElasticsearch(() => elasticClient)
            .PublishToRabbitMq(
                RabbitMqConfiguration.With(new Uri(rabbitMqConnection),
                                           true, 5, "eventflow"))
            .RegisterServices(sr => sr.Register <IScopedContext, ScopedContext>(Lifetime.Scoped))
            .RegisterServices(sr => sr.RegisterType(typeof(EmployeeLocator)))
            .UseElasticsearchReadModel <EmployeeReadModel, EmployeeLocator>()
            .RegisterServices(sr => sr.RegisterType(typeof(TransactionLocator)))
            .UseElasticsearchReadModel <TransactionReadModel, TransactionLocator>()
            .ConfigureDataRetrieval(dataRetrieval, typeof(EmployeeReadModel).Assembly)
            .AddAspNetCore();

            containerBuilder.Populate(services);
            var _tenantIndex = new ElasticSearchIndex(elasticSearchUrl);

            _tenantIndex.CreateIndex("employeeindex", elasticSearchUrl);
            services.AddSingleton(_tenantIndex.ElasticClient);
            return(new AutofacServiceProvider(containerBuilder.Build()));
        }
Пример #9
0
        public void Register(IEventFlowOptions options)
        {
            options
            .AddDefaults(typeof(TransactionReadModelModule).Assembly)
            .Configure(cfg => cfg.IsAsynchronousSubscribersEnabled = true)
            .SubscribeToRabbitMq(RabbitMqConfiguration.With(new Uri(@"amqp://*****:*****@localhost:5672")))
            .UseInMemoryReadStoreFor <TransactionServiceReadModel>()
            //.AddSubscribers(typeof(AllEventsSubscriber))
            //.AddAsynchronousSubscriber<AccountAggregate, AccountId,AccountRegisterCompletedEvent, AccountRegisterCompletedSubscriber>()

            .RegisterServices(s => {
                s.Register <ITransactionQueryService, TransactionQueryService>();
                s.Register <IReadModelStore <TransactionServiceReadModel>,
                            InMemoryReadStore <TransactionServiceReadModel> >();
                s.Register <ISubscribeSynchronousToAll, RabbitMqDomainEventSubscriber>();
            });
        }
Пример #10
0
        public async Task PassingTest()
        {
            using (var resolver = EventFlowOptions.New
                                  .UseAutofacContainerBuilder(new ContainerBuilder())
                                  .Configure(c => c.ThrowSubscriberExceptions = true)
                                  .AddEvents(typeof(ExampleEvent))
                                  .AddEvents(typeof(ResetEvent))
                                  .AddCommands(typeof(ExampleCommand))
                                  .AddCommands(typeof(ResetCommand))
                                  .AddCommandHandlers(typeof(ExampleCommandHandler))
                                  .AddCommandHandlers(typeof(ResetCommandHandler))
                                  .ConfigureEventStore()
                                  .ConfigureMongoDb(MongoClient, SNAPSHOT_CONTAINER_NAME)
                                  .AddSnapshots(typeof(ExampleSnaphost))
                                  .UseMongoDbSnapshotStore()
                                  .UseInMemoryReadStoreFor <ExampleReadModel>()
                                  .RegisterServices(sr => sr.Register(i => SnapshotEveryFewVersionsStrategy.Default))
                                  .RegisterServices(DecorateCommandBus)
                                  .PublishToRabbitMq(RabbitMqConfiguration.With(RabbitMqUri, true, 4, "eventflow"))
                                  .Configure(c => c.IsAsynchronousSubscribersEnabled = true)
                                  .AddJobs(typeof(ExampleJob))
                                  .CreateResolver())
            {
                Int32 magicNumber = 2;
                CommandBus = resolver.Resolve <ICommandBus>();

                ExampleId exampleId = PublishCommand.GetStreamName("Tenant", "EXAMPLE");

                CommandReturnResult result = await CommandBus.PublishAsync(
                    new ExampleCommand(exampleId, magicNumber), CancellationToken.None)
                                             .ConfigureAwait(false);

                IAggregateStore aggregateStore = resolver.Resolve <IAggregateStore>();
                var             @aggregate     = await aggregateStore.LoadAsync <ExampleAggregate, ExampleId>(exampleId, CancellationToken.None);

                //Command side
                result.IsSuccess.Should().BeTrue();
                result.AggregateRoot.Should().NotBeNull();
                result.AggregateRoot.Version.Should().Be(1);
                result.AggregateRoot.Name.Value.Should().Be("ExampleAggregate");
                result.AggregateRoot.GetIdentity().Value.Should().Be(exampleId.Value);
                @aggregate.Should().NotBeNull();
                result.AggregateRoot.Should().Equals(@aggregate);
            }
        }
Пример #11
0
        public Bootstrap()
        {
            var mquri  = new Uri("amqp://*****:*****@127.0.0.1");
            var mqconf = RabbitMqConfiguration.With(
                mquri, true, 5, "loxnet"
                );

            _resolver = EventFlowOptions.New
                        .ConfigureTransportDomain()
                        .UseConsoleLog()
                        .PublishToRabbitMq(mqconf)
                        .CreateResolver();

            _aggregateStore = _resolver
                              .Resolve <IAggregateStore>();

            _commandBus = _resolver
                          .Resolve <ICommandBus>();
        }
Пример #12
0
        public async Task ReadModelTest()
        {
            using (var resolver = EventFlowOptions.New
                                  .UseAutofacContainerBuilder(new ContainerBuilder())
                                  .Configure(c => c.ThrowSubscriberExceptions = true)
                                  .AddEvents(typeof(ExampleEvent))
                                  .AddEvents(typeof(ResetEvent))
                                  .AddCommands(typeof(ExampleCommand))
                                  .AddCommands(typeof(ResetCommand))
                                  .AddCommandHandlers(typeof(ExampleCommandHandler))
                                  .AddCommandHandlers(typeof(ResetCommandHandler))
                                  .ConfigureEventStore()
                                  .ConfigureMongoDb(MongoClient, SNAPSHOT_CONTAINER_NAME)
                                  .AddSnapshots(typeof(ExampleSnaphost))
                                  .UseMongoDbSnapshotStore()
                                  .UseInMemoryReadStoreFor <ExampleReadModel>()
                                  .RegisterServices(sr => sr.Register(i => SnapshotEveryFewVersionsStrategy.Default))
                                  .RegisterServices(DecorateCommandBus)
                                  .PublishToRabbitMq(RabbitMqConfiguration.With(RabbitMqUri, true, 4, "eventflow"))
                                  .Configure(c => c.IsAsynchronousSubscribersEnabled = true)
                                  .AddJobs(typeof(ExampleJob))
                                  .CreateResolver())
            {
                Int32 magicNumber = 2;
                CommandBus = resolver.Resolve <ICommandBus>();

                ExampleId exampleId = PublishCommand.GetStreamName("Tenant", "EXAMPLE");

                CommandReturnResult result = await CommandBus.PublishAsync(
                    new ExampleCommand(exampleId, magicNumber), CancellationToken.None)
                                             .ConfigureAwait(false);

                var queryProcessor = resolver.Resolve <IQueryProcessor>();
                ExampleReadModel exampleReadModel = await queryProcessor.ProcessAsync(
                    new ReadModelByIdQuery <ExampleReadModel>(exampleId),
                    CancellationToken.None)
                                                    .ConfigureAwait(false);

                exampleReadModel.Should().NotBeNull();
                exampleReadModel.MagicNumber.Should().ContainSingle();
                exampleReadModel.MagicNumber.First().Should().Be(2);
            }
        }
Пример #13
0
        // This method gets called by the runtime. Use this method to add services to the container.
        // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=398940
        public void ConfigureServices(IServiceCollection services)
        {
            var env = EnvironmentConfiguration.Bind(_configuration);

            services.ConfigureServices(env, typeof(Startup), new OpenApiInfo
            {
                Title   = "Movies API",
                Version = "v1"
            });

            EventFlowOptions.New
            .UseServiceCollection(services)
            .AddDefaults(typeof(Startup).Assembly)
            .AddAspNetCore()
            .UseConsoleLog()
            .RegisterModule <DomainModule>()
            .RegisterModule <MovieReadStoreModule>()
            .RegisterModule <EventSourcingModule>()
            .PublishToRabbitMq(RabbitMqConfiguration.With(new Uri(env.RabbitMqConnection)))
            .CreateServiceProvider();
        }
Пример #14
0
        // This method gets called by the runtime. Use this method to add services to the container.
        public IServiceProvider ConfigureServices(IServiceCollection services)
        {
            var env = EnvironmentConfiguration.Bind(_configuration);

            services.AddAutoMapper()
            .AddSingleton(env)
            .AddSwaggerGen(c => c.SwaggerDoc("v1", new Info {
                Title = "Vehicles API", Version = "v1"
            }))
            .AddMvc()
            .SetCompatibilityVersion(CompatibilityVersion.Version_2_2);

            return(EventFlowOptions.New
                   .UseServiceCollection(services)
                   .AddAspNetCoreMetadataProviders()
                   .UseConsoleLog()
                   .RegisterModule <DomainModule>()
                   .RegisterModule <VehicleReadStoreModule>()
                   .RegisterModule <EventSourcingModule>()
                   .PublishToRabbitMq(RabbitMqConfiguration.With(new Uri(env.RabbitMqConnection)))
                   .CreateServiceProvider());
        }
Пример #15
0
        public static void AddEventSourcing(this ContainerBuilder containerBuilder, IConfiguration configuration)
        {
            var snapshotStoreSettings = configuration.GetSnapshotStoreSettings();
            var rabbitMQSettings      = configuration.GetRabbitMQSettings();
            var eventStoreSettings    = configuration.GetEventStoreSettings();

            var rabbitMQConfiguration = RabbitMqConfiguration.With(new Uri($"amqp://{rabbitMQSettings.UserName}:{rabbitMQSettings.Password}@{rabbitMQSettings.Host}:{rabbitMQSettings.Port}"), rabbitMQSettings.Persistent.Value, 5, rabbitMQSettings.ExchangeName);

            EventFlowOptions.New

            .UseAutofacContainerBuilder(containerBuilder)                 // Must be the first line!
            .Configure(c => c.ThrowSubscriberExceptions = true)
            .RegisterModule <UserModule>()
            .AddAspNetCore(options =>
            {
                options.AddUserClaimsMetadata();
                options.AddDefaultMetadataProviders();
            })
            .ConfigureEventStore(eventStoreSettings)
            .ConfigureMongoDb(new MongoClient(snapshotStoreSettings.ConnectionString), snapshotStoreSettings.Name)
            .UseMongoDbSnapshotStore()
            .RegisterServices(sr => sr.Register(i => SnapshotEveryFewVersionsStrategy.Default))
            .PublishToRabbitMq(rabbitMQConfiguration);
        }
        public async Task PublishCommandAsync()
        {
            var client = new MongoClient("mongodb://*****:*****@"amqp://test:test@localhost:5672"), true, 4, "eventflow"))
                                  //.ConfigureSagas()
                                  //.UseNullLog()
                                  //.UseInMemoryReadStoreFor<Aggregates.ReadModels.ExampleReadModel>()
                                  .Configure(c => c.IsAsynchronousSubscribersEnabled = true)
                                  //.AddAsynchronousSubscriber<ExampleAggregate, Aggregates.Events.ExampleId, ExampleEvent, RabbitMqConsumePersistanceService>()
                                  //.RegisterServices(s => {
                                  //    s.Register<IHostedService, RabbitConsumePersistenceService>(Lifetime.Singleton);
                                  //    s.Register<IHostedService, RabbitMqConsumePersistanceService>(Lifetime.Singleton);
                                  //})
                                  //.AddSubscribers(new Type[] { typeof(ExampleSyncSubscriber) })
                                  // .UseHangfireJobScheduler()
                                  .AddJobs(typeof(ExampleJob))
                                  .CreateResolver())
            {
                Int32 magicNumber = 2;
                CommandBus = resolver.Resolve <ICommandBus>();

                var clock = new Stopwatch();
                clock.Start();

                ExampleId exampleId = GetStreamName("Tenant", "EXAMPLE");

                for (int i = 0; i < 1; i++)
                {
                    IExecutionResult result = await CommandBus.PublishAsync(new ExampleCommand(exampleId, magicNumber), CancellationToken.None)
                                              .ConfigureAwait(false);

                    #region Comments
                    //result.IsSuccess.Should().BeTrue();

                    //IAggregateStore aggregateStore = resolver.Resolve<IAggregateStore>();
                    //var @object = aggregateStore.LoadAsync<ExampleAggregate, ExampleId>(exampleId, CancellationToken.None);

                    ////Obsolete
                    ////IEventStore eventStore = resolver.Resolve<IEventStore>();
                    ////var aggregate = await eventStore.LoadAggregateAsync<ExampleAggregate, ExampleId>(exampleId, CancellationToken.None);

                    ////state of our aggregate root
                    //var queryProcessor = resolver.Resolve<IQueryProcessor>();
                    //var result = await queryProcessor.ProcessAsync(
                    //     new ReadModelByIdQuery<ExampleReadModel>(exampleId),
                    //     CancellationToken.None)
                    //     .ConfigureAwait(false);

                    //// Verify that the read model has the expected magic number
                    //exampleReadModel.MagicNumber.Should().Be(42);
                    #endregion
                }

                clock.Stop();

                Console.WriteLine("Duration: " + clock.ElapsedMilliseconds + "ms");
            }

            Console.ReadLine();
        }