NestJS Best Practices: 10 Adımda Güvenli ve Ölçeklenebilir API [2026]
Yazar: Burak Balkı | Kategori: Mobile Development | Okuma Süresi: 45 dk
Bu rehber, 2026 itibarıyla NestJS kullanarak mobil uygulamalar için güvenli, performanslı ve ölçeklenebilir API'lar geliştirmenin en iyi uygulamalarını sunar...
## NestJS Best Practices: 10 Adımda Güvenli ve Ölçeklenebilir API [2026]
### Giriş: Mobil Uygulamaların Kalbi İçin Sağlam Bir Backend
Günümüz mobil uygulama ekosisteminde, kullanıcı deneyiminin kalitesi büyük ölçüde uygulamanın arkasındaki backend servislerinin performansı ve güvenilirliği ile belirlenir. 2026 yılı itibarıyla, geliştiricilerin karşılaştığı en büyük zorluklardan biri, hızla değişen gereksinimlere uyum sağlayabilen, yüksek performanslı ve güvenli API'lar inşa etmektir. Bu kapsamlı rehberde, 10 yılı aşkın tecrübemle edindiğim bilgileri kullanarak, **NestJS best practices**'lerini, mobil uygulamalarınız için güvenli, performanslı ve ölçeklenebilir API'lar geliştirmenizi sağlayacak pratik örneklerle ele alacağız.
### NestJS Nedir?
NestJS, Node.js ile verimli ve ölçeklenebilir sunucu tarafı uygulamalar oluşturmak için TypeScript'i kullanan ilerici bir Node.js çerçevesidir. Express.js veya Fastify gibi HTTP sunucu iskeletlerini destekleyerek, kurumsal düzeyde uygulamaların geliştirilmesini kolaylaştırır ve mobil backend ihtiyaçları için idealdir. Modüler yapısı, bağımlılık enjeksiyonu ve dekoratör tabanlı yaklaşımı sayesinde, geliştiricilere temiz, test edilebilir ve sürdürülebilir kod yazma imkanı sunar.
NestJS, Angular'dan ilham alan mimarisiyle, geliştiricilere tanıdık bir yapı sunar. Bu yapı, özellikle büyük ölçekli ve karmaşık projelerde geliştirme sürecini hızlandırır ve ekip içi tutarlılığı artırır. 2026 itibarıyla NestJS, mikroservis mimarileri, GraphQL API'ları ve gerçek zamanlı uygulamalar (WebSockets) geliştirme konusunda da sektörde lider konumdadır. Bu sayede mobil uygulamalar için ihtiyaç duyulan esnek ve güçlü API'lar kolayca oluşturulabilir.
### Neden NestJS Kullanmalısınız?
2026 itibarıyla NestJS, özellikle mobil uygulamalar için API geliştirirken pek çok avantaj sunuyor. Frontend odaklı mobil geliştiricilerin bile kolayca adapte olabileceği, güçlü ve yapılandırılmış bir backend çözümü arayanlar için idealdir. İşte NestJS'i tercih etmeniz için başlıca nedenler:
* **Modüler ve Ölçeklenebilir Mimari:** NestJS, uygulamaları modüllere ayırarak kodun daha yönetilebilir olmasını sağlar. Bu sayede, mobil uygulamanızın farklı özelliklerine hizmet eden mikroservisler kolayca oluşturulabilir ve bağımsız olarak ölçeklenebilir.
* **TypeScript Desteği:** TypeScript'in sunduğu statik tip kontrolü, özellikle büyük ekiplerle çalışırken ve karmaşık API'lar geliştirirken hataları erkenden yakalamaya yardımcı olur. Bu, mobil uygulamaların güvenilirliğini doğrudan etkiler.
* **Kurumsal Hazır Yapı:** Bağımlılık enjeksiyonu (DI), dekoratörler ve modüler tasarım prensipleri sayesinde NestJS, kurumsal düzeyde, sürdürülebilir ve test edilebilir uygulamalar geliştirmek için gerekli tüm araçları sunar.
* **Aktif Topluluk ve Geniş Ekosistem:** NestJS'in 2026'daki aktif ve büyüyen topluluğu, sürekli destek ve zengin kütüphane ekosistemi anlamına gelir. Bu, karşılaşılan sorunlara hızlı çözümler bulmayı ve yeni özellikler entegre etmeyi kolaylaştırır.
* **Performans ve Verimlilik:** NestJS, temelinde Express.js veya Fastify gibi yüksek performanslı HTTP sunucularını kullandığı için, mobil uygulamalarınız için hızlı yanıt veren ve düşük gecikmeli API'lar sunar. Geliştirme verimliliği, CLI araçları ve otomatik kod üretimi ile artırılır.
### NestJS vs Alternatifler: Mobil Backend Seçimi
Mobil uygulamalar için backend seçimi, projenin başarısı için kritik öneme sahiptir. NestJS, Node.js ekosistemindeki diğer popüler framework'lerle karşılaştırıldığında belirli avantajlar sunar. Aşağıdaki tablo, NestJS'i Express.js ve Fastify ile 2026 yılındaki durumları göz önüne alınarak karşılaştırmaktadır:
| Özellik | NestJS | Express.js | Fastify |
| :----------------- | :--------------------------------------------- | :------------------------------------------ | :------------------------------------------ |
| **Yapı/Mimari** | Fikir sahibi (Opinionated), modüler, DI | Fikir sahibi değil (Unopinionated), minimal | Fikir sahibi değil (Unopinionated), minimal |
| **Performans** | Yüksek (Fastify ile de kullanılabilir) | Orta | Çok Yüksek (en hızlı Node.js framework'lerinden) |\
| **Öğrenme Eğrisi** | Orta (Angular/OOP geçmişi olanlara kolay) | Düşük (çok esnek) | Orta (plugin tabanlı, detaylı dökümantasyon) |\
| **Ekosistem** | Zengin (modüller, CLI, TypeORM entegrasyonu) | Çok Zengin (geniş middleware yelpazesi) | Orta (hızla büyüyor) |\
| **Topluluk** | Aktif ve büyüyen (2026 itibarıyla) | Çok Geniş ve köklü | Aktif ve hızla büyüyen |\
| **Kurumsal Destek**| Yüksek (yapılandırılmış, test edilebilir) | Orta (manuel yapılandırma gerektirir) | Orta (hız odaklı) |\
| **Kullanım Alanı** | Kurumsal uygulamalar, mikroservisler, GraphQL | Hızlı prototipler, küçük-orta ölçekli API'lar | Yüksek performans gerektiren API'lar, mikroservisler |
Bu karşılaştırma gösteriyor ki, NestJS özellikle mobil uygulamalar için karmaşık ve uzun ömürlü API'lar geliştirirken sunduğu yapısal avantajlarla öne çıkıyor. Express.js ve Fastify esneklik ve saf hız sunarken, NestJS geliştirme sürecinde daha fazla rehberlik ve tutarlılık sağlayarak büyük projelerde oluşan karmaşıklığı azaltır. Burak Balkı olarak, production ortamında ölçeklenebilirlik ve sürdürülebilirlik arayan ekipler için NestJS'i 2026'da da en güçlü adaylardan biri olarak görüyorum.
### Kurulum ve İlk Adımlar
NestJS ile mobil uygulamalarınız için bir backend oluşturmaya başlamak oldukça kolaydır. İşte 2026 yılı itibarıyla güncel kurulum adımları ve ilk projenizi oluşturma süreci:
**Ön Gereksinimler:**
* Node.js (LTS sürümü önerilir - 2026 itibarıyla v20.x veya v22.x)
* npm veya Yarn
1. **NestJS CLI Kurulumu:**
NestJS CLI (Command Line Interface), proje oluşturma, modül, servis ve kontrolcü gibi yapı taşlarını hızlıca üretme gibi işlemleri kolaylaştırır.
```bash
npm install -g @nestjs/cli
# veya
yarn global add @nestjs/cli
```
2. **Yeni Bir NestJS Projesi Oluşturma:**
CLI'yi kullanarak yeni bir proje iskeleti oluşturabilirsiniz. `mobile-api-backend` projenizin adı olsun.
```bash
nest new mobile-api-backend
```
Bu komut, size hangi paket yöneticisini kullanmak istediğinizi soracaktır (npm veya yarn). Seçiminizi yaptıktan sonra NestJS gerekli tüm bağımlılıkları kuracak ve temel proje yapısını oluşturacaktır.
3. **Proje Dizinine Gitme ve Uygulamayı Başlatma:**
Proje oluşturulduktan sonra, oluşturulan dizine geçip uygulamayı başlatabilirsiniz.
```bash
cd mobile-api-backend
npm run start:dev
# veya
yarn start:dev
```
Uygulamanız genellikle `http://localhost:3000` adresinde çalışmaya başlayacaktır. Tarayıcınızda bu adrese giderek `Hello World!` çıktısını görmelisiniz. Bu, ilk NestJS API'nızın 2026'da başarıyla çalıştığı anlamına gelir.
### Temel Kullanım ve Örnekler: Mobil API Geliştirme
NestJS'in temel yapı taşlarını ve mobil uygulamalar için nasıl API'lar geliştirebileceğinizi pratik örneklerle inceleyelim. Odak noktamız, mobil istemcilerin ihtiyaç duyacağı yaygın senaryolar olacak.
#### Örnek 1: Temel CRUD API (Kullanıcı Yönetimi)
Mobil uygulamaların çoğu, kullanıcı verilerini yönetmek için CRUD (Create, Read, Update, Delete) işlemlerine ihtiyaç duyar. İşte basit bir kullanıcı API'si:
**Problem:** Mobil uygulama için kullanıcıları listeleyebilen, yeni kullanıcı ekleyebilen, güncelleyebilen ve silebilen bir API oluşturmak.
**Çözüm:** Bir `UsersModule` oluşturup, `UsersController` ve `UsersService` kullanarak bu işlemleri yönetmek.
```bash
# Kullanıcı modülünü oluşturun
nest generate module users
# Kullanıcı servis ve kontrolcüsünü oluşturun
nest generate service users
nest generate controller users
```
**`src/users/users.controller.ts`:**
```typescript
import { Controller, Get, Post, Put, Delete, Param, Body } from '@nestjs/common';
import { UsersService } from './users.service';
import { CreateUserDto, UpdateUserDto } from './dto/user.dto'; // DTO'ları daha sonra oluşturacağız
@Controller('users')
export class UsersController {
constructor(private readonly usersService: UsersService) {}
@Post()
create(@Body() createUserDto: CreateUserDto) {
return this.usersService.create(createUserDto);
}
@Get()
findAll() {
return this.usersService.findAll();
}
@Get(':id')
findOne(@Param('id') id: string) {
return this.usersService.findOne(+id);
}
@Put(':id')
update(@Param('id') id: string, @Body() updateUserDto: UpdateUserDto) {
return this.usersService.update(+id, updateUserDto);
}
@Delete(':id')
remove(@Param('id') id: string) {
return this.usersService.remove(+id);
}
}
```
**`src/users/users.service.ts`:**
```typescript
import { Injectable } from '@nestjs/common';
import { CreateUserDto, UpdateUserDto } from './dto/user.dto';
interface User {
id: number;
name: string;
email: string;
}
@Injectable()
export class UsersService {
private users: User[] = [];
private nextId = 1;
create(createUserDto: CreateUserDto): User {
const newUser = { id: this.nextId++, ...createUserDto };
this.users.push(newUser);
return newUser;
}
findAll(): User[] {
return this.users;
}
findOne(id: number): User | undefined {
return this.users.find(user => user.id === id);
}
update(id: number, updateUserDto: UpdateUserDto): User | undefined {
const index = this.users.findIndex(user => user.id === id);
if (index > -1) {
this.users[index] = { ...this.users[index], ...updateUserDto };
return this.users[index];
}
return undefined;
}
remove(id: number): boolean {
const initialLength = this.users.length;
this.users = this.users.filter(user => user.id !== id);
return this.users.length < initialLength;
}
}
```
**`src/users/dto/user.dto.ts`:**
```typescript
// DTO'lar (Data Transfer Objects) veri validasyonu için kullanılır.
// class-validator ve class-transformer paketleri ile daha güçlü hale getirilebilir.
export class CreateUserDto {
name: string;
email: string;
}
export class UpdateUserDto {
name?: string;
email?: string;
}
```
#### Örnek 2: API Versiyonlama (Mobil Uyumluluğu İçin)
Mobil uygulamalar genellikle farklı API versiyonlarına ihtiyaç duyar. NestJS, esnek versiyonlama stratejileri sunar.
**Problem:** Mobil uygulamanın eski versiyonları ile yeni versiyonları arasında uyumluluğu sağlamak.
**Çözüm:** URI versiyonlama kullanarak farklı API versiyonlarını desteklemek.
**`src/app.controller.ts`:**
```typescript
import { Controller, Get, VERSION_NEUTRAL, Version } from '@nestjs/common';
import { AppService } from './app.service';
@Controller({ version: ['1', '2'] }) // Global olarak versiyon tanımlama
export class AppController {
constructor(private readonly appService: AppService) {}
@Version('1')
@Get('hello')
getHelloV1(): string {
return 'Hello from API v1!';
}
@Version('2')
@Get('hello')
getHelloV2(): string {
return 'Hello from API v2, with new features!';
}
// Veya versiyondan bağımsız bir endpoint
@Version(VERSION_NEUTRAL)
@Get('status')
getStatus(): string {
return 'API Status: OK';
}
}
```
**`src/main.ts`:**
```typescript
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
import { VersioningType } from '@nestjs/common';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
// URI versiyonlamayı etkinleştirin
app.enableVersioning({
type: VersioningType.URI,
});
await app.listen(3000);
}
bootstrap();
```
Bu yapılandırma ile mobil istemciler `http://localhost:3000/v1/hello` veya `http://localhost:3000/v2/hello` adreslerine istek yaparak farklı API versiyonlarına erişebilirler.
#### Örnek 3: Veri Validasyonu (DTO'lar ile)
Mobil uygulamalardan gelen verilerin doğru formatta ve geçerli olduğundan emin olmak, güvenlik ve stabilite açısından hayati öneme sahiptir. NestJS, `class-validator` ve `class-transformer` ile güçlü bir validasyon mekanizması sunar.
**Problem:** Kullanıcı kayıt olurken e-posta formatının ve şifre uzunluğunun kontrol edilmesi.
**Çözüm:** `CreateUserDto`'yu `class-validator` dekoratörleri ile zenginleştirmek ve `ValidationPipe` kullanmak.
Önce gerekli paketleri kurun:
```bash
npm install class-validator class-transformer
```
**`src/users/dto/create-user.dto.ts`:**
```typescript
import { IsEmail, IsNotEmpty, MinLength } from 'class-validator';
export class CreateUserDto {
@IsNotEmpty({ message: 'Kullanıcı adı boş bırakılamaz.' })
name: string;
@IsEmail({}, { message: 'Geçerli bir e-posta adresi giriniz.' })
email: string;
@MinLength(6, { message: 'Şifre en az 6 karakter olmalıdır.' })
password: string;
}
```
**`src/users/users.controller.ts` (Güncellenmiş):**
```typescript
import { Controller, Post, Body, UsePipes, ValidationPipe } from '@nestjs/common';
import { CreateUserDto } from './dto/create-user.dto';
import { UsersService } from './users.service';
@Controller('users')
export class UsersController {
constructor(private readonly usersService: UsersService) {}
@Post()
@UsePipes(new ValidationPipe({ whitelist: true, forbidNonWhitelisted: true })) // Global veya metod seviyesinde validasyon
create(@Body() createUserDto: CreateUserDto) {
return this.usersService.create(createUserDto);
}
// ... diğer CRUD metodları ...
}
```
**`src/main.ts` (Global ValidationPipe için):**
```typescript
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
import { ValidationPipe, VersioningType } from '@nestjs/common';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.enableVersioning({
type: VersioningType.URI,
});
app.useGlobalPipes(new ValidationPipe({
whitelist: true, // DTO'da tanımlanmayan alanları kaldırır
forbidNonWhitelisted: true, // DTO'da tanımlanmayan alanlar varsa hata döndürür
transform: true, // Gelen veriyi DTO sınıfına dönüştürür
}));
await app.listen(3000);
}
bootstrap();
```
Bu sayede mobil istemciden gelen isteğin body'si otomatik olarak validate edilir ve geçersiz verilerde hata döndürülür. Bu, API'nızın sağlamlığını artırır ve beklenmeyen veri girişlerini engeller.
### İleri Seviye Teknikler: Mobil Backend Optimizasyonu
Mobil uygulamalar için geliştirilen NestJS backend'lerinin sadece çalışması yetmez, aynı zamanda yüksek performanslı, güvenli ve esnek olması gerekir. İşte 2026'da kullanabileceğiniz ileri seviye teknikler:
#### Mikroservis Mimarisi ile Ölçeklenebilirlik
**Problem:** Büyük ve karmaşık mobil uygulamaların backend'ini tek bir monolitik yapı yerine daha yönetilebilir ve ölçeklenebilir parçalara ayırmak.
**Çözüm:** NestJS'in mikroservis yeteneklerini kullanarak farklı iş alanlarını ayrı servislere bölmek.
```bash
# Yeni bir mikroservis uygulaması oluşturun (örneğin 'notifications')
nest new notifications-service --type=microservice
```
**`notifications-service/src/main.ts` (Microservice):**
```typescript
import { NestFactory } from '@nestjs/core';
import { Transport, MicroserviceOptions } from '@nestjs/microservices';
import { AppModule } from './app.module';
async function bootstrap() {
const app = await NestFactory.createMicroservice(AppModule, {
transport: Transport.TCP, // Veya REDIS, NATS, Kafka vb.
options: {
host: '127.0.0.1',
port: 8877,
},
});
await app.listen();
}
bootstrap();
```
**`mobile-api-backend/src/app.module.ts` (Client):**
```typescript
import { Module } from '@nestjs/common';
import { ClientsModule, Transport } from '@nestjs/microservices';
import { AppController } from './app.controller';
import { AppService } from './app.service';
@Module({
imports: [
ClientsModule.register([
{
name: 'NOTIFICATIONS_SERVICE',
transport: Transport.TCP,
options: { host: '127.0.0.1', port: 8877 },
},
]),
],
controllers: [AppController],
providers: [AppService],
})
export class AppModule {}
```
Bu yapılandırma ile ana API'nız, bildirim gönderme gibi işlemleri ayrı bir mikroservise delege edebilir. Bu, özellikle mobil uygulamaların anlık bildirim gereksinimleri için oldukça kullanışlıdır.
#### GraphQL Entegrasyonu
**Problem:** Mobil istemcilerin ihtiyaç duyduğu veriyi tek bir istekte, tam olarak istedikleri formatta almasını sağlamak ve aşırı/eksik veri çekme sorununu çözmek.
**Çözüm:** NestJS'in GraphQL entegrasyonunu kullanarak esnek API'lar sunmak.
```bash
npm install @nestjs/graphql @nestjs/apollo graphql apollo-server-express
```
**`src/app.module.ts` (GraphQL Entegrasyonu):**
```typescript
import { Module } from '@nestjs/common';
import { GraphQLModule } from '@nestjs/graphql';
import { ApolloDriver, ApolloDriverConfig } from '@nestjs/apollo';
import { join } from 'path';
import { UsersModule } from './users/users.module'; // Varsayalım bir UsersModule var
@Module({
imports: [
GraphQLModule.forRoot({
driver: ApolloDriver,
autoSchemaFile: join(process.cwd(), 'src/schema.gql'),
sortSchema: true,
}),
UsersModule,
],
})
export class AppModule {}
```
Bu kurulumla, mobil istemciler tek bir GraphQL endpoint'i üzerinden birden fazla kaynakla etkileşime girebilir ve sadece ihtiyaç duydukları verileri alabilirler. Bu, özellikle mobil ağ kısıtlamaları düşünüldüğünde performansı artırır.
#### Graceful Shutdown (Hassas Kapanma)
**Problem:** Sunucu kapanırken veya yeniden başlatılırken devam eden isteklerin düzgün bir şekilde tamamlanmasını sağlamak ve veri kaybını önlemek.
**Çözüm:** NestJS'in yaşam döngüsü hook'larını kullanarak graceful shutdown mekanizması uygulamak.
**`src/main.ts` (Graceful Shutdown):**
```typescript
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
import { ValidationPipe, VersioningType } from '@nestjs/common';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.enableVersioning({
type: VersioningType.URI,
});
app.useGlobalPipes(new ValidationPipe({
whitelist: true,
forbidNonWhitelisted: true,
transform: true,
}));
// Graceful shutdown'ı etkinleştir
app.enableShutdownHooks();
await app.listen(3000);
}
bootstrap();
```
`enableShutdownHooks()` metodunu çağırdıktan sonra, modüllerinizde `OnModuleDestroy` veya `OnApplicationShutdown` gibi yaşam döngüsü hook'larını uygulayarak veritabanı bağlantılarını kapatma veya açık kaynakları serbest bırakma gibi işlemleri güvenli bir şekilde yapabilirsiniz. Bu, production ortamında stabilite için kritik bir **NestJS best practice**'idir.
### Best Practices & Anti-Patterns: 2026 İçin NestJS Rehberi
Production ortamında NestJS ile çalıştığım 10 yılı aşkın sürede, mobil uygulamalar için sağlam API'lar geliştirirken edindiğim en önemli dersleri ve 2026 itibarıyla geçerli olan best practices'leri aşağıda derledim:
* ✅ **DTO'ları ve `class-validator`'ı Kapsamlı Kullanın:** Gelen ve giden verilerin tip güvenliğini ve validasyonunu sağlamak için DTO'ları aktif olarak kullanın. Bu, API'nızın sağlamlığını artırır ve mobil istemcilerden gelebilecek hatalı verilere karşı koruma sağlar.
> **Neden Önemli?** Veri tutarlılığı ve güvenlik açısından kritik öneme sahiptir. Hatalı veriler, uygulamanızda beklenmeyen davranışlara ve güvenlik açıklarına yol açabilir.
* ❌ **Controller'larda İş Mantığı Tutmaktan Kaçının:** Controller'lar sadece HTTP isteklerini almalı, DTO'ları validate etmeli ve iş mantığını Service katmanına delege etmelidir. Controller'lar şişkin olmamalıdır.
> **Neden Önemli?** Kodun ayrışmasını (separation of concerns) sağlar, test edilebilirliği artırır ve yeniden kullanılabilirliği kolaylaştırır.
* ✅ **Bağımlılık Enjeksiyonunu (DI) Doğru Kullanın:** NestJS'in güçlü DI sisteminden tam olarak yararlanın. Manuel olarak sınıf örnekleri oluşturmaktan kaçının; bunun yerine `constructor` tabanlı enjeksiyonu tercih edin.
> **Neden Önemli?** Modülerliği, test edilebilirliği ve kodun sürdürülebilirliğini artırır. Mocklama ve birim testleri için esneklik sağlar.
* ❌ **Global Middleware'leri Gereksiz Yere Kullanmayın:** Her isteğe uygulanan middleware'ler performans düşüşüne neden olabilir. Yalnızca belirli rotalara veya modüllere uygulanması gereken middleware'leri `forRoutes` veya `@UseMiddleware()` dekoratörleri ile sınırlayın.
> **Neden Önemli?** Gereksiz işlem yükünü azaltır ve API'nızın daha verimli çalışmasını sağlar, özellikle mobil istemciler için önemlidir.
* ✅ **Hata Yönetimini Merkezi Hale Getirin:** `ExceptionFilter`'lar kullanarak tüm hata durumlarını tek bir noktadan yönetin. Mobil uygulamalara anlaşılır ve tutarlı hata mesajları döndürün (örneğin, HTTP durum kodları ile).
> **Neden Önemli?** Kullanıcı deneyimini iyileştirir ve frontend geliştiricilerinin hata ayıklamasını kolaylaştırır. Güvenlik açığı olabilecek detaylı hata mesajlarını production'da göstermeyi engeller.
* ✅ **Güvenlik Başlıklarını ve CORS'u Yapılandırın:** `helmet` paketi ile çeşitli güvenlik başlıklarını (XSS, CSP vb.) uygulayın. Mobil uygulamaların farklı domainlerden istek yapabilmesi için CORS (Cross-Origin Resource Sharing) ayarlarını dikkatlice yapılandırın.
> **Neden Önemli?** API'nızı yaygın web güvenlik açıklarına karşı korur ve mobil istemcilerin erişimini düzenler. Burak Balkı olarak, 2026'da siber güvenlik tehditlerinin artmasıyla bu konunun kritik olduğunu vurguluyorum.
* ❌ **`any` Tipini Kullanmaktan Kaçının:** TypeScript'in gücünden tam olarak yararlanın. `any` tipini kullanmak, statik tip kontrolünün avantajlarını ortadan kaldırır ve hatalara davetiye çıkarır.
> **Neden Önemli?** Kod kalitesini düşürür, refactoring'i zorlaştırır ve çalışma zamanı hatalarına yol açabilir.
* ✅ **Logger Kullanımını Standartlaştırın:** Uygulamanızdaki tüm loglama işlemlerini `@nestjs/common`'dan gelen `Logger` servisi veya üçüncü taraf bir kütüphane (örneğin Winston, Pino) ile standartlaştırın. Log seviyelerini (debug, info, warn, error) doğru kullanın.
> **Neden Önemli?** Sorun giderme, izleme ve denetim için hayati öneme sahiptir. Production ortamında performans düşüşünü engellemek için gereksiz loglardan kaçının.
* ✅ **Ortam Değişkenlerini Kullanın:** Hassas bilgileri (veritabanı kimlik bilgileri, API anahtarları) doğrudan kodda tutmak yerine `.env` dosyaları ve `@nestjs/config` modülü ile ortam değişkenleri olarak yönetin.
> **Neden Önemli?** Güvenliği artırır ve farklı dağıtım ortamları (geliştirme, test, üretim) arasında kolay geçiş sağlar.
* ✅ **API Versiyonlamayı Planlayın:** Mobil uygulamaların uzun ömürlü olması için API versiyonlama stratejilerini (URI, Header veya Query tabanlı) baştan planlayın. Bu, geriye dönük uyumluluğu korumanıza yardımcı olur.
> **Neden Önemli?** Mobil uygulama güncellemelerini sorunsuz hale getirir ve eski istemcilerin çalışmaya devam etmesini sağlar.
### Yaygın Hatalar ve Çözümleri
Her geliştirici NestJS ile çalışırken belirli hatalarla karşılaşabilir. 2026'da bile hala sıkça görülen bu sorunları ve çözümlerini aşağıda bulabilirsiniz:
1. **Problem: Circular Dependency (Döngüsel Bağımlılıklar)**
* **Sebep:** İki modül veya servis birbirine doğrudan veya dolaylı olarak bağımlı olduğunda ortaya çıkar (örneğin, `A` modülü `B` modülünü, `B` modülü de `A` modülünü import ettiğinde).
* **Çözüm:** `forwardRef()` yardımcı fonksiyonunu kullanarak bağımlılık grafiğini çözün. Modüler yapıyı gözden geçirerek bağımlılıkları azaltmaya çalışın.
```typescript
// src/module-a/module-a.module.ts
import { Module, forwardRef } from '@nestjs/common';
import { ModuleBModule } from '../module-b/module-b.module';
@Module({
imports: [forwardRef(() => ModuleBModule)],
// ...
})
export class ModuleAModule {}
```
2. **Problem: CORS (Cross-Origin Resource Sharing) Hatası**
* **Sebep:** Mobil uygulamalar veya farklı bir domaindeki web istemcisi, NestJS API'nıza istek gönderdiğinde tarayıcı güvenlik politikaları gereği engellenir.
* **Çözüm:** NestJS uygulamanızda CORS'u etkinleştirin ve `origin` ayarlarını mobil uygulamanızın kaynaklarına göre yapılandırın.
```typescript
// src/main.ts
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.enableCors({
origin: ['http://localhost:8080', 'https://mobiluygulama.com'], // Mobil uygulamanızın URL'si
methods: 'GET,HEAD,PUT,PATCH,POST,DELETE',
credentials: true,
});
await app.listen(3000);
}
bootstrap();
```
3. **Problem: ValidationPipe Hataları Anlaşılır Değil**
* **Sebep:** `ValidationPipe` kullanılırken varsayılan hata mesajları bazen frontend için yeterince açıklayıcı olmayabilir.
* **Çözüm:** `ValidationPipe`'ın `exceptionFactory` özelliğini kullanarak özel hata mesajları döndürün veya DTO'larda `@IsNotEmpty({ message: '...' })` gibi dekoratörlerle özel mesajlar tanımlayın.
```typescript
// src/main.ts (Özel exceptionFactory örneği)
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
import { ValidationPipe, BadRequestException } from '@nestjs/common';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.useGlobalPipes(
new ValidationPipe({
exceptionFactory: (errors) => {
const result = errors.map((error) => ({
property: error.property,
constraints: error.constraints,
}));
return new BadRequestException(result);
},
stopAtFirstError: true, // İlk hatada dur
}),
);
await app.listen(3000);
}
bootstrap();
```
### Performans Optimizasyonu: Mobil API'lar İçin Kritik Adımlar
Mobil uygulamalar, genellikle kısıtlı ağ koşullarında veya düşük güçlü cihazlarda çalışır. Bu nedenle, NestJS backend'inizin performansı doğrudan kullanıcı deneyimini etkiler. 2026'da mobil API'larınızdan maksimum verim almak için aşağıdaki optimizasyon tekniklerini uygulayın:
1. **Önbellekleme (Caching):**
* **Metrik:** Yanıt süresi (ms) ve veritabanı yükü. Önbellekleme ile yanıt sürelerinde %50'ye varan iyileşmeler görülebilir.
* **Uygulama:** Sık erişilen ama nadiren değişen veriler için Redis gibi bir önbellek katmanı kullanın. NestJS'in `@nestjs/cache-manager` modülü ile kolayca entegre edilebilir.
```typescript
// src/app.module.ts
import { Module, CacheModule } from '@nestjs/common';
import * as redisStore from 'cache-manager-redis-store';
@Module({
imports: [
CacheModule.register({
store: redisStore,
host: 'localhost',
port: 6379,
ttl: 300, // saniye
}),
],
// ...
})
export class AppModule {}
```
Ardından servislerde `@CacheInterceptor` veya `CacheManager`'ı kullanın.
2. **Veritabanı Optimizasyonu:**
* **Metrik:** Sorgu yanıt süresi (ms), veritabanı CPU/bellek kullanımı.
* **Uygulama:** Doğru indeksleme, N+1 sorgu problemlerinden kaçınma, bağlantı havuzu (connection pooling) kullanma. ORM'lerde `eager loading` yerine `lazy loading` veya `select` optimizasyonlarını tercih edin.
> **Pro Tip:** TypeORM veya Prisma gibi ORM'ler kullanırken, `relations` veya `include` seçeneklerini dikkatli kullanın. Gereksiz join'ler performansı olumsuz etkileyebilir.
3. **Gzip Sıkıştırma:**
* **Metrik:** Yanıt boyutu (KB). Sıkıştırma ile yanıt boyutları %70'e kadar azalabilir.
* **Uygulama:** Özellikle JSON yanıtları gibi metin tabanlı veriler için `compression` middleware'ini kullanın. Bu, mobil ağ trafiğini azaltır.
```bash
npm install compression
```
```typescript
// src/main.ts
import { NestFactory } from '@nestjs/core';
import { AppModule } from './app.module';
import * as compression from 'compression';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.use(compression()); // Tüm yanıtları sıkıştırır
await app.listen(3000);
}
bootstrap();
```
4. **Asenkron İşlemler ve Arka Plan Görevleri:**
* **Metrik:** API yanıt süresi. Uzun süren işlemlerin arka plana atılmasıyla yanıt süreleri birkaç saniyeden milisaniyelere düşebilir.
* **Uygulama:** E-posta gönderme, resim işleme gibi uzun süren işlemleri doğrudan API isteği içinde yapmak yerine, RabbitMQ veya Kafka gibi mesaj kuyrukları aracılığıyla ayrı bir işçi (worker) servisine delege edin. NestJS'in mikroservisleri bu konuda çok yardımcı olur.
5. **Logger Seviyelerini Ayarlayın:**
* **Metrik:** CPU ve I/O kullanımı. Gereksiz loglama, production ortamında performansı düşürebilir.
* **Uygulama:** Production ortamında `verbose` veya `debug` gibi seviyeleri kapatın, sadece `info`, `warn` ve `error` seviyelerini aktif bırakın.
### Gerçek Dünya Proje Örneği: Mobil Kullanıcı Profili API'sı
Bu bölümde, NestJS best practices'lerini uygulayarak mobil uygulamalar için basit ama gerçekçi bir kullanıcı profili yönetim API'sı oluşturalım. Bu API, kullanıcıların profillerini görüntülemesini ve güncellemesini sağlayacak.
**Proje Yapısı:**
```
mobile-profile-api/
├── src/
│ ├── auth/
│ │ ├── auth.module.ts
│ │ ├── auth.service.ts
│ │ ├── auth.controller.ts
│ │ ├── jwt.strategy.ts
│ │ └── dto/
│ │ └── login.dto.ts
│ ├── users/
│ │ ├── users.module.ts
│ │ ├── users.service.ts
│ │ ├── users.controller.ts
│ │ └── dto/
│ │ ├── create-user.dto.ts
│ │ └── updat