> ## Documentation Index
> Fetch the complete documentation index at: https://docs.diyanet.pro/llms.txt
> Use this file to discover all available pages before exploring further.

# Application Katmanı

> Use-case orkestrasyonu, MediatR CQRS, klasör yapısı ve request akışı

## Rolü

Application katmanı, **use-case orkestrasyonudur**. İş kuralları Domain'de (aggregate'lar, value object'ler, domain servisleri) yaşar; Application bu kuralları bir senaryo etrafında düzenler:

1. Gelen request'i (Command/Query) karşılar,
2. Repository / domain servis / factory çağrılarını sıralar,
3. Aggregate metodlarını tetikler (domain event'ler burada doğar),
4. `IUnitOfWork.SaveEntitiesAsync` ile transaction'ı kapatır,
5. Sonucu bir `ResponseWrapper` zarfı içinde döner.

Katman **MediatR** üzerine kuruludur ve **CQRS** ayrımını uygular: yazma tarafı `IRepository<T>` (write), okuma tarafı `IReadRepository<T>` (cache decorator) kullanır. Controller'lar incedir — sadece `_mediator.Send(...)` çağırır.

<Note>
  Application katmanı Infrastructure'a (`DiyanetCleanArchitecture.Infrastructure.EFCore`) referans verir; çünkü `DependencyInjection.cs` MassTransit Outbox'ı `DiyanetCleanArchitectureDbContext` üzerine register eder. İş mantığı yine de Domain'e bağımlıdır, altyapıya değil.
</Note>

## Klasör yapısı

```text theme={null}
DiyanetCleanArchitecture.Application/
├── Features/                    # Use-case'ler (CQRS) — Feature/Admin|Website/Commands|Queries
├── DomainEventHandlers/         # In-process INotificationHandler'lar (SaveEntitiesAsync sonrası)
├── IntegrationEventHandlers/    # Cross-instance / cross-service event tüketicileri
├── SeedWork/                    # Çapraz kesen altyapı
│   ├── PipelineBehaviors/       # MediatR IPipelineBehavior zinciri
│   ├── Authorization/           # IRequirePermissions, IRequireTenantAccess, ForbiddenException
│   ├── Security/                # ICurrentUser, ICurrentTenant, ICurrentActor, IRequirePermission
│   ├── Validations/             # FluentValidation custom validator'ları
│   ├── Mappings/                # AutoMapper IMapFrom<T> + MappingProfile
│   ├── Models/                  # ResponseWrapper, Paged, RequestWrapper, Export
│   ├── Caching/                 # Cache broadcast soyutlamaları
│   └── Exceptions/              # UndefinedApplicationException
├── Services/                    # Application-level servisler (Identity, File, Payment, ...)
└── DependencyInjection.cs       # AddApplication() — tüm kayıtlar
```

### Features altında Admin / Website ayrımı

Her feature, hedef SPA'ya göre ikiye ayrılır. Aynı aggregate için Admin (back-office) ve Website (vatandaş portalı) farklı DTO, farklı yetki ve farklı specification kullanır:

```text theme={null}
Features/BagisBasvuruPlanlari/
├── Admin/
│   ├── Commands/   CreateBagisBasvuruPlan, UpdateBagisBasvuruPlan, DeleteBagisBasvuruPlan, ...
│   └── Queries/    GetAdminBagisBasvuruPlanlar, GetAdminBagisBasvuruPlanById
└── Website/
    └── Queries/    GetPublicBagisBasvuruPlanlar, GetPublicBagisBasvuruPlanById
```

Kimlik doğrulama feature'ı için ayrım `Features/Authentication/Website/Commands/SignUpUser`, `.../VerifyOtp` şeklindedir.

## Request akışı

Bir Command/Query, Controller'dan MediatR'a girer, pipeline behavior zincirinden geçer ve Handler'a ulaşır. Handler aggregate'i değiştirir, `IUnitOfWork` SaveChanges yapar ve domain event'leri dağıtır.

```mermaid theme={null}
flowchart TD
    C[Controller<br/>_mediator.Send] --> M[MediatR]
    M --> B1[ExceptionPipelineBehavior]
    B1 --> B2[AuthorizationPipelineBehavior]
    B2 --> B3[ValidationPipelineBehavior]
    B3 --> B4[PermissionPipelineBehavior]
    B4 --> H[Command/Query Handler]
    H --> R[(IRepository / IReadRepository)]
    H --> UoW[IUnitOfWork.SaveEntitiesAsync]
    UoW --> DE[Domain Event Dispatch<br/>INotificationHandler]
    H --> RW[ResponseWrapper&lt;T&gt;]
```

Pipeline sırası `DependencyInjection.cs` içinde kayıt sırasıyla belirlenir: **Exception → Authorization → Validation → Permission**. `LoggingPipelineBehavior` kayıtlıdır ama yorum satırına alınmıştır.

```csharp theme={null}
builder.Services.AddTransient(typeof(IPipelineBehavior<,>), typeof(ExceptionPipelineBehavior<,>));
builder.Services.AddTransient(typeof(IPipelineBehavior<,>), typeof(AuthorizationPipelineBehavior<,>));
//builder.Services.AddTransient(typeof(IPipelineBehavior<,>), typeof(LoggingPipelineBehavior<,>));
builder.Services.AddTransient(typeof(IPipelineBehavior<,>), typeof(ValidationPipelineBehavior<,>));
builder.Services.AddTransient(typeof(IPipelineBehavior<,>), typeof(PermissionPipelineBehavior<,>));
```

<Tip>
  Cache MediatR pipeline'ında **değildir**. Okuma cache'i specification katmanında (`.EnableCache(...)`) işaretlenir ve `CachedRepository<T>` tarafından HybridCache'e bağlanır. Invalidation ise domain event handler'larında `IHybridRequestCache.RemoveByTagAsync` ile yapılır.
</Tip>

## Sonraki adımlar

<CardGroup cols={2}>
  <Card title="Command / Query deseni" icon="code" href="/application/commands-queries">
    SignUpUser, VerifyOtp ve admin query örnekleriyle CQRS akışı.
  </Card>

  <Card title="Pipeline Behaviors" icon="layer-group" href="/application/pipeline-behaviors">
    Exception, Authorization, Validation ve Permission zinciri.
  </Card>

  <Card title="Validation & Mapping" icon="check-double" href="/application/validation-mapping">
    FluentValidation custom kuralları ve AutoMapper convention'ı.
  </Card>

  <Card title="Domain Katmanı" icon="cube" href="/domain/overview">
    Aggregate'lar, value object'ler ve domain event'ler.
  </Card>
</CardGroup>
