Ulaşım
- Adres:Batıkent Mh. 8910 Sk. 6. Etap 1H No: 18 Yeni Toki Eyyübiye / Şanlıurfa (Yeni Alım Satım Karşısı)
- Telefon:0 (545) 528 88 93
- eMail: info@alestaweb.com
Yavaş sorgular ve yüksek CPU kullanımı MongoDB Performance sorunlarının başında gelir. MongoDB Performance Tuning ile database sorgularınızı 10x hızlandırabilir, server maliyetlerini %50'ye kadar azaltabilirsiniz. Alesta Web olarak production ortamlarında test edilmiş optimizasyon tekniklerini paylaşıyoruz.
MongoDB Performance sorunlarının %80'i şu nedenlerden kaynaklanır:
| Sorun | Belirtiler | Çözüm |
|---|---|---|
| Missing Indexes | Query süresi > 1000ms, full collection scan | Index oluşturma |
| Inefficient Queries | Yüksek CPU, RAM kullanımı | Aggregation pipeline optimize |
| Small WiredTiger Cache | Disk I/O yüksek, page faults | Cache boyutu artırma |
| Connection Pool Exhaustion | Timeout errors, queue buildup | Pool size tuning |
| Unoptimized Schema | Çok fazla JOIN ($lookup) | Embedding, denormalization |
Müşteri projelerinde yaptığımız MongoDB Performance Tuning sonrası ortalama iyileşmeler:
MongoDB Performance Tuning'in en kritik adımı doğru index'leri oluşturmak:
// users collection (5 million documents)
db.users.find({ email: "user@example.com", status: "active" })
// EXPLAIN plan:
{
"executionStats": {
"executionTimeMillis": 2850, // 2.8 saniye!
"totalDocsExamined": 5000000, // TÜM collection scan
"totalKeysExamined": 0, // Index kullanılmadı
"stage": "COLLSCAN" // ❌ Collection scan
}
}
// Compound index oluştur (email + status)
db.users.createIndex({ email: 1, status: 1 })
// Aynı query tekrar çalıştır
db.users.find({ email: "user@example.com", status: "active" })
// EXPLAIN plan:
{
"executionStats": {
"executionTimeMillis": 12, // 12ms! (%99.6 iyileşme)
"totalDocsExamined": 1, // Sadece 1 document
"totalKeysExamined": 1, // Index kullanıldı
"stage": "IXSCAN" // ✅ Index scan
}
}
E (Equality) → S (Sort) → R (Range) sırası ile index oluşturun:
// Query: status=active, createdAt sırala, age aralığı
db.users.find({
status: "active", // Equality
age: { $gte: 18, $lte: 65 } // Range
}).sort({ createdAt: -1 }) // Sort
// ❌ Yanlış index sırası
db.users.createIndex({ createdAt: -1, status: 1, age: 1 }) // Verimsiz
// ✅ Doğru index (ESR rule)
db.users.createIndex({ status: 1, createdAt: -1, age: 1 }) // Optimal
// Sonuç: %70 daha hızlı query
MongoDB Performance analizi için explain() komutu kullanın:
// Query performance analizi
db.orders.find({
customerId: "12345",
status: "pending",
total: { $gte: 100 }
}).sort({ createdAt: -1 }).explain("executionStats")
// Key metrics:
{
"executionTimeMillis": 45, // Query süresi
"totalDocsExamined": 120, // Taranan document sayısı
"totalKeysExamined": 120, // Taranan index key sayısı
"nReturned": 15, // Dönen sonuç sayısı
"executionStages": {
"stage": "FETCH", // Index + fetch
"inputStage": {
"stage": "IXSCAN", // ✅ Index kullanıldı
"indexName": "customerId_1_status_1_createdAt_-1"
}
}
}
// İdeal oran: totalDocsExamined ≈ nReturned (çok fazla gereksiz doc taranmamalı)
// ❌ Kötü: $match en sonda
db.orders.aggregate([
{
$lookup: { // 5M order + 2M customer JOIN → Çok yavaş
from: "customers",
localField: "customerId",
foreignField: "_id",
as: "customer"
}
},
{ $unwind: "$customer" },
{ $match: { status: "pending", "customer.country": "TR" } } // Filter en sonda!
])
// Execution time: 8500ms ❌
// ✅ İyi: $match en başta (index kullanır)
db.orders.aggregate([
{ $match: { status: "pending" } }, // ✅ Index kullan, 5M → 50K
{
$lookup: { // 50K order + 2M customer JOIN → Hızlı
from: "customers",
localField: "customerId",
foreignField: "_id",
as: "customer"
}
},
{ $unwind: "$customer" },
{ $match: { "customer.country": "TR" } } // Final filter
])
// Execution time: 320ms ✅ (%96 iyileşme)
Alesta Web production deneyimleri:
MongoDB Performance Tuning için schema design kritik:
// ❌ Kötü: Her query JOIN gerektirir (yavaş)
// users collection
{
_id: ObjectId("..."),
name: "John Doe",
email: "john@example.com"
}
// orders collection (1M documents)
{
_id: ObjectId("..."),
userId: ObjectId("..."), // Reference
items: [...],
total: 250
}
// Her order query $lookup gerektirir:
db.orders.aggregate([
{ $match: { _id: ObjectId("...") } },
{
$lookup: {
from: "users",
localField: "userId",
foreignField: "_id",
as: "user"
}
}
])
// Execution time: 45ms (her seferinde JOIN)
// ✅ İyi: Embedding (1-to-few relationship)
// orders collection
{
_id: ObjectId("..."),
user: { // Embedded document
_id: ObjectId("..."),
name: "John Doe",
email: "john@example.com"
},
items: [...],
total: 250
}
// Tek query, JOIN yok:
db.orders.findOne({ _id: ObjectId("...") })
// Execution time: 2ms (%95 iyileşme)
// ❌ Kötü: Sınırsız array growth (16MB document limit)
{
_id: ObjectId("..."),
productId: "12345",
reviews: [ // 10,000+ review → Document çok büyük
{ user: "...", rating: 5, comment: "..." },
{ user: "...", rating: 4, comment: "..." },
// ... 10,000 more
]
}
// Problem: Document > 16MB → Error, query çok yavaş
// ✅ İyi: Separate collection (1-to-many)
// products collection
{
_id: ObjectId("..."),
name: "Product Name",
avgRating: 4.5,
reviewCount: 10000
}
// reviews collection (ayrı)
{
_id: ObjectId("..."),
productId: ObjectId("..."), // Index!
user: "...",
rating: 5,
comment: "..."
}
// Index oluştur:
db.reviews.createIndex({ productId: 1, createdAt: -1 })
// Query (sayfalama ile):
db.reviews.find({ productId: ObjectId("...") })
.sort({ createdAt: -1 })
.limit(20)
.skip(0)
// Hızlı ve scalable
MongoDB Performance için connection pool ayarları önemli:
// ❌ Kötü: Default settings (production için yetersiz)
const mongoose = require('mongoose');
mongoose.connect('mongodb://localhost:27017/mydb');
// Default: maxPoolSize=100, minPoolSize=0
// Problem: High traffic'te connection exhaustion
// ✅ İyi: Production-ready settings
mongoose.connect('mongodb://localhost:27017/mydb', {
maxPoolSize: 200, // Max connections (server kapasitesine göre)
minPoolSize: 50, // Min connections (always ready)
maxIdleTimeMS: 30000, // Idle connection timeout
serverSelectionTimeoutMS: 5000,
socketTimeoutMS: 45000,
family: 4 // IPv4 kullan (faster DNS)
});
// Connection pool monitoring
mongoose.connection.on('open', () => {
console.log('MongoDB connected, pool ready');
});
// Alesta Web production: 200 max pool, 1000 req/s → %0 timeout
# ❌ Kötü: Default pool settings
from pymongo import MongoClient
client = MongoClient('mongodb://localhost:27017/')
# Default: maxPoolSize=100
# ✅ İyi: Optimized pool
client = MongoClient(
'mongodb://localhost:27017/',
maxPoolSize=300, # Max connections
minPoolSize=50, # Min connections
maxIdleTimeMS=30000,
serverSelectionTimeoutMS=5000,
connectTimeoutMS=10000,
retryWrites=True # Automatic retry on network errors
)
# Connection pool stats
client.server_info() # Verify connection
print(f"Active connections: {client.nodes}")
# Alesta Web Django app: 300 max pool, FastAPI async → 2500 req/s
MongoDB Performance Tuning için WiredTiger cache optimize edin:
# /etc/mongod.conf - Production settings
storage:
dbPath: /var/lib/mongodb
journal:
enabled: true
commitIntervalMs: 100 # Default 100ms, write performance
engine: wiredTiger
wiredTiger:
engineConfig:
# Cache size: 50% of RAM (default) → 70% için override
cacheSizeGB: 14 # 20GB RAM sunucuda 14GB cache
journalCompressor: snappy # zlib → snappy (daha hızlı)
directoryForIndexes: true # Index'leri ayrı klasörde
collectionConfig:
blockCompressor: snappy # Default, hızlı compression
indexConfig:
prefixCompression: true # Index compression (disk tasarrufu)
# Network settings
net:
port: 27017
bindIp: 127.0.0.1 # Localhost only (production'da private IP)
maxIncomingConnections: 65536 # Default 65536, yeterli
# Operation profiling
operationProfiling:
mode: slowOp
slowOpThresholdMs: 100 # 100ms+ query'leri logla
# Restart MongoDB
# sudo systemctl restart mongod
Alesta Web müşteri projesi (20GB RAM server):
MongoDB Performance Tuning sürekli monitoring gerektirir:
Managed MongoDB Atlas kullanıyorsanız, built-in Performance Advisor index önerileri sunar:
// Atlas Console → Performance Advisor
// Önerilen index'leri gösterir:
// Örnek öneri:
{
"namespace": "mydb.users",
"index": { "email": 1, "status": 1 },
"impact": "High",
"avgExecutionTime": "1250ms",
"suggestedExecutionTime": "15ms"
}
// Tek tıkla index oluşturabilirsiniz
// Profiler aktif et (slow queries logla)
db.setProfilingLevel(1, { slowms: 100 })
// Slow query'leri analiz et
db.system.profile.find({ millis: { $gt: 100 } })
.sort({ ts: -1 })
.limit(10)
.pretty()
// Örnek slow query:
{
"op": "query",
"ns": "mydb.orders",
"command": { "find": "orders", "filter": { "status": "pending" } },
"millis": 1250,
"planSummary": "COLLSCAN", // ❌ Index yok!
"ts": ISODate("2026-01-01T12:00:00Z")
}
// Çözüm: Index oluştur
db.orders.createIndex({ status: 1 })
# docker-compose.yml - MongoDB monitoring stack
version: '3.8'
services:
mongodb:
image: mongo:7
ports:
- "27017:27017"
mongodb-exporter:
image: percona/mongodb_exporter:0.40
command:
- '--mongodb.uri=mongodb://mongodb:27017'
- '--collect-all'
ports:
- "9216:9216"
prometheus:
image: prom/prometheus
volumes:
- ./prometheus.yml:/etc/prometheus/prometheus.yml
ports:
- "9090:9090"
grafana:
image: grafana/grafana
ports:
- "3000:3000"
environment:
- GF_SECURITY_ADMIN_PASSWORD=admin
# Key metrics to monitor:
# - Query execution time (p95, p99)
# - Connection pool usage
# - WiredTiger cache hit ratio
# - Disk I/O
# - CPU usage
MongoDB Performance Tuning ile query sürelerini %90+ azaltmak mümkün. En kritik adımlar: Index optimization (ESR rule), aggregation pipeline $match önceliklendirme, WiredTiger cache tuning (%70 RAM), schema design (embedding vs referencing).
Hızlı Kontrol Listesi:
Faydalı Kaynaklar:
© 2026 Alesta Web - MongoDB performance ve database optimization uzmanınız. Tüm hakları saklıdır.