Merge branch 'dev' into Validation-decorator-integration

This commit is contained in:
Ramón Tomás 2017-03-23 13:46:21 +01:00
commit 007525b4cc
30 changed files with 567 additions and 119 deletions

View File

@ -1,7 +1,7 @@
 
Microsoft Visual Studio Solution File, Format Version 12.00 Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 15 # Visual Studio 15
VisualStudioVersion = 15.0.26228.4 VisualStudioVersion = 15.0.26228.0
MinimumVisualStudioVersion = 10.0.40219.1 MinimumVisualStudioVersion = 10.0.40219.1
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{932D8224-11F6-4D07-B109-DA28AD288A63}" Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{932D8224-11F6-4D07-B109-DA28AD288A63}"
EndProject EndProject
@ -72,6 +72,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "EventBus", "src\BuildingBlo
EndProject EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "EventBusRabbitMQ", "src\BuildingBlocks\EventBus\EventBusRabbitMQ\EventBusRabbitMQ.csproj", "{8088F3FC-6787-45FA-A924-816EC81CBFAC}" Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "EventBusRabbitMQ", "src\BuildingBlocks\EventBus\EventBusRabbitMQ\EventBusRabbitMQ.csproj", "{8088F3FC-6787-45FA-A924-816EC81CBFAC}"
EndProject EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "IntegrationEventLogEF", "src\BuildingBlocks\EventBus\IntegrationEventLogEF\IntegrationEventLogEF.csproj", "{9EE28E45-1533-472B-8267-56C48855BA0E}"
EndProject
Global Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution GlobalSection(SolutionConfigurationPlatforms) = preSolution
Ad-Hoc|Any CPU = Ad-Hoc|Any CPU Ad-Hoc|Any CPU = Ad-Hoc|Any CPU
@ -662,6 +664,54 @@ Global
{8088F3FC-6787-45FA-A924-816EC81CBFAC}.Release|x64.Build.0 = Release|Any CPU {8088F3FC-6787-45FA-A924-816EC81CBFAC}.Release|x64.Build.0 = Release|Any CPU
{8088F3FC-6787-45FA-A924-816EC81CBFAC}.Release|x86.ActiveCfg = Release|Any CPU {8088F3FC-6787-45FA-A924-816EC81CBFAC}.Release|x86.ActiveCfg = Release|Any CPU
{8088F3FC-6787-45FA-A924-816EC81CBFAC}.Release|x86.Build.0 = Release|Any CPU {8088F3FC-6787-45FA-A924-816EC81CBFAC}.Release|x86.Build.0 = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|Any CPU.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|Any CPU.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|ARM.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|ARM.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|iPhone.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|iPhone.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|iPhoneSimulator.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|iPhoneSimulator.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|x64.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|x64.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|x86.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Ad-Hoc|x86.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|Any CPU.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|Any CPU.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|ARM.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|ARM.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|iPhone.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|iPhone.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|iPhoneSimulator.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|iPhoneSimulator.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|x64.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|x64.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|x86.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.AppStore|x86.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|Any CPU.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|ARM.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|ARM.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|iPhone.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|iPhone.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|iPhoneSimulator.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|iPhoneSimulator.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|x64.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|x64.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|x86.ActiveCfg = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Debug|x86.Build.0 = Debug|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|Any CPU.ActiveCfg = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|Any CPU.Build.0 = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|ARM.ActiveCfg = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|ARM.Build.0 = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|iPhone.ActiveCfg = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|iPhone.Build.0 = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|iPhoneSimulator.ActiveCfg = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|iPhoneSimulator.Build.0 = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|x64.ActiveCfg = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|x64.Build.0 = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|x86.ActiveCfg = Release|Any CPU
{9EE28E45-1533-472B-8267-56C48855BA0E}.Release|x86.Build.0 = Release|Any CPU
EndGlobalSection EndGlobalSection
GlobalSection(SolutionProperties) = preSolution GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE HideSolutionNode = FALSE
@ -689,5 +739,6 @@ Global
{807BB76E-B2BB-47A2-A57B-3D1B20FF5E7F} = {DB0EFB20-B024-4E5E-A75C-52143C131D25} {807BB76E-B2BB-47A2-A57B-3D1B20FF5E7F} = {DB0EFB20-B024-4E5E-A75C-52143C131D25}
{0044B293-1DCC-4224-B948-00CF6DC7F510} = {807BB76E-B2BB-47A2-A57B-3D1B20FF5E7F} {0044B293-1DCC-4224-B948-00CF6DC7F510} = {807BB76E-B2BB-47A2-A57B-3D1B20FF5E7F}
{8088F3FC-6787-45FA-A924-816EC81CBFAC} = {807BB76E-B2BB-47A2-A57B-3D1B20FF5E7F} {8088F3FC-6787-45FA-A924-816EC81CBFAC} = {807BB76E-B2BB-47A2-A57B-3D1B20FF5E7F}
{9EE28E45-1533-472B-8267-56C48855BA0E} = {807BB76E-B2BB-47A2-A57B-3D1B20FF5E7F}
EndGlobalSection EndGlobalSection
EndGlobal EndGlobal

View File

@ -11,6 +11,6 @@ namespace Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events
Id = Guid.NewGuid(); Id = Guid.NewGuid();
} }
public Guid Id { get; private set; } public Guid Id { get; }
} }
} }

View File

@ -21,7 +21,8 @@ namespace Microsoft.eShopOnContainers.BuildingBlocks.EventBusRabbitMQ
private readonly Dictionary<string, List<IIntegrationEventHandler>> _handlers; private readonly Dictionary<string, List<IIntegrationEventHandler>> _handlers;
private readonly List<Type> _eventTypes; private readonly List<Type> _eventTypes;
private Tuple<IModel, IConnection> _connection; private IModel _model;
private IConnection _connection;
private string _queueName; private string _queueName;
@ -86,15 +87,15 @@ namespace Microsoft.eShopOnContainers.BuildingBlocks.EventBusRabbitMQ
_handlers.Remove(eventName); _handlers.Remove(eventName);
var eventType = _eventTypes.Single(e => e.Name == eventName); var eventType = _eventTypes.Single(e => e.Name == eventName);
_eventTypes.Remove(eventType); _eventTypes.Remove(eventType);
_connection.Item1.QueueUnbind(queue: _queueName, _model.QueueUnbind(queue: _queueName,
exchange: _brokerName, exchange: _brokerName,
routingKey: eventName); routingKey: eventName);
if (_handlers.Keys.Count == 0) if (_handlers.Keys.Count == 0)
{ {
_queueName = string.Empty; _queueName = string.Empty;
_connection.Item1.Dispose(); _model.Dispose();
_connection.Item2.Dispose(); _connection.Dispose();
} }
} }
@ -103,50 +104,53 @@ namespace Microsoft.eShopOnContainers.BuildingBlocks.EventBusRabbitMQ
public void Dispose() public void Dispose()
{ {
if (_connection != null) _handlers.Clear();
{ _model?.Dispose();
_handlers.Clear(); _connection?.Dispose();
_connection.Item1.Dispose();
_connection.Item2.Dispose();
}
} }
private IModel GetChannel() private IModel GetChannel()
{ {
if (_connection != null) if (_model != null)
{ {
return _connection.Item1; return _model;
} }
else else
{ {
var factory = new ConnectionFactory() { HostName = _connectionString }; (_model, _connection) = CreateConnection();
var connection = factory.CreateConnection(); return _model;
var channel = connection.CreateModel();
channel.ExchangeDeclare(exchange: _brokerName,
type: "direct");
if (string.IsNullOrEmpty(_queueName))
{
_queueName = channel.QueueDeclare().QueueName;
}
var consumer = new EventingBasicConsumer(channel);
consumer.Received += async (model, ea) =>
{
var eventName = ea.RoutingKey;
var message = Encoding.UTF8.GetString(ea.Body);
await ProcessEvent(eventName, message);
};
channel.BasicConsume(queue: _queueName,
noAck: true,
consumer: consumer);
_connection = new Tuple<IModel, IConnection>(channel, connection);
return _connection.Item1;
} }
} }
private (IModel model, IConnection connection) CreateConnection()
{
var factory = new ConnectionFactory() { HostName = _connectionString };
var con = factory.CreateConnection();
var channel = con.CreateModel();
channel.ExchangeDeclare(exchange: _brokerName,
type: "direct");
if (string.IsNullOrEmpty(_queueName))
{
_queueName = channel.QueueDeclare().QueueName;
}
var consumer = new EventingBasicConsumer(channel);
consumer.Received += async (model, ea) =>
{
var eventName = ea.RoutingKey;
var message = Encoding.UTF8.GetString(ea.Body);
await ProcessEvent(eventName, message);
};
channel.BasicConsume(queue: _queueName,
noAck: true,
consumer: consumer);
return (channel, con);
}
private async Task ProcessEvent(string eventName, string message) private async Task ProcessEvent(string eventName, string message)
{ {
if (_handlers.ContainsKey(eventName)) if (_handlers.ContainsKey(eventName))

View File

@ -9,6 +9,7 @@
<ItemGroup> <ItemGroup>
<PackageReference Include="Newtonsoft.Json" Version="9.0.1" /> <PackageReference Include="Newtonsoft.Json" Version="9.0.1" />
<PackageReference Include="RabbitMQ.Client" Version="4.1.1" /> <PackageReference Include="RabbitMQ.Client" Version="4.1.1" />
<PackageReference Include="System.ValueTuple" Version="4.3.0" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>

View File

@ -2,7 +2,7 @@
using System.Collections.Generic; using System.Collections.Generic;
using System.Text; using System.Text;
namespace Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events.IntegrationEventLog namespace Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF
{ {
public enum EventStateEnum public enum EventStateEnum
{ {

View File

@ -0,0 +1,48 @@
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using System;
using System.Collections.Generic;
using System.Text;
namespace Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF
{
public class IntegrationEventLogContext : DbContext
{
public IntegrationEventLogContext(DbContextOptions<IntegrationEventLogContext> options) : base(options)
{
}
public DbSet<IntegrationEventLogEntry> IntegrationEventLogs { get; set; }
protected override void OnModelCreating(ModelBuilder builder)
{
builder.Entity<IntegrationEventLogEntry>(ConfigureIntegrationEventLogEntry);
}
void ConfigureIntegrationEventLogEntry(EntityTypeBuilder<IntegrationEventLogEntry> builder)
{
builder.ToTable("IntegrationEventLog");
builder.HasKey(e => e.EventId);
builder.Property(e => e.EventId)
.IsRequired();
builder.Property(e => e.Content)
.IsRequired();
builder.Property(e => e.CreationTime)
.IsRequired();
builder.Property(e => e.State)
.IsRequired();
builder.Property(e => e.TimesSent)
.IsRequired();
builder.Property(e => e.EventTypeName)
.IsRequired();
}
}
}

View File

@ -0,0 +1,27 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netcoreapp1.1</TargetFramework>
<RuntimeFrameworkVersion>1.1.0</RuntimeFrameworkVersion>
<RootNamespace>Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF</RootNamespace>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="1.1.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="1.1.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Relational" Version="1.1.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="1.1.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer.Design" Version="1.1.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="1.1.0" />
<PackageReference Include="Newtonsoft.Json" Version="9.0.1" />
</ItemGroup>
<ItemGroup>
<DotNetCliToolReference Include="Microsoft.EntityFrameworkCore.Tools.DotNet" Version="1.0.0" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\EventBus\EventBus.csproj" />
</ItemGroup>
</Project>

View File

@ -2,11 +2,13 @@
using System.Collections.Generic; using System.Collections.Generic;
using System.Text; using System.Text;
using Newtonsoft.Json; using Newtonsoft.Json;
using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events;
namespace Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events.IntegrationEventLog namespace Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF
{ {
public class IntegrationEventLogEntry public class IntegrationEventLogEntry
{ {
private IntegrationEventLogEntry() { }
public IntegrationEventLogEntry(IntegrationEvent @event) public IntegrationEventLogEntry(IntegrationEvent @event)
{ {
EventId = @event.Id; EventId = @event.Id;

View File

@ -58,6 +58,7 @@
<ItemGroup> <ItemGroup>
<ProjectReference Include="..\..\..\BuildingBlocks\EventBus\EventBusRabbitMQ\EventBusRabbitMQ.csproj" /> <ProjectReference Include="..\..\..\BuildingBlocks\EventBus\EventBusRabbitMQ\EventBusRabbitMQ.csproj" />
<ProjectReference Include="..\..\..\BuildingBlocks\EventBus\EventBus\EventBus.csproj" /> <ProjectReference Include="..\..\..\BuildingBlocks\EventBus\EventBus\EventBus.csproj" />
<ProjectReference Include="..\..\..\BuildingBlocks\EventBus\IntegrationEventLogEF\IntegrationEventLogEF.csproj" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>

View File

@ -1,7 +1,9 @@
using Microsoft.AspNetCore.Mvc; using Catalog.API.IntegrationEvents;
using Microsoft.AspNetCore.Mvc;
using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Storage;
using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Abstractions; using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Abstractions;
using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events.IntegrationEventLog; using Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF;
using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure; using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure;
using Microsoft.eShopOnContainers.Services.Catalog.API.IntegrationEvents.Events; using Microsoft.eShopOnContainers.Services.Catalog.API.IntegrationEvents.Events;
using Microsoft.eShopOnContainers.Services.Catalog.API.Model; using Microsoft.eShopOnContainers.Services.Catalog.API.Model;
@ -16,28 +18,31 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
[Route("api/v1/[controller]")] [Route("api/v1/[controller]")]
public class CatalogController : ControllerBase public class CatalogController : ControllerBase
{ {
private readonly CatalogContext _context; private readonly CatalogContext _catalogContext;
private readonly IOptionsSnapshot<Settings> _settings; private readonly IOptionsSnapshot<Settings> _settings;
private readonly IEventBus _eventBus; private readonly IEventBus _eventBus;
private readonly IIntegrationEventLogService _integrationEventLogService;
public CatalogController(CatalogContext context, IOptionsSnapshot<Settings> settings, IEventBus eventBus) public CatalogController(CatalogContext Context, IOptionsSnapshot<Settings> settings, IEventBus eventBus, IIntegrationEventLogService integrationEventLogService)
{ {
_context = context; _catalogContext = Context;
_settings = settings; _settings = settings;
_eventBus = eventBus; _eventBus = eventBus;
_integrationEventLogService = integrationEventLogService;
((DbContext)context).ChangeTracker.QueryTrackingBehavior = QueryTrackingBehavior.NoTracking; ((DbContext)Context).ChangeTracker.QueryTrackingBehavior = QueryTrackingBehavior.NoTracking;
} }
// GET api/v1/[controller]/items[?pageSize=3&pageIndex=10] // GET api/v1/[controller]/items[?pageSize=3&pageIndex=10]
[HttpGet] [HttpGet]
[Route("[action]")] [Route("[action]")]
public async Task<IActionResult> Items([FromQuery]int pageSize = 10, [FromQuery]int pageIndex = 0) public async Task<IActionResult> Items([FromQuery]int pageSize = 10, [FromQuery]int pageIndex = 0)
{ {
var totalItems = await _context.CatalogItems var totalItems = await _catalogContext.CatalogItems
.LongCountAsync(); .LongCountAsync();
var itemsOnPage = await _context.CatalogItems var itemsOnPage = await _catalogContext.CatalogItems
.OrderBy(c=>c.Name) .OrderBy(c=>c.Name)
.Skip(pageSize * pageIndex) .Skip(pageSize * pageIndex)
.Take(pageSize) .Take(pageSize)
@ -57,11 +62,11 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
public async Task<IActionResult> Items(string name, [FromQuery]int pageSize = 10, [FromQuery]int pageIndex = 0) public async Task<IActionResult> Items(string name, [FromQuery]int pageSize = 10, [FromQuery]int pageIndex = 0)
{ {
var totalItems = await _context.CatalogItems var totalItems = await _catalogContext.CatalogItems
.Where(c => c.Name.StartsWith(name)) .Where(c => c.Name.StartsWith(name))
.LongCountAsync(); .LongCountAsync();
var itemsOnPage = await _context.CatalogItems var itemsOnPage = await _catalogContext.CatalogItems
.Where(c => c.Name.StartsWith(name)) .Where(c => c.Name.StartsWith(name))
.Skip(pageSize * pageIndex) .Skip(pageSize * pageIndex)
.Take(pageSize) .Take(pageSize)
@ -80,7 +85,7 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
[Route("[action]/type/{catalogTypeId}/brand/{catalogBrandId}")] [Route("[action]/type/{catalogTypeId}/brand/{catalogBrandId}")]
public async Task<IActionResult> Items(int? catalogTypeId, int? catalogBrandId, [FromQuery]int pageSize = 10, [FromQuery]int pageIndex = 0) public async Task<IActionResult> Items(int? catalogTypeId, int? catalogBrandId, [FromQuery]int pageSize = 10, [FromQuery]int pageIndex = 0)
{ {
var root = (IQueryable<CatalogItem>)_context.CatalogItems; var root = (IQueryable<CatalogItem>)_catalogContext.CatalogItems;
if (catalogTypeId.HasValue) if (catalogTypeId.HasValue)
{ {
@ -113,7 +118,7 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
[Route("[action]")] [Route("[action]")]
public async Task<IActionResult> CatalogTypes() public async Task<IActionResult> CatalogTypes()
{ {
var items = await _context.CatalogTypes var items = await _catalogContext.CatalogTypes
.ToListAsync(); .ToListAsync();
return Ok(items); return Ok(items);
@ -124,7 +129,7 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
[Route("[action]")] [Route("[action]")]
public async Task<IActionResult> CatalogBrands() public async Task<IActionResult> CatalogBrands()
{ {
var items = await _context.CatalogBrands var items = await _catalogContext.CatalogBrands
.ToListAsync(); .ToListAsync();
return Ok(items); return Ok(items);
@ -135,7 +140,7 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
[HttpPost] [HttpPost]
public async Task<IActionResult> EditProduct([FromBody]CatalogItem product) public async Task<IActionResult> EditProduct([FromBody]CatalogItem product)
{ {
var item = await _context.CatalogItems.SingleOrDefaultAsync(i => i.Id == product.Id); var item = await _catalogContext.CatalogItems.SingleOrDefaultAsync(i => i.Id == product.Id);
if (item == null) if (item == null)
{ {
@ -146,20 +151,21 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
{ {
var oldPrice = item.Price; var oldPrice = item.Price;
item.Price = product.Price; item.Price = product.Price;
_context.CatalogItems.Update(item);
var @event = new ProductPriceChangedIntegrationEvent(item.Id, item.Price, oldPrice); var @event = new ProductPriceChangedIntegrationEvent(item.Id, item.Price, oldPrice);
var eventLogEntry = new IntegrationEventLogEntry(@event);
_context.IntegrationEventLog.Add(eventLogEntry);
await _context.SaveChangesAsync(); using (var transaction = _catalogContext.Database.BeginTransaction())
{
_catalogContext.CatalogItems.Update(item);
await _catalogContext.SaveChangesAsync();
await _integrationEventLogService.SaveEventAsync(@event);
transaction.Commit();
}
_eventBus.Publish(@event); _eventBus.Publish(@event);
eventLogEntry.TimesSent++; await _integrationEventLogService.MarkEventAsPublishedAsync(@event);
eventLogEntry.State = EventStateEnum.Published;
_context.IntegrationEventLog.Update(eventLogEntry);
await _context.SaveChangesAsync();
} }
return Ok(); return Ok();
@ -170,7 +176,7 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
[HttpPost] [HttpPost]
public async Task<IActionResult> CreateProduct([FromBody]CatalogItem product) public async Task<IActionResult> CreateProduct([FromBody]CatalogItem product)
{ {
_context.CatalogItems.Add( _catalogContext.CatalogItems.Add(
new CatalogItem new CatalogItem
{ {
CatalogBrandId = product.CatalogBrandId, CatalogBrandId = product.CatalogBrandId,
@ -181,7 +187,7 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
Price = product.Price Price = product.Price
}); });
await _context.SaveChangesAsync(); await _catalogContext.SaveChangesAsync();
return Ok(); return Ok();
} }
@ -191,15 +197,15 @@ namespace Microsoft.eShopOnContainers.Services.Catalog.API.Controllers
[HttpDelete] [HttpDelete]
public async Task<IActionResult> DeleteProduct(int id) public async Task<IActionResult> DeleteProduct(int id)
{ {
var product = _context.CatalogItems.SingleOrDefault(x => x.Id == id); var product = _catalogContext.CatalogItems.SingleOrDefault(x => x.Id == id);
if (product == null) if (product == null)
{ {
return NotFound(); return NotFound();
} }
_context.CatalogItems.Remove(product); _catalogContext.CatalogItems.Remove(product);
await _context.SaveChangesAsync(); await _catalogContext.SaveChangesAsync();
return Ok(); return Ok();
} }

View File

@ -3,24 +3,24 @@
using EntityFrameworkCore.Metadata.Builders; using EntityFrameworkCore.Metadata.Builders;
using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore;
using Model; using Model;
using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events.IntegrationEventLog; using Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF;
public class CatalogContext : DbContext public class CatalogContext : DbContext
{ {
public CatalogContext(DbContextOptions options) : base(options) public CatalogContext(DbContextOptions<CatalogContext> options) : base(options)
{ {
} }
public DbSet<CatalogItem> CatalogItems { get; set; } public DbSet<CatalogItem> CatalogItems { get; set; }
public DbSet<CatalogBrand> CatalogBrands { get; set; } public DbSet<CatalogBrand> CatalogBrands { get; set; }
public DbSet<CatalogType> CatalogTypes { get; set; } public DbSet<CatalogType> CatalogTypes { get; set; }
public DbSet<IntegrationEventLogEntry> IntegrationEventLog { get; set; } //public DbSet<IntegrationEventLogEntry> IntegrationEventLog { get; set; }
protected override void OnModelCreating(ModelBuilder builder) protected override void OnModelCreating(ModelBuilder builder)
{ {
builder.Entity<CatalogBrand>(ConfigureCatalogBrand); builder.Entity<CatalogBrand>(ConfigureCatalogBrand);
builder.Entity<CatalogType>(ConfigureCatalogType); builder.Entity<CatalogType>(ConfigureCatalogType);
builder.Entity<CatalogItem>(ConfigureCatalogItem); builder.Entity<CatalogItem>(ConfigureCatalogItem);
builder.Entity<IntegrationEventLogEntry>(ConfigureIntegrationEventLogEntry); //builder.Entity<IntegrationEventLogEntry>(ConfigureIntegrationEventLogEntry);
} }
void ConfigureCatalogItem(EntityTypeBuilder<CatalogItem> builder) void ConfigureCatalogItem(EntityTypeBuilder<CatalogItem> builder)
@ -80,30 +80,30 @@
.HasMaxLength(100); .HasMaxLength(100);
} }
void ConfigureIntegrationEventLogEntry(EntityTypeBuilder<IntegrationEventLogEntry> builder) //void ConfigureIntegrationEventLogEntry(EntityTypeBuilder<IntegrationEventLogEntry> builder)
{ //{
builder.ToTable("IntegrationEventLog"); // builder.ToTable("IntegrationEventLog");
builder.HasKey(e => e.EventId); // builder.HasKey(e => e.EventId);
builder.Property(e => e.EventId) // builder.Property(e => e.EventId)
.IsRequired(); // .IsRequired();
builder.Property(e => e.Content) // builder.Property(e => e.Content)
.IsRequired(); // .IsRequired();
builder.Property(e => e.CreationTime) // builder.Property(e => e.CreationTime)
.IsRequired(); // .IsRequired();
builder.Property(e => e.State) // builder.Property(e => e.State)
.IsRequired(); // .IsRequired();
builder.Property(e => e.TimesSent) // builder.Property(e => e.TimesSent)
.IsRequired(); // .IsRequired();
builder.Property(e => e.EventTypeName) // builder.Property(e => e.EventTypeName)
.IsRequired(); // .IsRequired();
} //}
} }
} }

View File

@ -0,0 +1,99 @@
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure;
namespace Catalog.API.Infrastructure.Migrations
{
[DbContext(typeof(CatalogContext))]
[Migration("20170322124244_RemoveIntegrationEventLogs")]
partial class RemoveIntegrationEventLogs
{
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
modelBuilder
.HasAnnotation("ProductVersion", "1.1.1")
.HasAnnotation("SqlServer:Sequence:.catalog_brand_hilo", "'catalog_brand_hilo', '', '1', '10', '', '', 'Int64', 'False'")
.HasAnnotation("SqlServer:Sequence:.catalog_hilo", "'catalog_hilo', '', '1', '10', '', '', 'Int64', 'False'")
.HasAnnotation("SqlServer:Sequence:.catalog_type_hilo", "'catalog_type_hilo', '', '1', '10', '', '', 'Int64', 'False'")
.HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
modelBuilder.Entity("Microsoft.eShopOnContainers.Services.Catalog.API.Model.CatalogBrand", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasAnnotation("SqlServer:HiLoSequenceName", "catalog_brand_hilo")
.HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.SequenceHiLo);
b.Property<string>("Brand")
.IsRequired()
.HasMaxLength(100);
b.HasKey("Id");
b.ToTable("CatalogBrand");
});
modelBuilder.Entity("Microsoft.eShopOnContainers.Services.Catalog.API.Model.CatalogItem", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasAnnotation("SqlServer:HiLoSequenceName", "catalog_hilo")
.HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.SequenceHiLo);
b.Property<int>("CatalogBrandId");
b.Property<int>("CatalogTypeId");
b.Property<string>("Description");
b.Property<string>("Name")
.IsRequired()
.HasMaxLength(50);
b.Property<string>("PictureUri");
b.Property<decimal>("Price");
b.HasKey("Id");
b.HasIndex("CatalogBrandId");
b.HasIndex("CatalogTypeId");
b.ToTable("Catalog");
});
modelBuilder.Entity("Microsoft.eShopOnContainers.Services.Catalog.API.Model.CatalogType", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasAnnotation("SqlServer:HiLoSequenceName", "catalog_type_hilo")
.HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.SequenceHiLo);
b.Property<string>("Type")
.IsRequired()
.HasMaxLength(100);
b.HasKey("Id");
b.ToTable("CatalogType");
});
modelBuilder.Entity("Microsoft.eShopOnContainers.Services.Catalog.API.Model.CatalogItem", b =>
{
b.HasOne("Microsoft.eShopOnContainers.Services.Catalog.API.Model.CatalogBrand", "CatalogBrand")
.WithMany()
.HasForeignKey("CatalogBrandId")
.OnDelete(DeleteBehavior.Cascade);
b.HasOne("Microsoft.eShopOnContainers.Services.Catalog.API.Model.CatalogType", "CatalogType")
.WithMany()
.HasForeignKey("CatalogTypeId")
.OnDelete(DeleteBehavior.Cascade);
});
}
}
}

View File

@ -0,0 +1,34 @@
using System;
using System.Collections.Generic;
using Microsoft.EntityFrameworkCore.Migrations;
namespace Catalog.API.Infrastructure.Migrations
{
public partial class RemoveIntegrationEventLogs : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "IntegrationEventLog");
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "IntegrationEventLog",
columns: table => new
{
EventId = table.Column<Guid>(nullable: false),
Content = table.Column<string>(nullable: false),
CreationTime = table.Column<DateTime>(nullable: false),
EventTypeName = table.Column<string>(nullable: false),
State = table.Column<int>(nullable: false),
TimesSent = table.Column<int>(nullable: false)
},
constraints: table =>
{
table.PrimaryKey("PK_IntegrationEventLog", x => x.EventId);
});
}
}
}

View File

@ -4,7 +4,6 @@ using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Metadata; using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations; using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure; using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure;
using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events;
namespace Catalog.API.Infrastructure.Migrations namespace Catalog.API.Infrastructure.Migrations
{ {
@ -20,28 +19,6 @@ namespace Catalog.API.Infrastructure.Migrations
.HasAnnotation("SqlServer:Sequence:.catalog_type_hilo", "'catalog_type_hilo', '', '1', '10', '', '', 'Int64', 'False'") .HasAnnotation("SqlServer:Sequence:.catalog_type_hilo", "'catalog_type_hilo', '', '1', '10', '', '', 'Int64', 'False'")
.HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn); .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
modelBuilder.Entity("Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events.IntegrationEventLogEntry", b =>
{
b.Property<Guid>("EventId")
.ValueGeneratedOnAdd();
b.Property<string>("Content")
.IsRequired();
b.Property<DateTime>("CreationTime");
b.Property<string>("EventTypeName")
.IsRequired();
b.Property<int>("State");
b.Property<int>("TimesSent");
b.HasKey("EventId");
b.ToTable("IntegrationEventLog");
});
modelBuilder.Entity("Microsoft.eShopOnContainers.Services.Catalog.API.Model.CatalogBrand", b => modelBuilder.Entity("Microsoft.eShopOnContainers.Services.Catalog.API.Model.CatalogBrand", b =>
{ {
b.Property<int>("Id") b.Property<int>("Id")

View File

@ -0,0 +1,43 @@
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF;
namespace Catalog.API.Migrations
{
[DbContext(typeof(IntegrationEventLogContext))]
[Migration("20170322145434_IntegrationEventInitial")]
partial class IntegrationEventInitial
{
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
modelBuilder
.HasAnnotation("ProductVersion", "1.1.1")
.HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
modelBuilder.Entity("Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF.IntegrationEventLogEntry", b =>
{
b.Property<Guid>("EventId")
.ValueGeneratedOnAdd();
b.Property<string>("Content")
.IsRequired();
b.Property<DateTime>("CreationTime");
b.Property<string>("EventTypeName")
.IsRequired();
b.Property<int>("State");
b.Property<int>("TimesSent");
b.HasKey("EventId");
b.ToTable("IntegrationEventLog");
});
}
}
}

View File

@ -0,0 +1,34 @@
using System;
using System.Collections.Generic;
using Microsoft.EntityFrameworkCore.Migrations;
namespace Catalog.API.Migrations
{
public partial class IntegrationEventInitial : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "IntegrationEventLog",
columns: table => new
{
EventId = table.Column<Guid>(nullable: false),
Content = table.Column<string>(nullable: false),
CreationTime = table.Column<DateTime>(nullable: false),
EventTypeName = table.Column<string>(nullable: false),
State = table.Column<int>(nullable: false),
TimesSent = table.Column<int>(nullable: false)
},
constraints: table =>
{
table.PrimaryKey("PK_IntegrationEventLog", x => x.EventId);
});
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "IntegrationEventLog");
}
}
}

View File

@ -0,0 +1,42 @@
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF;
namespace Catalog.API.Migrations
{
[DbContext(typeof(IntegrationEventLogContext))]
partial class IntegrationEventLogContextModelSnapshot : ModelSnapshot
{
protected override void BuildModel(ModelBuilder modelBuilder)
{
modelBuilder
.HasAnnotation("ProductVersion", "1.1.1")
.HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn);
modelBuilder.Entity("Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF.IntegrationEventLogEntry", b =>
{
b.Property<Guid>("EventId")
.ValueGeneratedOnAdd();
b.Property<string>("Content")
.IsRequired();
b.Property<DateTime>("CreationTime");
b.Property<string>("EventTypeName")
.IsRequired();
b.Property<int>("State");
b.Property<int>("TimesSent");
b.HasKey("EventId");
b.ToTable("IntegrationEventLog");
});
}
}
}

View File

@ -0,0 +1,14 @@
using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
namespace Catalog.API.IntegrationEvents
{
public interface IIntegrationEventLogService
{
Task SaveEventAsync(IntegrationEvent @event);
Task MarkEventAsPublishedAsync(IntegrationEvent @event);
}
}

View File

@ -0,0 +1,51 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Events;
using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Storage;
using Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF;
using Microsoft.EntityFrameworkCore.Infrastructure;
namespace Catalog.API.IntegrationEvents
{
public class IntegrationEventLogService : IIntegrationEventLogService
{
private readonly IntegrationEventLogContext _integrationEventLogContext;
private readonly CatalogContext _catalogContext;
public IntegrationEventLogService(CatalogContext catalogContext)
{
_catalogContext = catalogContext;
_integrationEventLogContext = new IntegrationEventLogContext(
new DbContextOptionsBuilder<IntegrationEventLogContext>()
.UseSqlServer(catalogContext.Database.GetDbConnection())
.ConfigureWarnings(warnings => warnings.Throw(RelationalEventId.QueryClientEvaluationWarning))
.Options);
}
public Task SaveEventAsync(IntegrationEvent @event)
{
var eventLogEntry = new IntegrationEventLogEntry(@event);
// as a constraint this transaction has to be done together with a catalogContext transaction
_integrationEventLogContext.Database.UseTransaction(_catalogContext.Database.CurrentTransaction.GetDbTransaction());
_integrationEventLogContext.IntegrationEventLogs.Add(eventLogEntry);
return _integrationEventLogContext.SaveChangesAsync();
}
public Task MarkEventAsPublishedAsync(IntegrationEvent @event)
{
var eventLogEntry = _integrationEventLogContext.IntegrationEventLogs.Single(ie => ie.EventId == @event.Id);
eventLogEntry.TimesSent++;
eventLogEntry.State = EventStateEnum.Published;
_integrationEventLogContext.IntegrationEventLogs.Update(eventLogEntry);
return _integrationEventLogContext.SaveChangesAsync();
}
}
}

View File

@ -1,16 +1,19 @@
namespace Microsoft.eShopOnContainers.Services.Catalog.API namespace Microsoft.eShopOnContainers.Services.Catalog.API
{ {
using global::Catalog.API.IntegrationEvents;
using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Hosting;
using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure; using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Abstractions; using Microsoft.eShopOnContainers.BuildingBlocks.EventBus.Abstractions;
using Microsoft.eShopOnContainers.BuildingBlocks.EventBusRabbitMQ; using Microsoft.eShopOnContainers.BuildingBlocks.EventBusRabbitMQ;
using Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF;
using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure; using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure;
using Microsoft.Extensions.Configuration; using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Logging; using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options; using Microsoft.Extensions.Options;
using System.Data.SqlClient;
using System.Reflection; using System.Reflection;
public class Startup public class Startup
@ -36,15 +39,23 @@
public void ConfigureServices(IServiceCollection services) public void ConfigureServices(IServiceCollection services)
{ {
var sqlConnection = new SqlConnection(Configuration["ConnectionString"]);
services.AddDbContext<CatalogContext>(c => services.AddDbContext<CatalogContext>(c =>
{ {
c.UseSqlServer(Configuration["ConnectionString"]); c.UseSqlServer(sqlConnection);
// Changing default behavior when client evaluation occurs to throw. // Changing default behavior when client evaluation occurs to throw.
// Default in EF Core would be to log a warning when client evaluation is performed. // Default in EF Core would be to log a warning when client evaluation is performed.
c.ConfigureWarnings(warnings => warnings.Throw(RelationalEventId.QueryClientEvaluationWarning)); c.ConfigureWarnings(warnings => warnings.Throw(RelationalEventId.QueryClientEvaluationWarning));
//Check Client vs. Server evaluation: https://docs.microsoft.com/en-us/ef/core/querying/client-eval //Check Client vs. Server evaluation: https://docs.microsoft.com/en-us/ef/core/querying/client-eval
}); });
services.AddDbContext<IntegrationEventLogContext>(c =>
{
c.UseSqlServer(sqlConnection, b => b.MigrationsAssembly("Catalog.API"));
c.ConfigureWarnings(warnings => warnings.Throw(RelationalEventId.QueryClientEvaluationWarning));
});
services.Configure<Settings>(Configuration); services.Configure<Settings>(Configuration);
// Add framework services. // Add framework services.
@ -70,6 +81,8 @@
.AllowCredentials()); .AllowCredentials());
}); });
services.AddTransient<IIntegrationEventLogService, IntegrationEventLogService>();
var serviceProvider = services.BuildServiceProvider(); var serviceProvider = services.BuildServiceProvider();
var configuration = serviceProvider.GetRequiredService<IOptionsSnapshot<Settings>>().Value; var configuration = serviceProvider.GetRequiredService<IOptionsSnapshot<Settings>>().Value;
services.AddSingleton<IEventBus>(new EventBusRabbitMQ(configuration.EventBusConnection)); services.AddSingleton<IEventBus>(new EventBusRabbitMQ(configuration.EventBusConnection));
@ -77,7 +90,7 @@
services.AddMvc(); services.AddMvc();
} }
public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory) public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory, IntegrationEventLogContext integrationEventLogContext)
{ {
//Configure logs //Configure logs
@ -98,9 +111,10 @@
//Seed Data //Seed Data
CatalogContextSeed.SeedAsync(app, loggerFactory) CatalogContextSeed.SeedAsync(app, loggerFactory)
.Wait(); .Wait();
integrationEventLogContext.Database.Migrate();
} }
} }
} }