Docker由.Net Core NUnit Test和Redis组成



我有一个.Net Core解决方案,其中包含一个API和NUnit测试。当我运行docker-compose up时,如果我不包括测试,API工作正常。然而,如果我实现了测试,那么docker-compose就无法构建,并出现错误命令行中的StackExchange.Redis.RedisConnectionException : It was not possible to connect to the redis server(s). UnableToConnect on redis-service:6379/Interactive

我的Dockerfile:

FROM mcr.microsoft.com/dotnet/core/aspnet:3.1-buster-slim AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM mcr.microsoft.com/dotnet/core/sdk:3.1-buster AS build
WORKDIR /src
COPY ["ReportApi/ReportApi.csproj", "ReportApi/"]
COPY ["ReportApi.Test/ReportApi.Test.csproj", "ReportApi.Test/"]RUN dotnet restore "ReportApi/ReportApi.csproj"
RUN dotnet restore "ReportApi.Test/ReportApi.Test.csproj"
COPY . .
WORKDIR "/src/ReportApi"
RUN dotnet build "ReportApi.csproj" -c Release -o /app/build
WORKDIR "/src/ReportApi.Test"
RUN dotnet build "ReportApi.Test.csproj" -c Release -o /app/build

FROM build AS publish
WORKDIR "/src/ReportApi"
RUN dotnet publish "ReportApi.csproj" -c Release -o /app/publish
WORKDIR "/src/ReportApi.Test"
RUN dotnet test "ReportApi.Test.csproj" -c Release -o /app/publish
FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .
ENTRYPOINT ["dotnet", "ReportApi.dll"]

我的docker-compose.yml:

version: "3.7"
services: 
redis-service:
container_name: redis
image: redis
ports:
- "6379:6379"
restart: always
report-api:
build: 
context: .
dockerfile: Dockerfile
ports: 
- "10001:80"
depends_on: 
- "redis-service"

我的测试课程:

namespace ReportApi.Test
{
class RedisCacheControllerTest
{
public IDatabase Cache { get; set; }
public RedisCacheController Controller { get; set; }
[SetUp]
public void Init()
{
// Set up Redis Cache
var redis = ConnectionMultiplexer.Connect("redis-service:6379");
var services = new ServiceCollection();
services.AddScoped(s => redis.GetDatabase());
var provider = services.BuildServiceProvider();
Cache = provider.GetService<IDatabase>();
// Create controller instance
Controller = new RedisCacheController(Cache);
}
[Test]
public void InsertRecordTest()
{
// Create a new instance of RedisCache
RedisCache redisCache = new RedisCache()
{
id = "testId",
value = "CacheData"
};
// If the redisCache object doesn't exist, check if it returns 200 OK;
// otherwise check if it returns 409 Conflict
if (Cache.StringGet(redisCache.id).Length() == 0)
{
Assert.IsInstanceOf<OkObjectResult>(Controller.Create(redisCache));
}
else
{
Assert.IsInstanceOf<ConflictObjectResult>(Controller.Create(redisCache));
}
}
[Test]
public void RetrieveRecordTest()
{
string key = "testId";
// If the record exists, check if it returns 200 OK;
// otherwise check if it returns 204 No Content
if (Cache.StringGet(key).Length() != 0)
{
Assert.IsInstanceOf<OkObjectResult>(Controller.Get(key));
}
else
{
Assert.IsInstanceOf<NoContentResult>(Controller.Get(key));
}
}
}
}

Redis是在docker-compose.yml中定义的,只有当每个服务(在其中定义(都已经构建好时,它才会运行。

因此,在构建Dockerfile的时候,还没有从docker-compose运行任何内容。

在互联网上,人们在这种情况下会采取不同的方法进行补救,例如:https://medium.com/@christiansparre/集成测试-与核心组件和可视化研究团队服务-83a1166055a8

但是,无论如何,我建议您在构建Dockerfile时不要运行测试。相反,从docker-compose.yml(上面的链接(运行它们。

您当前使用的方法的目标是确保在创建时已经测试了容器的图像。但是,你对此没有任何看法。如果您的测试在镜像构建后失败,只需删除并不使用它,没有人要求您运行keep容器,如果它不起作用。