Skip to content

Commit cb94259

Browse files
author
ericuss
committed
Migrate catalog functional tests
1 parent 2e0dadf commit cb94259

5 files changed

Lines changed: 90 additions & 5 deletions

File tree

Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
using Microsoft.EntityFrameworkCore;
2+
using Microsoft.Extensions.Configuration;
3+
using System;
4+
using Microsoft.Extensions.DependencyInjection;
5+
using Microsoft.Extensions.Logging;
6+
using Polly;
7+
using System.Data.SqlClient;
8+
using Microsoft.AspNetCore.Hosting;
9+
10+
namespace Catalog.API.Extensions
11+
{
12+
public static class WebHostExtensions
13+
{
14+
public static bool IsInKubernetes(this IWebHost host)
15+
{
16+
var cfg = host.Services.GetService<IConfiguration>();
17+
var orchestratorType = cfg.GetValue<string>("OrchestratorType");
18+
return orchestratorType?.ToUpper() == "K8S";
19+
}
20+
21+
public static IWebHost MigrateDbContext<TContext>(this IWebHost host, Action<TContext, IServiceProvider> seeder) where TContext : DbContext
22+
{
23+
var underK8s = host.IsInKubernetes();
24+
25+
using (var scope = host.Services.CreateScope())
26+
{
27+
var services = scope.ServiceProvider;
28+
29+
var logger = services.GetRequiredService<ILogger<TContext>>();
30+
31+
var context = services.GetService<TContext>();
32+
33+
try
34+
{
35+
logger.LogInformation("Migrating database associated with context {DbContextName}", typeof(TContext).Name);
36+
37+
if (underK8s)
38+
{
39+
InvokeSeeder(seeder, context, services);
40+
}
41+
else
42+
{
43+
var retry = Policy.Handle<SqlException>()
44+
.WaitAndRetry(new TimeSpan[]
45+
{
46+
TimeSpan.FromSeconds(3),
47+
TimeSpan.FromSeconds(5),
48+
TimeSpan.FromSeconds(8),
49+
});
50+
51+
//if the sql server container is not created on run docker compose this
52+
//migration can't fail for network related exception. The retry options for DbContext only
53+
//apply to transient exceptions
54+
// Note that this is NOT applied when running some orchestrators (let the orchestrator to recreate the failing service)
55+
retry.Execute(() => InvokeSeeder(seeder, context, services));
56+
}
57+
58+
logger.LogInformation("Migrated database associated with context {DbContextName}", typeof(TContext).Name);
59+
}
60+
catch (Exception ex)
61+
{
62+
logger.LogError(ex, "An error occurred while migrating the database used on context {DbContextName}", typeof(TContext).Name);
63+
if (underK8s)
64+
{
65+
throw; // Rethrow under k8s because we rely on k8s to re-run the pod
66+
}
67+
}
68+
}
69+
70+
return host;
71+
}
72+
73+
private static void InvokeSeeder<TContext>(Action<TContext, IServiceProvider> seeder, TContext context, IServiceProvider services)
74+
where TContext : DbContext
75+
{
76+
context.Database.Migrate();
77+
seeder(context, services);
78+
}
79+
}
80+
}

src/Services/Catalog/Catalog.API/Program.cs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,6 @@ public static int Main(string[] args)
6868
private static IHostBuilder CreateHostBuilder(IConfiguration configuration, string[] args) =>
6969
Host.CreateDefaultBuilder(args)
7070
.ConfigureServices(services => services.AddAutofac())
71-
.UseServiceProviderFactory(new AutofacServiceProviderFactory())
7271
.ConfigureWebHostDefaults(builder =>
7372
{
7473
builder.CaptureStartupErrors(false)

src/Services/Catalog/Catalog.API/Startup.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ public Startup(IConfiguration configuration)
4444

4545
public IConfiguration Configuration { get; }
4646

47-
public void ConfigureServices(IServiceCollection services)
47+
public IServiceProvider ConfigureServices(IServiceCollection services)
4848
{
4949
services.AddAppInsight(Configuration)
5050
.AddGrpc().Services
@@ -59,6 +59,7 @@ public void ConfigureServices(IServiceCollection services)
5959
var container = new ContainerBuilder();
6060
container.Populate(services);
6161

62+
return new AutofacServiceProvider(container.Build());
6263
}
6364

6465
public void Configure(IApplicationBuilder app, IWebHostEnvironment env, ILoggerFactory loggerFactory)

src/Services/Catalog/Catalog.FunctionalTests/Catalog.FunctionalTests.csproj

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@
3333
</ItemGroup>
3434

3535
<ItemGroup>
36-
<PackageReference Include="Microsoft.AspNetCore.Mvc.Testing" Version="2.2.0" />
36+
<PackageReference Include="Microsoft.AspNetCore.Mvc.Testing" Version="$(Microsoft_AspNetCore_Mvc_Testing)" />
3737
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="$(Microsoft_NET_Test_Sdk)" />
3838
<PackageReference Include="Microsoft.AspNetCore.TestHost" Version="$(Microsoft_AspNetCore_TestHost)" />
3939
<PackageReference Include="xunit" Version="$(xunit)" />

src/Services/Catalog/Catalog.FunctionalTests/CatalogScenarioBase.cs

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,13 @@
1+
using Autofac.Extensions.DependencyInjection;
2+
using Catalog.API.Extensions;
13
using Microsoft.AspNetCore.Hosting;
24
using Microsoft.AspNetCore.TestHost;
35
using Microsoft.eShopOnContainers.BuildingBlocks.IntegrationEventLogEF;
46
using Microsoft.eShopOnContainers.Services.Catalog.API;
57
using Microsoft.eShopOnContainers.Services.Catalog.API.Infrastructure;
68
using Microsoft.Extensions.Configuration;
79
using Microsoft.Extensions.DependencyInjection;
10+
using Microsoft.Extensions.Hosting;
811
using Microsoft.Extensions.Logging;
912
using Microsoft.Extensions.Options;
1013
using System.IO;
@@ -25,14 +28,16 @@ public TestServer CreateServer()
2528
{
2629
cb.AddJsonFile("appsettings.json", optional: false)
2730
.AddEnvironmentVariables();
28-
}).UseStartup<Startup>();
31+
})
32+
.UseStartup<Startup>();
33+
2934

3035
var testServer = new TestServer(hostBuilder);
3136

3237
testServer.Host
3338
.MigrateDbContext<CatalogContext>((context, services) =>
3439
{
35-
var env = services.GetService<IHostingEnvironment>();
40+
var env = services.GetService<IWebHostEnvironment>();
3641
var settings = services.GetService<IOptions<CatalogSettings>>();
3742
var logger = services.GetService<ILogger<CatalogContextSeed>>();
3843

0 commit comments

Comments
 (0)