add docker config

This commit is contained in:
Aaron Po
2026-02-03 23:02:07 -05:00
parent 2ae99d5224
commit 9bfbed9b92
13 changed files with 257 additions and 40 deletions

25
src/Core/.dockerignore Normal file
View File

@@ -0,0 +1,25 @@
**/.dockerignore
**/.env
**/.git
**/.gitignore
**/.project
**/.settings
**/.toolstarget
**/.vs
**/.vscode
**/.idea
**/*.*proj.user
**/*.dbmdl
**/*.jfm
**/azds.yaml
**/bin
**/charts
**/docker-compose*
**/Dockerfile*
**/node_modules
**/npm-debug.log
**/obj
**/secrets.dev.yaml
**/values.dev.yaml
LICENSE
README.md

View File

@@ -4,6 +4,7 @@
<Nullable>enable</Nullable>
<ImplicitUsings>enable</ImplicitUsings>
<RootNamespace>WebAPI</RootNamespace>
<DockerDefaultTargetOS>Linux</DockerDefaultTargetOS>
</PropertyGroup>
<ItemGroup>
@@ -19,4 +20,10 @@
<ProjectReference Include="..\..\Repository\Repository.Core\Repository.Core.csproj" />
<ProjectReference Include="..\..\Service\Service.Core\Service.Core.csproj" />
</ItemGroup>
<ItemGroup>
<Content Include="..\..\.dockerignore">
<Link>.dockerignore</Link>
</Content>
</ItemGroup>
</Project>

View File

@@ -0,0 +1,26 @@
FROM mcr.microsoft.com/dotnet/aspnet:10.0 AS base
ARG APP_UID=1000
USER $APP_UID
WORKDIR /app
EXPOSE 8080
EXPOSE 8081
FROM mcr.microsoft.com/dotnet/sdk:10.0 AS build
ARG BUILD_CONFIGURATION=Release
WORKDIR /src
COPY ["API/API.Core/API.Core.csproj", "API/API.Core/"]
COPY ["Repository/Repository.Core/Repository.Core.csproj", "Repository/Repository.Core/"]
COPY ["Service/Service.Core/Service.Core.csproj", "Service/Service.Core/"]
RUN dotnet restore "API/API.Core/API.Core.csproj"
COPY . .
WORKDIR "/src/API/API.Core"
RUN dotnet build "./API.Core.csproj" -c $BUILD_CONFIGURATION -o /app/build
FROM build AS publish
ARG BUILD_CONFIGURATION=Release
RUN dotnet publish "./API.Core.csproj" -c $BUILD_CONFIGURATION -o /app/publish /p:UseAppHost=false
FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .
ENTRYPOINT ["dotnet", "API.Core.dll"]

View File

@@ -10,6 +10,17 @@ builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
builder.Services.AddOpenApi();
// Add health checks
builder.Services.AddHealthChecks();
// Configure logging for container output
builder.Logging.ClearProviders();
builder.Logging.AddConsole();
if (!builder.Environment.IsProduction())
{
builder.Logging.AddDebug();
}
// Dependency Injection
builder.Services.AddSingleton<ISqlConnectionFactory, DefaultSqlConnectionFactory>();
builder.Services.AddScoped<IUserAccountRepository, UserAccountRepository>();
@@ -17,6 +28,7 @@ builder.Services.AddScoped<IUserService, UserService>();
builder.Services.AddScoped<IUserCredentialRepository, UserCredentialRepository>();
builder.Services.AddScoped<IAuthService, AuthService>();
builder.Services.AddScoped<IJwtService, JwtService>();
var app = builder.Build();
app.UseSwagger();
@@ -24,6 +36,18 @@ app.UseSwaggerUI();
app.MapOpenApi();
app.UseHttpsRedirection();
// Health check endpoint (used by Docker health checks and orchestrators)
app.MapHealthChecks("/health");
app.MapControllers();
app.MapFallbackToController("Handle404", "NotFound");
// Graceful shutdown handling
var lifetime = app.Services.GetRequiredService<IHostApplicationLifetime>();
lifetime.ApplicationStopping.Register(() =>
{
app.Logger.LogInformation("Application is shutting down gracefully...");
});
app.Run();

View File

@@ -2,7 +2,18 @@
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning"
"Microsoft.AspNetCore": "Information",
"Microsoft.EntityFrameworkCore": "Information"
},
"Console": {
"IncludeScopes": true,
"TimestampFormat": "yyyy-MM-ddTHH:mm:ss.fffZ"
}
},
"AllowedHosts": "*",
"Jwt": {
"ExpirationMinutes": 120,
"Issuer": "biergarten-api",
"Audience": "biergarten-users"
}
}

View File

@@ -0,0 +1,19 @@
{
"Logging": {
"LogLevel": {
"Default": "Warning",
"Microsoft.AspNetCore": "Warning",
"Microsoft.EntityFrameworkCore": "Error"
},
"Console": {
"IncludeScopes": false,
"TimestampFormat": "yyyy-MM-ddTHH:mm:ss.fffZ"
}
},
"AllowedHosts": "*",
"Jwt": {
"ExpirationMinutes": 60,
"Issuer": "biergarten-api",
"Audience": "biergarten-users"
}
}

View File

@@ -2,8 +2,23 @@
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft.AspNetCore": "Warning"
"Microsoft.AspNetCore": "Warning",
"Microsoft.EntityFrameworkCore": "Information"
},
"Console": {
"IncludeScopes": true,
"TimestampFormat": "yyyy-MM-ddTHH:mm:ss.fffZ"
}
},
"AllowedHosts": "*"
"AllowedHosts": "*",
"ConnectionStrings": {
"DefaultConnection": ""
},
"Jwt": {
"SecretKey": "",
"ExpirationMinutes": 60,
"Issuer": "biergarten-api",
"Audience": "biergarten-users"
}
}

View File

@@ -12,6 +12,7 @@
<PackageReference Include="xunit" Version="2.9.2" />
<PackageReference Include="xunit.runner.visualstudio" Version="2.8.2" />
<PackageReference Include="FluentAssertions" Version="6.9.0" />
<PackageReference Include="dbup" Version="5.0.41" />
<!-- Reqnroll core, xUnit adapter and code-behind generator -->
<PackageReference Include="Reqnroll" Version="3.3.3" />
@@ -33,5 +34,6 @@
<ItemGroup>
<ProjectReference Include="..\API.Core\API.Core.csproj" />
<ProjectReference Include="..\..\Database\Database.Core\Database.Core.csproj" />
</ItemGroup>
</Project>

View File

@@ -1,17 +1,17 @@
<Solution>
<Folder Name="/API/" >
<Project Path="API/API.Core/API.Core.csproj"/>
<Project Path="API/API.Specs/API.Specs.csproj"/>
<Folder Name="/API/">
<Project Path="API/API.Core/API.Core.csproj" />
<Project Path="API/API.Specs/API.Specs.csproj" />
</Folder>
<Folder Name="/Database/">
<Project Path="Database/Database.Core/Database.Core.csproj" />
<Project Path="Database/Database.Seed/Database.Seed.csproj" />
</Folder>
<Folder Name="/Repository/" >
<Project Path="Repository/Repository.Core/Repository.Core.csproj"/>
<Project Path="Repository/Repository.Tests/Repository.Tests.csproj"/>
<Folder Name="/Repository/">
<Project Path="Repository/Repository.Core/Repository.Core.csproj" />
<Project Path="Repository/Repository.Tests/Repository.Tests.csproj" />
</Folder>
<Folder Name="/Service/">
<Project Path="Service/Service.Core/Service.Core.csproj"/>
<Project Path="Service/Service.Core/Service.Core.csproj" />
</Folder>
</Solution>