Adds Docker support and updates dependencies#42
Conversation
Introduces Dockerfile and docker-compose for containerization. Refactors project structure and moves external services to their own project. Updates dependencies to the latest versions and fixes related issues. Also adds .dockerignore to exclude unnecessary files during build.
WalkthroughAtualiza a infraestrutura de containerização (Dockerfile multi-stage, docker-compose, .dockerignore, perfis de lançamento), centraliza e atualiza versões de pacotes, migra referências para InvoiceReminder.ExternalServices, refatora ConfigurationService para receber IConfiguration e ajusta DI/tests conforme o novo fluxo de configuração. Changes
Sequence Diagram(s)sequenceDiagram
autonumber
participant App as Aplicação / Host
participant DI as Contêiner DI
participant CfgRoot as IConfiguration (root)
participant ConfigSvc as ConfigurationService
App->>DI: Registra IConfiguration (appsettings + env + user secrets)
App->>ConfigSvc: new ConfigurationService(IConfiguration)
ConfigSvc->>ConfigSvc: Constrói ConfigurationBuilder\nAddConfiguration + AddJsonFiles + AddEnvironmentVariables\n(Dev -> AddUserSecrets)
ConfigSvc-->>App: Instância pronta
App->>ConfigSvc: GetConnectionString("DatabaseConnection")
ConfigSvc-->>App: connection string ou null/default
App->>ConfigSvc: GetSecret("Section","Key") / GetSecret("Section","Key__Name")
ConfigSvc-->>App: secret ou null/default
Estimated code review effort🎯 4 (Complex) | ⏱️ ~45 minutos Possibly related PRs
Poem
✨ Finishing Touches
🧪 Generate unit tests
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. 🪧 TipsChatThere are 3 ways to chat with CodeRabbit:
SupportNeed help? Create a ticket on our support page for assistance with any issues or questions. CodeRabbit Commands (Invoked using PR/Issue comments)Type Other keywords and placeholders
CodeRabbit Configuration File (
|
There was a problem hiding this comment.
Actionable comments posted: 11
🧹 Nitpick comments (21)
InvoiceReminder.Application.UnitTests/InvoiceReminder.Application.UnitTests.csproj (1)
1-1: Remover BOM (caractere invisível) no início do arquivoHá um BOM UTF-8 antes da tag . Evite-o para reduzir diffs desnecessários entre plataformas/editores.
Aplique este diff para remover o BOM:
-<Project Sdk="MSTest.Sdk/3.10.2"> +<Project Sdk="MSTest.Sdk/3.10.2">InvoiceReminder.UnitTests.Assets/InvoiceReminder.UnitTests.Assets.csproj (1)
1-1: Evitar BOM UTF-8 no início do arquivoHá um caractere BOM antes de . Remova para manter consistência.
-<Project Sdk="MSTest.Sdk/3.10.2"> +<Project Sdk="MSTest.Sdk/3.10.2">InvoiceReminder.ExternalServices.UnitTests/InvoiceReminder.ExternalServices.UnitTests.csproj (1)
1-1: Remover BOM no início do arquivoHá um BOM UTF-8 antes da tag .
-<Project Sdk="MSTest.Sdk/3.10.2"> +<Project Sdk="MSTest.Sdk/3.10.2">.dockerignore (1)
27-30: Reinclusão de metadados do Git no contexto de build — confirme necessidadeAs exceções para .git (HEAD/config/packed-refs/refs/heads) aumentam o contexto e podem afetar cache. Se não estiver usando BuildKit com
gitmetadata (ou versionamento viagit rev-parseno build), considere remover estas reinclusões.Gostaria que eu propusesse uma variante do Dockerfile que obtenha a versão via
--mount=type=bind,source=.git(BuildKit) sem precisar re-incluir arquivos do .git no contexto?InvoiceReminder.CrossCutting.IoC/DependencyInjectionConfig.cs (1)
133-133: Evitar “magic string” para o nome da connection stringConsidere extrair "DatabaseConnection" para uma constante compartilhada/Options fortemente tipadas (ex.: DatabaseOptions.ConnectionName) para reduzir risco de typos e facilitar manutenção.
InvoiceReminder.API/Dockerfile (2)
33-35: Torne explícito o diretório de trabalho no stage publishO
FROM build AS publishherda oWORKDIRda stage anterior, o que é frágil e pode quebrar em alterações futuras. Recomendo setar oWORKDIRexplicitamente antes dodotnet publish.Aplique:
FROM build AS publish ARG BUILD_CONFIGURATION=Release +WORKDIR "/src/InvoiceReminder.API" RUN dotnet publish "./InvoiceReminder.API.csproj" -c $BUILD_CONFIGURATION -o /app/publish /p:UseAppHost=false
30-30: Build redundante pode ser removido para reduzir tempo de buildO
dotnet publishrecompila; odotnet buildanterior não é utilizado no artefato final. Se não houver dependência explícita dessa etapa (ex.: debug do VS), você pode removê-la para acelerar builds.Aplique:
-RUN dotnet build "./InvoiceReminder.API.csproj" -c $BUILD_CONFIGURATION -o /app/builddocker-compose.yml (1)
2-12: Considere adicionar healthcheck e política de restartMelhora observabilidade e resiliência ao rodar standalone ou em CI.
Sugestão:
services: api: build: context: . dockerfile: InvoiceReminder.API/Dockerfile ports: - "8080:8080" - "8081:8081" env_file: - .env + healthcheck: + test: ["CMD", "wget", "--no-verbose", "--tries=1", "--spider", "http://localhost:8080/healthz"] + interval: 30s + timeout: 5s + retries: 3 + restart: unless-stoppedAjuste o endpoint do healthcheck conforme o endpoint de saúde disponível.
InvoiceReminder.API/Properties/launchSettings.json (1)
23-33: Perfil Docker pode falhar com HTTPS se o certificado não for injetadoO
useSSL: trueeASPNETCORE_HTTPS_PORTSexigem certificado no container. Em ambientes fora do Visual Studio, isso não ocorre automaticamente.
- Se for usar HTTPS apenas no VS, mantenha assim.
- Para execução fora do VS, ou configure o certificado (variáveis
ASPNETCORE_Kestrel__Certificates__Default__Path/...Password) ou remova ouseSSL/HTTPS.Além disso, defina o ambiente explicitamente para consistência:
"environmentVariables": { + "ASPNETCORE_ENVIRONMENT": "Development", "ASPNETCORE_HTTPS_PORTS": "8081", "ASPNETCORE_HTTP_PORTS": "8080" },InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (1)
59-62: Compatibilidade com DOTNET_ENVIRONMENTMuitos apps usam
DOTNET_ENVIRONMENT. Considere suportá-lo além deASPNETCORE_ENVIRONMENT.Aplique:
- return Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT") == "Development"; + var env = Environment.GetEnvironmentVariable("DOTNET_ENVIRONMENT") + ?? Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT"); + return string.Equals(env, "Development", StringComparison.OrdinalIgnoreCase);InvoiceReminder.DomainEntities.UnitTests/InvoiceReminder.DomainEntities.UnitTests.csproj (1)
1-1: Remover BOM (U+FEFF) no início do arquivoHá um caractere BOM antes da tag . Não quebra o build, mas pode gerar diffs desnecessários e problemas com algumas ferramentas.
Sugestão de ajuste mínimo:
-<Project Sdk="MSTest.Sdk/3.10.2"> +<Project Sdk="MSTest.Sdk/3.10.2">InvoiceReminder.Domain/InvoiceReminder.Domain.csproj (1)
12-12: Evitar provider de configuração na camada de Domínio (mover para o composition root)Adicionar Microsoft.Extensions.Configuration.EnvironmentVariables no projeto de Domínio tende a acoplar o domínio a providers de configuração. Idealmente, o domínio recebe IConfiguration (ou Options) já composto pela camada host (API, Job, etc.), que agrega appsettings, secrets e variáveis de ambiente — especialmente agora com Docker. Isso mantém o domínio mais puro e facilita testes.
Possíveis caminhos:
- Remover o PackageReference do Domínio e compor a IConfiguration (com AddEnvironmentVariables) apenas em projetos host.
- Se o Domínio não estiver criando ConfigurationBuilder internamente, este PackageReference pode ser removido sem impacto.
Se quiser, eu ajudo a preparar um commit movendo a composição para a API/Job e ajustando a injeção no IoC.
InvoiceReminder.JobScheduler.UnitTests/InvoiceReminder.JobScheduler.UnitTests.csproj (1)
16-16: Nova referência a ExternalServices no projeto de testesA referência ao InvoiceReminder.ExternalServices em testes de JobScheduler é plausível diante da reorganização. Só valide se os testes realmente dependem de tipos concretos da implementação; se o objetivo for apenas contratos/abstrações, preferir referenciar apenas esses contratos reduz o acoplamento.
InvoiceReminder.API/InvoiceReminder.API.csproj (1)
28-28: Tornar Microsoft.VisualStudio.Azure.Containers.Tools.Targets um pacote apenas de desenvolvimentoEste pacote fornece targets para integração com ferramentas de containers (VS/VS Code) e não precisa fluir transitivamente. Recomendo marcar como PrivateAssets=all para evitar influência em projetos consumidores e manter escopo de build/dev.
Aplicar:
- <PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" /> + <PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets"> + <PrivateAssets>all</PrivateAssets> + <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets> + </PackageReference>Directory.Packages.props (2)
37-38: Alinhar patches do Npgsql e do provider EF Core PostgreSQLPara reduzir riscos de incompatibilidades sutis, recomendo alinhar os patches de Npgsql e do provider EFCore. Como o provider está em 9.0.4, sugiro subir o Npgsql de 9.0.3 para 9.0.4 também.
Aplicar:
- <PackageVersion Include="Npgsql" Version="9.0.3" /> + <PackageVersion Include="Npgsql" Version="9.0.4" />Se preferirem, posso verificar em notas de versão se há correção relevante no 9.0.4 que justifique a padronização.
36-36: Containers.Tools.Targets no gerenciamento centralCentralizar a versão é ok, mas mantenham a recomendação de marcar como PrivateAssets=all nos projetos que usam (como sugerido no API.csproj) para evitar propagação transitive de assets de build para outros projetos.
InvoiceReminder.sln (1)
16-17: "2.3 - External Services" continua no .sln; confirmar se essa pasta deve ser removida ou mantidaO resumo diz que o bloco de solução “2.3 - External Services” foi removido e que InvoiceReminder.ExternalServices virou projeto de nível superior. Entretanto, a pasta de solução “2.3 - External Services” ainda está definida e, no mapeamento de NestedProjects (ver Linhas 156-157), o novo projeto é aninhado dentro dela. Alinhar intenção x estrutura final (ou atualizar o resumo).
InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs (4)
10-16: Boa prática: restaurar o ambiente entre testes — considere desabilitar paralelismoÓtimo capturar/restaurar ASPNETCORE_ENVIRONMENT. Porém, se o runner estiver paralelo, mexer em variável de ambiente global pode causar interferência entre testes/classe. Considere marcar a classe como não paralelizável.
Você pode anotar a classe assim (fora do trecho alterado):
using Microsoft.VisualStudio.TestTools.UnitTesting; [TestClass] [DoNotParallelize] public class ConfigurationServiceTests { // ... }Also applies to: 18-22
35-45: Nome do teste sugere validação de UserSecrets, mas não há assert específicoO teste apenas assegura que não lança exceção. Se a intenção é somente isso, renomeie para refletir o comportamento (ex.:
Constructor_DevelopmentEnvironment_DoesNotThrow). Caso contrário, considere validar a presença do provider de secrets (difícil sem expor a configuração interna).
47-56: Mesmo ponto do teste anterior: nome x assertO nome indica que não adiciona UserSecrets, mas o teste só garante que não lança. Recomendo alinhar o nome ao objetivo real ou criar assert mais específico (se viável).
86-99: Cobertura extra: connection string via "ConnectionStrings__Name"Vocês já testam
GetSecretcom__. Seria útil adicionar um teste análogo para connection strings comConnectionStrings__MyDbvia provider de env vars, garantindo que a convenção dupla underscore também funciona para connection strings.Posso esboçar o teste se acharem útil.
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (22)
.dockerignore(1 hunks)Directory.Packages.props(1 hunks)InvoiceReminder.API.UnitTests/InvoiceReminder.API.UnitTests.csproj(2 hunks)InvoiceReminder.API/Dockerfile(1 hunks)InvoiceReminder.API/InvoiceReminder.API.csproj(2 hunks)InvoiceReminder.API/Properties/launchSettings.json(1 hunks)InvoiceReminder.Application.UnitTests/InvoiceReminder.Application.UnitTests.csproj(1 hunks)InvoiceReminder.Application/InvoiceReminder.Application.csproj(1 hunks)InvoiceReminder.ArchitectureTests/InvoiceReminder.ArchitectureTests.csproj(2 hunks)InvoiceReminder.CrossCutting.IoC/DependencyInjectionConfig.cs(1 hunks)InvoiceReminder.CrossCutting.IoC/InvoiceReminder.CrossCutting.IoC.csproj(1 hunks)InvoiceReminder.Domain/InvoiceReminder.Domain.csproj(1 hunks)InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs(3 hunks)InvoiceReminder.DomainEntities.UnitTests/InvoiceReminder.DomainEntities.UnitTests.csproj(1 hunks)InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs(1 hunks)InvoiceReminder.ExternalServices.UnitTests/InvoiceReminder.ExternalServices.UnitTests.csproj(2 hunks)InvoiceReminder.Infrastructure.UnitTests/InvoiceReminder.Infrastructure.UnitTests.csproj(1 hunks)InvoiceReminder.JobScheduler.UnitTests/InvoiceReminder.JobScheduler.UnitTests.csproj(2 hunks)InvoiceReminder.JobScheduler/InvoiceReminder.JobScheduler.csproj(1 hunks)InvoiceReminder.UnitTests.Assets/InvoiceReminder.UnitTests.Assets.csproj(1 hunks)InvoiceReminder.sln(4 hunks)docker-compose.yml(1 hunks)
🧰 Additional context used
🧬 Code Graph Analysis (7)
InvoiceReminder.CrossCutting.IoC/DependencyInjectionConfig.cs (2)
InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (1)
GetConnectionString(29-32)InvoiceReminder.Domain/Services/Configuration/IConfigurationService.cs (2)
GetConnectionString(6-6)IConfigurationService(3-12)
InvoiceReminder.UnitTests.Assets/InvoiceReminder.UnitTests.Assets.csproj (5)
InvoiceReminder.DomainEntities.UnitTests/Entities/InvoiceTests.cs (1)
InvoiceTests(6-17)InvoiceReminder.ArchitectureTests/Domain/ExtensionsTests.cs (1)
ExtensionsTests(7-28)InvoiceReminder.Application.UnitTests/ViewModels/InvoiceViewModelTests.cs (1)
InvoiceViewModelTests(6-17)InvoiceReminder.UnitTests.Assets/PropertyTester.cs (1)
TestProperties(93-120)InvoiceReminder.ArchitectureTests/Presentation/EndpointsTests.cs (1)
EndpointsTests(7-43)
InvoiceReminder.Application.UnitTests/InvoiceReminder.Application.UnitTests.csproj (3)
InvoiceReminder.DomainEntities.UnitTests/Entities/InvoiceTests.cs (2)
InvoiceTests(6-17)TestProperties(9-16)InvoiceReminder.Application.UnitTests/ViewModels/InvoiceViewModelTests.cs (1)
InvoiceViewModelTests(6-17)InvoiceReminder.API.UnitTests/Endpoints/InvoiceEndpointsTests.cs (1)
InvoiceEndpointsTests(19-663)
InvoiceReminder.Infrastructure.UnitTests/InvoiceReminder.Infrastructure.UnitTests.csproj (4)
InvoiceReminder.DomainEntities.UnitTests/Entities/InvoiceTests.cs (2)
InvoiceTests(6-17)TestProperties(9-16)InvoiceReminder.ArchitectureTests/Domain/ExtensionsTests.cs (1)
ExtensionsTests(7-28)InvoiceReminder.API.UnitTests/Endpoints/InvoiceEndpointsTests.cs (1)
InvoiceEndpointsTests(19-663)InvoiceReminder.Application.UnitTests/ViewModels/InvoiceViewModelTests.cs (1)
InvoiceViewModelTests(6-17)
InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (2)
InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs (1)
ConfigurationService(24-31)InvoiceReminder.Domain/Services/Configuration/IConfigurationService.cs (2)
IConfigurationService(3-12)GetSecret(8-8)
InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs (3)
InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (7)
ConfigurationService(5-63)ConfigurationService(9-22)GetAppSetting(24-27)GetConnectionString(29-32)GetSecret(34-37)GetSecret(39-42)GetSecret(44-47)InvoiceReminder.CrossCutting.IoC/DependencyInjectionConfig.cs (1)
GetConnectionString(129-136)InvoiceReminder.Domain/Services/Configuration/IConfigurationService.cs (1)
IConfigurationService(3-12)
Directory.Packages.props (2)
InvoiceReminder.Data/Migrations/CoreDbContextModelSnapshot.cs (2)
BuildModel(18-257)CoreDbContextModelSnapshot(14-258)InvoiceReminder.Data/Migrations/20250509040148_Initial_Create.Designer.cs (2)
BuildTargetModel(19-258)Initial_Create(14-259)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
- GitHub Check: Analyze (csharp)
🔇 Additional comments (22)
InvoiceReminder.Application.UnitTests/InvoiceReminder.Application.UnitTests.csproj (1)
1-1: Atualização do MSTest.Sdk para 3.10.2 — OKMudança coerente com a padronização do repositório. Sem impactos aparentes.
InvoiceReminder.UnitTests.Assets/InvoiceReminder.UnitTests.Assets.csproj (1)
1-1: Atualização do MSTest.Sdk para 3.10.2 — OKAlinha a versão com os demais projetos de teste.
InvoiceReminder.ExternalServices.UnitTests/InvoiceReminder.ExternalServices.UnitTests.csproj (3)
1-1: MSTest.Sdk 3.10.2 — atualização corretaAlinhado ao restante da solução e ao Directory.Packages.props.
27-29: Atualização do caminho do ProjectReference — OKA referência foi atualizada para o novo projeto top-level InvoiceReminder.ExternalServices. Está correta para a estrutura descrita no PR.
27-29: Nenhuma referência ao caminho antigo encontradaA busca por referências a
InvoiceReminder.Services\InvoiceReminder.ExternalServices.csprojem arquivos.csprojnão retornou resultados, indicando que não há menções remanescentes ao caminho anterior.InvoiceReminder.API.UnitTests/InvoiceReminder.API.UnitTests.csproj (1)
1-1: Todas as versões do Sdk MSTest estão alinhadasVerificamos que:
- Todos os projetos de teste usam
<Project Sdk="MSTest.Sdk/3.10.2">.- Em
Directory.Packages.props, os pacotesMSTest.Analyzers,MSTest.TestAdaptereMSTest.TestFrameworktambém estão na versão3.10.2.Não há inconsistências de versionamento a serem ajustadas.
InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (1)
39-42: Boa abordagem para suportar ENV (__) e configuração hierárquica (:)A resolução priorizando
key:secretNamee fallback parakey__secretNamecobre bem cenários de JSON vs. variáveis de ambiente.InvoiceReminder.DomainEntities.UnitTests/InvoiceReminder.DomainEntities.UnitTests.csproj (1)
1-1: Bump do MSTest.Sdk para 3.10.2: OKAtualização consistente com o restante do PR e com o .NET 9.
InvoiceReminder.Infrastructure.UnitTests/InvoiceReminder.Infrastructure.UnitTests.csproj (1)
1-1: Upgrade do MSTest.Sdk: coerente e seguroA troca para MSTest.Sdk/3.10.2 é alinhada às demais suites de teste e ao .NET 9.
InvoiceReminder.JobScheduler.UnitTests/InvoiceReminder.JobScheduler.UnitTests.csproj (1)
1-1: Upgrade do MSTest.Sdk para 3.10.2: aprovadoMantém consistência entre projetos de teste e o Testing Platform.
InvoiceReminder.ArchitectureTests/InvoiceReminder.ArchitectureTests.csproj (2)
1-1: Atualização para MSTest.Sdk/3.10.2: OKCompatível com a suíte e sem impactos aparentes.
20-20: Adicionar ExternalServices às ArchitectureTests: faz sentidoPara validar regras de arquitetura envolvendo o novo projeto ExternalServices, esta referência é adequada.
InvoiceReminder.JobScheduler/InvoiceReminder.JobScheduler.csproj (1)
11-11: Verificação concluída: referências antigas removidas
Nenhuma referência ao caminho antigo (InvoiceReminder.Services/.../InvoiceReminder.ExternalServices.csproj) foi encontrada. As ocorrências deInvoiceReminder.ExternalServices.csprojregistradas apontam exclusivamente para o novo diretório em todos os projetos, conforme esperado.InvoiceReminder.API/InvoiceReminder.API.csproj (2)
8-8: DockerDefaultTargetOS=Linux: bom alinhamento com imagens LinuxConfigurar o alvo Docker para Linux é compatível com o uso de imagens .NET base Linux. Apenas garanta que o Dockerfile esteja baseado em imagens linux e que as portas/publicações no docker-compose acompanhem essa escolha.
Se quiser, posso validar o Dockerfile/Docker Compose para checar consistência de base image, portas e variáveis de ambiente.
15-15: LGTM: referência para ExternalServices atualizadaA referência está em linha com a nova estrutura do solution.
InvoiceReminder.CrossCutting.IoC/InvoiceReminder.CrossCutting.IoC.csproj (1)
13-13: LGTM: IoC como composition root referenciando ExternalServicesFaz sentido que o projeto de IoC agregue as implementações concretas (ExternalServices) para fazer o wiring de dependências. Apenas mantenha Domain/Application livres de referências a concreções.
Directory.Packages.props (1)
18-23: Consistência de pacotes centralizados confirmadaNão foram encontradas referências diretas a MSTest.Sdk em nenhum arquivo *.csproj, logo não é necessário adicionar
<PackageVersion Update="MSTest.Sdk" Version="3.10.2" />no Directory.Packages.props para manter consistência.
InvoiceReminder.sln (2)
28-29: "5 - Unit Tests" ainda existe; discrepância com o resumoO resumo aponta remoção do bloco “5 - Unit Tests”, mas ele segue presente no .sln, com diversos projetos aninhados (Linhas 158-166). Ajustar o resumo ou remover a pasta, se de fato não for mais desejada.
42-42: Verificação concluída: sem referências obsoletas ao caminho antigo
Executamos a busca nas entradas deProjectReferencee não há nenhuma referência a
InvoiceReminder.Services/InvoiceReminder.ExternalServices.csproj. Todos os projetos apontam corretamente para
..\InvoiceReminder.ExternalServices\InvoiceReminder.ExternalServices.csproj.InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs (3)
145-153: Bom teste cobrindo convenção de dupla underscoreValidar
Secrets__MySecretcobre o cenário comum de variáveis de ambiente em contêineres/orquestradores.
168-183: Boa cobertura para default em GetSecret com chave ausenteO teste garante que o fallback para defaultValue funciona como esperado.
24-31: Compatibilidade confirmada: Uso de C# 12/C# “collection expressions” é suportado
Os projetos estão configurados com<LangVersion>latest</LangVersion>e<TargetFramework>net9.0</TargetFramework>, garantindo que a expressão[]de C# 12 seja válida. Nenhuma alteração é necessária.Likely an incorrect or invalid review comment.
There was a problem hiding this comment.
Actionable comments posted: 14
🔭 Outside diff range comments (1)
InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (1)
59-62: Método IsDevelopment() pode não funcionar corretamente em contêineresO método verifica apenas
ASPNETCORE_ENVIRONMENT, mas em aplicações não-web ou serviços em background (como o JobScheduler mencionado no PR), a variável de ambiente pode serDOTNET_ENVIRONMENT. Isso é especialmente importante com a adição de suporte Docker.private static bool IsDevelopment() { - return Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT") == "Development"; + var aspNetEnv = Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT"); + var dotNetEnv = Environment.GetEnvironmentVariable("DOTNET_ENVIRONMENT"); + return aspNetEnv == "Development" || dotNetEnv == "Development"; }
🧹 Nitpick comments (13)
InvoiceReminder.Infrastructure.UnitTests/InvoiceReminder.Infrastructure.UnitTests.csproj (1)
1-1: BOM (byte order mark) no início do arquivoHá um BOM antes da tag
<Project>. Não é crítico, mas pode causar diffs ruidosos e inconsistência entre projetos. Se possível, padronize os.csprojpara UTF-8 sem BOM.InvoiceReminder.API/Properties/launchSettings.json (1)
34-36: Posicionamento do $schemaFunciona mesmo ao final, mas editores/IDE costumam reconhecer melhor o schema se estiver no topo do arquivo. Opcional mover a propriedade
$schemapara a primeira linha para melhorar a experiência de edição.docker-compose.yml (1)
4-11: Adicionar healthcheck e política de restart para robustez em dev/CIRecomendo incluir healthcheck (por ex., GET /health ou /scalar/v1 se aplicável) e restart: unless-stopped para melhorar resiliência local/CI.
Exemplo:
api: build: context: . dockerfile: InvoiceReminder.API/Dockerfile ports: - "8080:8080" - - "8081:8081" + # - "8081:8081" # ver comentário acima sobre HTTPS env_file: - .env + restart: unless-stopped + healthcheck: + test: ["CMD", "wget", "--no-verbose", "--tries=1", "--spider", "http://localhost:8080/health"] + interval: 10s + timeout: 3s + retries: 5InvoiceReminder.JobScheduler.UnitTests/InvoiceReminder.JobScheduler.UnitTests.csproj (1)
3-13: Defina IsPackable=false em projetos de testeEvita geração acidental de pacotes NuGet de projetos de teste.
<PropertyGroup> <TargetFramework>net9.0</TargetFramework> <LangVersion>latest</LangVersion> <ImplicitUsings>enable</ImplicitUsings> <Nullable>disable</Nullable> + <IsPackable>false</IsPackable> <!-- Displays error on console in addition to the log file. Note that this feature comes with a performance impact. For more information, visit https://learn.microsoft.com/dotnet/core/testing/unit-testing-platform-integration-dotnet-test#show-failure-per-test --> <TestingPlatformShowTestsFailure>true</TestingPlatformShowTestsFailure> </PropertyGroup>InvoiceReminder.Domain/InvoiceReminder.Domain.csproj (1)
12-12: Provider de variáveis de ambiente no projeto de Domain: mova para o composition rootIdealmente, o Domain depende apenas de abstrações (IConfiguration) e não referencia providers/concretudes. Registre EnvironmentVariables no host (API/JobScheduler/IoC) e injete IConfiguration no Domain.
Sugestão de remoção aqui e adição no projeto host:
<ItemGroup> <PackageReference Include="Microsoft.Extensions.Configuration.Binder" /> - <PackageReference Include="Microsoft.Extensions.Configuration.EnvironmentVariables" /> <PackageReference Include="Microsoft.Extensions.Configuration.FileExtensions" /> <PackageReference Include="Microsoft.Extensions.Configuration.UserSecrets" /> <PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" />InvoiceReminder.API/InvoiceReminder.API.csproj (1)
28-28: Evite vazar Containers.Tools.Targets como dependência transitivaApenas tooling de build/IDE. Marque como PrivateAssets=all para não transitar para consumidores.
- <PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" /> + <PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets"> + <PrivateAssets>all</PrivateAssets> + <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets> + </PackageReference>InvoiceReminder.API/Dockerfile (4)
15-17: Aprimorar cache: copie Directory.Packages.props diretamente para /srcCopiar o props para a raiz “/” funciona, mas é menos explícito. Copiar para /src alinha com o fluxo de restore por projeto e melhora a clareza do cache.
-# Adiciona o arquivo de versões centralizadas -COPY Directory.Packages.props ./ +# Adiciona o arquivo de versões centralizadas ao contexto de build dos projetos +COPY Directory.Packages.props /src/
27-31: Evitar restore duplicado no buildComo já foi executado dotnet restore antes, use --no-restore no build para otimizar etapas e cache.
-RUN dotnet build "./InvoiceReminder.API.csproj" -c $BUILD_CONFIGURATION -o /app/build +RUN dotnet build "./InvoiceReminder.API.csproj" -c $BUILD_CONFIGURATION -o /app/build --no-restore
33-35: Evitar restore duplicado no publishMesma otimização do build: acrescente --no-restore.
-RUN dotnet publish "./InvoiceReminder.API.csproj" -c $BUILD_CONFIGURATION -o /app/publish /p:UseAppHost=false +RUN dotnet publish "./InvoiceReminder.API.csproj" -c $BUILD_CONFIGURATION -o /app/publish /p:UseAppHost=false --no-restore
39-41: (Opcional) Definir ASPNETCORE_URLS para garantir bind no 8080Embora o runtime .NET em contêiner já use 8080/8081 por padrão, explicitar ASPNETCORE_URLS evita ambiguidades em ambientes heterogêneos.
FROM base AS final WORKDIR /app +ENV ASPNETCORE_URLS=http://0.0.0.0:8080 COPY --from=publish /app/publish . ENTRYPOINT ["dotnet", "InvoiceReminder.API.dll"]InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs (3)
10-16: Campo de ambiente deve aceitar null — evite warnings/erros com NRT.Environment.GetEnvironmentVariable pode retornar null. Marque o campo como nullable para evitar warning (ou erro se TreatWarningsAsErrors está ativo) e deixar o intent explícito.
Aplique:
- private string _originalEnvironment; + private string? _originalEnvironment;Also applies to: 18-22
86-99: Padronize usando o helper CreateService nas configurações in-memory.Para consistência e legibilidade, use o helper CreateService também neste teste.
Aplique:
- var service = new ConfigurationService(new ConfigurationBuilder() - .AddInMemoryCollection(new Dictionary<string, string> - { - ["ConnectionStrings:MyDb"] = "Server=.;Database=Test;" - }) - .Build()); + var service = CreateService(new() + { + ["ConnectionStrings:MyDb"] = "Server=.;Database=Test;" + });
33-45: Tests de construtor sem assert útil — consider ar validar efeito observável.Os testes de construtor apenas checam “não nulo”. Se a intenção é validar inclusão (ou não) de UserSecrets por ambiente, proponho validar algum comportamento observável (p.ex., carregar um valor simulado por UserSecrets quando Development). Caso isso não seja trivial, considere re-enquadrar o teste para refletir o objetivo ou convertê-lo em smoke test com nome condizente.
Also applies to: 47-57
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (22)
.dockerignore(1 hunks)Directory.Packages.props(1 hunks)InvoiceReminder.API.UnitTests/InvoiceReminder.API.UnitTests.csproj(2 hunks)InvoiceReminder.API/Dockerfile(1 hunks)InvoiceReminder.API/InvoiceReminder.API.csproj(2 hunks)InvoiceReminder.API/Properties/launchSettings.json(1 hunks)InvoiceReminder.Application.UnitTests/InvoiceReminder.Application.UnitTests.csproj(1 hunks)InvoiceReminder.Application/InvoiceReminder.Application.csproj(1 hunks)InvoiceReminder.ArchitectureTests/InvoiceReminder.ArchitectureTests.csproj(2 hunks)InvoiceReminder.CrossCutting.IoC/DependencyInjectionConfig.cs(1 hunks)InvoiceReminder.CrossCutting.IoC/InvoiceReminder.CrossCutting.IoC.csproj(1 hunks)InvoiceReminder.Domain/InvoiceReminder.Domain.csproj(1 hunks)InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs(3 hunks)InvoiceReminder.DomainEntities.UnitTests/InvoiceReminder.DomainEntities.UnitTests.csproj(1 hunks)InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs(1 hunks)InvoiceReminder.ExternalServices.UnitTests/InvoiceReminder.ExternalServices.UnitTests.csproj(2 hunks)InvoiceReminder.Infrastructure.UnitTests/InvoiceReminder.Infrastructure.UnitTests.csproj(1 hunks)InvoiceReminder.JobScheduler.UnitTests/InvoiceReminder.JobScheduler.UnitTests.csproj(2 hunks)InvoiceReminder.JobScheduler/InvoiceReminder.JobScheduler.csproj(1 hunks)InvoiceReminder.UnitTests.Assets/InvoiceReminder.UnitTests.Assets.csproj(1 hunks)InvoiceReminder.sln(4 hunks)docker-compose.yml(1 hunks)
🧰 Additional context used
🧬 Code Graph Analysis (4)
InvoiceReminder.CrossCutting.IoC/DependencyInjectionConfig.cs (1)
InvoiceReminder.Domain/Services/Configuration/IConfigurationService.cs (2)
GetConnectionString(6-6)IConfigurationService(3-12)
InvoiceReminder.ArchitectureTests/InvoiceReminder.ArchitectureTests.csproj (2)
InvoiceReminder.ArchitectureTests/Services/AppServicesTests.cs (1)
AppServicesTests(9-67)InvoiceReminder.ArchitectureTests/Domain/EntitiesTests.cs (1)
GivenDomainLayer_ThenShouldNotHaveAnyDependencies(10-22)
InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (1)
InvoiceReminder.Domain/Services/Configuration/IConfigurationService.cs (1)
IConfigurationService(3-12)
InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs (1)
InvoiceReminder.Domain/Services/Configuration/IConfigurationService.cs (1)
IConfigurationService(3-12)
🔇 Additional comments (27)
InvoiceReminder.UnitTests.Assets/InvoiceReminder.UnitTests.Assets.csproj (1)
1-1: Upgrade do MSTest.Sdk para 3.10.2: OKA atualização para
Sdk="MSTest.Sdk/3.10.2"está alinhada ao restante do PR e ao alvonet9.0. Nenhuma inconsistência aparente neste projeto.InvoiceReminder.Infrastructure.UnitTests/InvoiceReminder.Infrastructure.UnitTests.csproj (1)
1-1: Upgrade do MSTest.Sdk para 3.10.2: OKA migração para
Sdk="MSTest.Sdk/3.10.2"e o restante das referências (via central package management) parecem consistentes para a suíte de testes de Infra. Sem impacto funcional negativo aparente.InvoiceReminder.API/Properties/launchSettings.json (3)
9-12: Reordenação de propriedades (http): OKMover
dotnetRunMessageseapplicationUrlapósenvironmentVariablesnão altera comportamento. Mantém legibilidade.
19-22: Reordenação de propriedades (https): OKSem impacto funcional; URLs e ambiente permanecem corretos.
23-33: Perfil de execução em contêiner adicionado: verifique HTTPS/portsO perfil Docker está coerente com os ports (8080/8081) e a URL de lançamento. Dois pontos de atenção:
- HTTPS em container requer certificados configurados/montados. Verifique se a configuração de Kestrel/cert dev está operacional neste perfil; caso contrário, considere expor apenas HTTP ou configurar corretamente os certificados.
- Se o Dockerfile já expõe 8080/8081, essa configuração deve funcionar. Alternativamente, você pode definir
ASPNETCORE_URLS=http://+:8080;https://+:8081para maior previsibilidade em cenários fora do VS.Gostaria que eu validasse a presença de configuração de certificado para o perfil Docker e a consistência com o docker-compose?
InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (1)
16-19: Não há problemas com AddUserSecrets no container DockerVerificamos que:
- Todos os projetos têm a propriedade
<UserSecretsId>definida nos arquivos.csproj, o que garante que o atributo de assembly será gerado corretamente.- O Dockerfile não define
ASPNETCORE_ENVIRONMENT=Development, logo o blocoif (IsDevelopment())não será executado dentro do container – portanto, oAddUserSecrets<ConfigurationService>()nem será chamado em produção.- Há um teste automatizado (
Constructor_ProductionEnvironment_DoesNotAddUserSecrets) que valida esse comportamento.Como resultado, não é necessário adicionar tratamento de erro extra nem ajustes na configuração de Docker.
InvoiceReminder.API.UnitTests/InvoiceReminder.API.UnitTests.csproj (2)
1-1: Atualização do MSTest.Sdk aprovadaA atualização para a versão 3.10.2 está alinhada com as outras atualizações de pacotes MSTest no PR.
18-18: Nova referência ao projeto ExternalServices adicionada corretamenteA adição da referência ao projeto
InvoiceReminder.ExternalServicesestá consistente com a reestruturação do projeto mencionada nos objetivos do PR.InvoiceReminder.DomainEntities.UnitTests/InvoiceReminder.DomainEntities.UnitTests.csproj (1)
1-1: Atualização consistente do MSTest.SdkA versão 3.10.2 está alinhada com as atualizações em outros projetos de teste.
InvoiceReminder.Application.UnitTests/InvoiceReminder.Application.UnitTests.csproj (1)
1-1: Versão do MSTest.Sdk atualizada corretamenteAtualização consistente com os demais projetos de teste para a versão 3.10.2.
InvoiceReminder.Application/InvoiceReminder.Application.csproj (1)
20-20: Referência ao projeto ExternalServices atualizada com sucessoA mudança do caminho do projeto ExternalServices está alinhada com a reestruturação mencionada nos objetivos do PR, movendo serviços externos para seu próprio projeto.
docker-compose.yml (1)
8-9: Evite expor HTTPS (8081) sem certificados montados/configuradosMapear 8081:8081 sugere HTTPS no container. Sem certificados (volumes/ASP.NET Core dev-certs) o endpoint 8081 provavelmente não subirá ou ficará inútil. Considere remover 8081 ou montar certificados e definir variáveis necessárias.
Sugestão (se não houver certificados em uso no container):
ports: - "8080:8080" - - "8081:8081"Se for manter HTTPS, adicione volumes e variáveis conforme necessário (Kestrel/ASP.NET Core), por ex.:
ports: - "8080:8080" - "8081:8081" + environment: + - ASPNETCORE_HTTP_PORTS=8080 + - ASPNETCORE_HTTPS_PORTS=8081 + volumes: + - ~/.aspnet/https:/https:ro + - ~/.microsoft/usersecrets:/root/.microsoft/usersecrets:roInvoiceReminder.JobScheduler.UnitTests/InvoiceReminder.JobScheduler.UnitTests.csproj (1)
1-1: Atualização do MSTest.Sdk para 3.10.2: OKUso do Sdk com versão inline está consistente com MSTest v3. Sem objeções.
InvoiceReminder.CrossCutting.IoC/InvoiceReminder.CrossCutting.IoC.csproj (1)
13-13: Nenhuma referência órfã ao caminho antigo
A busca não retornou nenhuma ocorrência deInvoiceReminder.Services/InvoiceReminder.ExternalServices.csproj, confirmando que todos os.csprojjá apontam para o novo caminhoInvoiceReminder.ExternalServices\InvoiceReminder.ExternalServices.csproj.InvoiceReminder.API/InvoiceReminder.API.csproj (2)
8-8: DockerDefaultTargetOS=Linux: alinhado com o DockerfileDefinição coerente com a imagem Linux do Dockerfile. Sem pontos a ajustar.
15-15: Atualização da ProjectReference para ExternalServices: OKCaminho atualizado condiz com a nova estrutura. Sem ressalvas.
InvoiceReminder.ExternalServices.UnitTests/InvoiceReminder.ExternalServices.UnitTests.csproj (3)
1-1: Atualização do Sdk MSTest para 3.10.2 — OKAlinha com os bumps centralizados no Directory.Packages.props e com net9.0. Sem observações funcionais aqui.
27-29: Validação concluída — sem referências ao caminho antigoO comando de busca não encontrou nenhuma ocorrência de
..\InvoiceReminder.Services\InvoiceReminder.ExternalServices.csproj,
portanto não há resíduos de referências ao caminho anterior.
9-13: Nome da propriedade MSBuild confirmadoA grafia “TestingPlatformShowTestsFailure” está correta para exibir falhas por teste no modelo clássico de integração do Test Platform.
Pontos de atenção:
- Arquivo InvoiceReminder.ExternalServices.UnitTests/InvoiceReminder.ExternalServices.UnitTests.csproj (linhas 9–13) – a propriedade está corretamente definida como
<TestingPlatformShowTestsFailure>true</TestingPlatformShowTestsFailure>.- Se o seu pipeline de testes estiver usando o novo modo Microsoft.Testing.Platform (ativo via
dotnet.configou .NET 10+), essa propriedade não será aplicada. Nesse caso, forneça os argumentos através deTestingPlatformCommandLineArgumentsou ajuste diretamente as opções do test runner.InvoiceReminder.JobScheduler/InvoiceReminder.JobScheduler.csproj (1)
11-11: Ref. para ExternalServices atualizada — OKMoveu corretamente para ..\InvoiceReminder.ExternalServices\InvoiceReminder.ExternalServices.csproj. Sem impactos aparentes.
InvoiceReminder.ArchitectureTests/InvoiceReminder.ArchitectureTests.csproj (3)
1-1: Atualização do Sdk MSTest para 3.10.2 — OKConsistente com a migração geral. Mantém o alvo em net9.0.
20-20: Inclusão de ProjectReference para ExternalServices — OKFaz sentido para carregar o assembly nas regras de arquitetura (NetArchTest). Sem objeções.
8-13: Propriedade MSBuild confirmada
A propriedadeTestingPlatformShowTestsFailureestá correta conforme a documentação oficial do .NET (dotnet test –p:TestingPlatformShowTestsFailure=true). Não é necessária nenhuma alteração.InvoiceReminder.sln (2)
16-17: Resumo inconsistente: os nós de pasta "2.3 - External Services" e "5 - Unit Tests" ainda existem na solução.O resumo afirma que o placeholder “2.3 - External Services” foi substituído e que o nó “5 - Unit Tests” foi removido. Porém, o arquivo mantém ambos os nós (Linhas 16-17 e 28-29), e os projetos de testes estão devidamente aninhados sob “5 - Unit Tests”. Sem problema funcional aqui, apenas divergência do resumo.
Also applies to: 28-29
42-42: Tudo verificado: referência ao InvoiceReminder.ExternalServices está corretaO arquivo
InvoiceReminder.ExternalServices/InvoiceReminder.ExternalServices.csprojexiste, está referenciado naInvoiceReminder.sln(linha 42) e o GUID{F2EB382B-25E4-43D8-8159-53DB5085DED6}aparece corretamente nos blocos de configuração (linhas 103–106) e de aninhamento (linhas 156–157).
Nenhuma ação adicional é necessária.InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs (2)
254-269: DTO de teste com Equals/GetHashCode — bom para asserções de igualdade.A presença de Equals/GetHashCode aqui viabiliza as asserções ShouldBe no cenário “WithDefault”. Após a remoção do tipo aninhado (Linhas 189-193), este tipo será usado nas asserções corretamente.
24-31: Nenhuma ação necessária: C# 12+ já está configurado
Todos os projetos usam<LangVersion>latest</LangVersion>e<TargetFramework>net9.0</TargetFramework>, garantindo suporte à expressão de coleção[].
Streamlines project dependencies by removing unnecessary external service references from unit tests and application layers. Updates Dockerfile to define APP_UID as an argument for better flexibility. Configures central package version management and transitive pinning for more consistent dependency resolution. Updates configuration loading to correctly handle environment-specific settings. Adds `PrivateAssets="all"` attribute to several package references to improve build performance and reduce output size. Excludes `TestResults` from Docker image.
There was a problem hiding this comment.
Actionable comments posted: 0
♻️ Duplicate comments (4)
.dockerignore (1)
28-28: Boa correção: Dockerfile da API reintroduzido no contexto de buildA exceção
!InvoiceReminder.API/Dockerfileresolve o problema anteriormente apontado de o Dockerfile ficar fora do contexto e quebrar odocker build/docker compose build.InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (2)
45-48: Superfície silenciosa de erro ao buscar secrets; sugerir log/erro descritivo quando não encontradoAtualmente retorna null silenciosamente quando as chaves não existem, o que dificulta diagnóstico (especialmente em Docker/prod). Proponho registrar em Development e considerar lançar exceção (ou deixe apenas o log e use o overload com default quando apropriado).
public string GetSecret(string key, string secretName) { - return _configuration[$"{key}:{secretName}"] ?? _configuration[$"{key}__{secretName}"]; + var colonKey = $"{key}:{secretName}"; + var underscoreKey = $"{key}__{secretName}"; + var value = _configuration[colonKey] ?? _configuration[underscoreKey]; + + if (value == null) + { + // Evita falhas silenciosas em Dev; em Prod, avalie lançar InvalidOperationException + System.Diagnostics.Debug.WriteLine( + $"[Configuration] Secret não encontrado para '{colonKey}' ou '{underscoreKey}'."); + } + + return value; }
9-28: Evite reconstruir IConfiguration aqui (duplicação de provedores e possível inversão de precedência); prefira pass-through no composition rootReconstruir a configuração dentro do serviço pode duplicar provedores (JSON, env vars, secrets) já presentes no host, aumentar consumo de memória e alterar precedência inesperadamente. Mantenha a composição no host/IoC e use o IConfiguration injetado como está.
Opção A (recomendada): pass-through simples
- public ConfigurationService(IConfiguration configuration) - { - var environment = configuration["ASPNETCORE_ENVIRONMENT"] - ?? Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT") - ?? "Production"; - - var builder = new ConfigurationBuilder() - .AddConfiguration(configuration) - .AddJsonFile("appsettings.json", optional: true, reloadOnChange: true) - .AddJsonFile($"appsettings.{environment}.json", optional: true, reloadOnChange: true); - - if (string.Equals(environment, "Development", StringComparison.OrdinalIgnoreCase)) - { - _ = builder.AddUserSecrets<ConfigurationService>(); - } - - _ = builder.AddEnvironmentVariables(); - - _configuration = builder.Build(); - } + public ConfigurationService(IConfiguration configuration) + { + _configuration = configuration ?? throw new ArgumentNullException(nameof(configuration)); + }Opção B (se insistir em montar aqui): inclua fallback para DOTNET_ENVIRONMENT e mantenha a ordem “UserSecrets antes de EnvVars”
public ConfigurationService(IConfiguration configuration) { - var environment = configuration["ASPNETCORE_ENVIRONMENT"] - ?? Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT") - ?? "Production"; + var environment = configuration["ASPNETCORE_ENVIRONMENT"] + ?? configuration["DOTNET_ENVIRONMENT"] + ?? Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT") + ?? Environment.GetEnvironmentVariable("DOTNET_ENVIRONMENT") + ?? "Production"; var builder = new ConfigurationBuilder() .AddConfiguration(configuration) .AddJsonFile("appsettings.json", optional: true, reloadOnChange: true) .AddJsonFile($"appsettings.{environment}.json", optional: true, reloadOnChange: true); if (string.Equals(environment, "Development", StringComparison.OrdinalIgnoreCase)) { - _ = builder.AddUserSecrets<ConfigurationService>(); + builder.AddUserSecrets<ConfigurationService>(); } - _ = builder.AddEnvironmentVariables(); + builder.AddEnvironmentVariables(); _configuration = builder.Build(); }Directory.Packages.props (1)
16-16: Remover pacotes AspNetCore.*.Abstractions 2.3.0 (legados e potencialmente conflitantes no .NET 9)Esses pacotes são da era 2.x e geralmente são providos pelo shared framework. Mantê-los fixa versões antigas e pode gerar conflitos/duplicidades. Remova-os do gerenciamento central (e quaisquer referências diretas em csproj).
- <PackageVersion Include="Microsoft.AspNetCore.Http.Abstractions" Version="2.3.0" /> ... - <PackageVersion Include="Microsoft.AspNetCore.Authentication.Abstractions" Version="2.3.0" />Caso algum projeto ainda os referencie explicitamente, remova o PackageReference correspondente.
Also applies to: 48-48
🧹 Nitpick comments (3)
.dockerignore (2)
18-28: Evite ignorar Dockerfiles globalmente para reduzir risco de regressões futurasIgnorar
**/Dockerfile*e depois re-incluir seletivamente um arquivo específico é frágil: qualquer novo Dockerfile que vier a ser adicionado (por exemplo, de serviços auxiliares) será excluído por padrão e poderá quebrar builds. Dockerfiles são pequenos e não impactam significativamente o tamanho do contexto.Sugestão: remova a regra global que ignora Dockerfiles e também a exceção correspondente; isso simplifica e evita pegadinhas futuras.
Aplicar este diff:
-**/Dockerfile* ... -!InvoiceReminder.API/Dockerfile
1-29: Reduza o contexto de build definindo o build.context no serviço da APISe o docker-compose atualmente usa o diretório raiz como contexto, considere apontar o contexto diretamente para
InvoiceReminder.API. Isso:
- reduz o contexto enviado ao daemon,
- elimina a necessidade de exceções como
!InvoiceReminder.API/Dockerfile,- diminui a dependência de padrões frágeis no .dockerignore.
Exemplo (no docker-compose):
services: api: build: context: ./InvoiceReminder.API dockerfile: DockerfileIsso permite simplificar este .dockerignore e acelera builds.
InvoiceReminder.Data/InvoiceReminder.Data.csproj (1)
19-22: Duplicação de PrivateAssets no mesmo PackageReferenceVocê adicionou PrivateAssets="all" no atributo e mantém o nó interno all. É redundante; escolha um só para evitar ruído.
- <PackageReference Include="Microsoft.EntityFrameworkCore.Design" PrivateAssets="all"> - <PrivateAssets>all</PrivateAssets> - <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets> - </PackageReference> + <PackageReference Include="Microsoft.EntityFrameworkCore.Design" PrivateAssets="all"> + <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets> + </PackageReference>
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (11)
.dockerignore(1 hunks)Directory.Packages.props(1 hunks)InvoiceReminder.API.UnitTests/InvoiceReminder.API.UnitTests.csproj(1 hunks)InvoiceReminder.API/Dockerfile(1 hunks)InvoiceReminder.API/InvoiceReminder.API.csproj(1 hunks)InvoiceReminder.Application/InvoiceReminder.Application.csproj(1 hunks)InvoiceReminder.CrossCutting.IoC/DependencyInjectionConfig.cs(1 hunks)InvoiceReminder.Data/InvoiceReminder.Data.csproj(1 hunks)InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs(3 hunks)InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs(1 hunks)InvoiceReminder.JobScheduler.UnitTests/InvoiceReminder.JobScheduler.UnitTests.csproj(1 hunks)
🚧 Files skipped from review as they are similar to previous changes (7)
- InvoiceReminder.Application/InvoiceReminder.Application.csproj
- InvoiceReminder.API/Dockerfile
- InvoiceReminder.API.UnitTests/InvoiceReminder.API.UnitTests.csproj
- InvoiceReminder.CrossCutting.IoC/DependencyInjectionConfig.cs
- InvoiceReminder.API/InvoiceReminder.API.csproj
- InvoiceReminder.JobScheduler.UnitTests/InvoiceReminder.JobScheduler.UnitTests.csproj
- InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs
🧰 Additional context used
🧬 Code Graph Analysis (3)
InvoiceReminder.Data/InvoiceReminder.Data.csproj (2)
InvoiceReminder.Data/Migrations/20250509040148_Initial_Create.Designer.cs (3)
Initial_Create(14-259)BuildTargetModel(19-258)b(29-80)InvoiceReminder.Data/Migrations/CoreDbContextModelSnapshot.cs (1)
CoreDbContextModelSnapshot(14-258)
InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (2)
InvoiceReminder.DomainEntities.UnitTests/Services/Configuration/ConfigurationServiceTests.cs (1)
ConfigurationService(24-31)InvoiceReminder.Domain/Services/Configuration/IConfigurationService.cs (1)
IConfigurationService(3-12)
Directory.Packages.props (2)
InvoiceReminder.Data/Migrations/CoreDbContextModelSnapshot.cs (1)
CoreDbContextModelSnapshot(14-258)InvoiceReminder.Data/Migrations/20250509040148_Initial_Create.Designer.cs (1)
BuildTargetModel(19-258)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
- GitHub Check: Analyze (csharp)
🔇 Additional comments (6)
.dockerignore (1)
3-3: Boa prática:.envfora do contexto do buildIgnorar
**/.envevita enviar segredos ao daemon durante o build. Mantendo as variáveis viaenv_file/compose em runtime, você reduz risco de vazamento.InvoiceReminder.Domain/Services/Configuration/ConfigurationService.cs (2)
50-53: Overload com default para secrets: bom incremento de DXO fallback para defaultValue evita null checks espalhados. LGTM.
60-63: Overload com default para sections: boa ergonomiaFacilita configuração opcional sem boilerplate. LGTM.
Directory.Packages.props (3)
4-4: Pinagem transitiva ativada: ótimo para builds determinísticosA propriedade CentralPackageTransitivePinningEnabled=true está correta e alinha o restore com o versionamento central. LGTM.
39-39: Alinhar Npgsql.EntityFrameworkCore.PostgreSQL à versão do EF CoreVocê fixou Microsoft.EntityFrameworkCore em 9.0.8, porém o provider Npgsql EFCore está em 9.0.4. Recomendo alinhar o provider para reduzir risco de incompatibilidades.
Proposta:
- <PackageVersion Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="9.0.4" /> + <PackageVersion Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="9.0.8" />Depois, valide restore/build/testes.
37-37: Referências ao pacote de containers já estão marcadas como dev-onlyVerificamos que apenas o projeto
InvoiceReminder.API/InvoiceReminder.API.csprojreferencia
Microsoft.VisualStudio.Azure.Containers.Tools.Targetse já incluiPrivateAssets="all".
Nenhuma outra referência sem a flag foi encontrada.
Introduces Dockerfile and docker-compose for containerization.
Refactors project structure and moves external services to their own project.
Updates dependencies to the latest versions and fixes related issues.
Also adds .dockerignore to exclude unnecessary files during build.
✨
Description by Callstackai
This PR introduces Docker support with a Dockerfile and docker-compose for containerization, refactors project structure, updates dependencies, and adds a .dockerignore file.
Diagrams of code changes
sequenceDiagram participant Client participant Docker participant API participant ConfigService participant Database Client->>Docker: Build Container Docker->>Docker: Multi-stage build Note over Docker: Uses base, build, publish, and final stages Docker->>API: Start API Container API->>ConfigService: Initialize Configuration ConfigService->>ConfigService: Load Configuration Sources Note over ConfigService: Loads from:<br/>1. appsettings.json<br/>2. appsettings.{env}.json<br/>3. User Secrets (Dev only)<br/>4. Environment Variables API->>Database: Configure PostgreSQL Connection Note over Database: Uses connection string from configuration Client->>API: HTTP/HTTPS Requests Note over API: Exposes ports:<br/>8080 (HTTP)<br/>8081 (HTTPS)Files Changed
This PR includes files in programming languages that we currently do not support. We have not reviewed files with the extensions
.dockerignore,.props,.csproj,.json,.cs,.sln,.yml. See list of supported languages.Summary by CodeRabbit