Skip to content

One API project owns the domain; health checks per house pattern (ADR-0009)#6

Merged
KaliCZ merged 2 commits into
fix/naming-rule-private-constantsfrom
restructure/single-api-project
Jul 16, 2026
Merged

One API project owns the domain; health checks per house pattern (ADR-0009)#6
KaliCZ merged 2 commits into
fix/naming-rule-private-constantsfrom
restructure/single-api-project

Conversation

@KaliCZ

@KaliCZ KaliCZ commented Jul 16, 2026

Copy link
Copy Markdown
Owner

Two things, per request: the health-check setup used in DemoPage/hampap, and the collapse of the Domain + ServiceDefaults projects into the API project.

Based on the fix/naming-rule-private-constants branch (PR #5) — GitHub will retarget this to main automatically once #5 merges.

Single API project (ADR-0009, supersedes ADR-0001)

A feature folder now owns its whole slice — entities, handlers + error enums, controller, DTOs, mapping — instead of being split across Api and Domain:

src/ProductReviews.Api/
├── Features/{Catalog,Reviews,Votes,Profile}/   # complete slices
├── Persistence/                                # DbContext, configurations, migrations, seeding
├── Infrastructure/                             # one concern per file
└── Program.cs
  • ProductReviews.ServiceDefaults is gone: OTel lives in Infrastructure/Observability.cs, health in Infrastructure/Health.cs; service discovery was dropped (nothing used it) and HTTP resilience moved onto the Zitadel userinfo client — per-client, not ConfigureHttpClientDefaults (rule Bump the nuget group with 1 update #14).
  • Migration IDs untouched — existing dev databases keep working; only the namespace moved.
  • "Domain never sees HTTP" is now a review rule, not a compiler edge — spelled out in ADR-0009 and CLAUDE.md rule Product Reviews showcase: StrongTypes end to end #1.
  • ProductReviews.Domain.TestsProductReviews.Api.UnitTests.

Health checks (house pattern)

  • /alive — liveness only: the version check (commit hash from the assembly SourceRevisionId, embedded by the SDK), no dependencies — a shared Postgres/Zitadel outage never reads as a dead process.
  • /health — full readiness: EF Core AddDbContextCheck<ReviewsDbContext> (database, the Aspire integration''s duplicate check disabled) + zitadel probing the OIDC discovery document with a 5 s timeout. Zitadel failures report Degraded, not Unhealthy: reads survive an identity-provider outage.
  • Both endpoints answer "<status> <commit>" — greppable by a blue/green deploy gate, no per-check detail leaked.

Verification

  • dotnet build: 0 warnings, 0 errors
  • dotnet test: 43/43 (13 unit + 30 integration, incl. two new wire-level health tests: /aliveHealthy <commit> with no Zitadel configured; /healthDegraded <commit> with DB up and no identity provider)
  • Playwright E2E against the full restructured stack: 8/8 in 30 s

🤖 Generated with Claude Code

KaliCZ and others added 2 commits July 16, 2026 17:19
Merge ProductReviews.Domain into ProductReviews.Api so a feature folder
owns its whole slice (entities, handlers, controller, DTOs), and fold
ProductReviews.ServiceDefaults into Infrastructure/ (Observability.cs =
OTel, Health.cs = health checks). Resilience moves onto the userinfo
client instead of ConfigureHttpClientDefaults.

Health follows the house pattern: /alive = commit-hash check only, no
dependencies; /health = EF Core DbContext check + Zitadel discovery
probe (Degraded, not Unhealthy). Both answer "<status> <commit>" from
the assembly SourceRevisionId. Wire-level tests cover both endpoints.

Domain.Tests becomes Api.UnitTests. Migration IDs are untouched.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant