Prometheus + Grafana, açık kaynak dünyasının monitoring standardıdır. Prometheus zaman serisi veri toplar ve sorgular, Grafana bu veriyi güzel dashboard''larda gösterir. Bu rehber sıfırdan bir monitoring stack kurup 20 sunucuyu tek ekrandan izlemeyi anlatır.

Mimari

İlgili rehberler: DNS nedir, ayarları değiştirme · Domain adı ve WHOIS sorgulama · Hosting türleri rehberi · Nginx yapılandırma · Plesk panel yönetimi

Prometheus pull model kullanır — her 15 saniyede hedef servislerin /metrics endpoint''ine istek atar, cevabı disk''te time-series DB''ye yazar. Node Exporter gibi küçük ajanslar her sunucuda CPU/RAM/disk metric''lerini açar. Grafana, Prometheus''u data source olarak kullanıp panel çizer.

Kurulum: Docker Compose

# compose.yml
services:
  prometheus:
    image: prom/prometheus:latest
    volumes:
      - ./prometheus.yml:/etc/prometheus/prometheus.yml
      - prometheus-data:/prometheus
    ports: ['9090:9090']
    command:
      - '--config.file=/etc/prometheus/prometheus.yml'
      - '--storage.tsdb.retention.time=30d'
      - '--web.enable-lifecycle'
    restart: unless-stopped

  grafana:
    image: grafana/grafana:latest
    ports: ['3000:3000']
    volumes:
      - grafana-data:/var/lib/grafana
    environment:
      GF_SECURITY_ADMIN_PASSWORD: supersecret
      GF_SERVER_ROOT_URL: https://monitor.example.com
    restart: unless-stopped

  node-exporter:
    image: prom/node-exporter:latest
    volumes:
      - /proc:/host/proc:ro
      - /sys:/host/sys:ro
      - /:/rootfs:ro
    command:
      - '--path.procfs=/host/proc'
      - '--path.sysfs=/host/sys'
      - '--path.rootfs=/rootfs'
    ports: ['9100:9100']
    restart: unless-stopped

volumes:
  prometheus-data:
  grafana-data:

prometheus.yml

global:
  scrape_interval: 15s
  evaluation_interval: 15s

scrape_configs:
  - job_name: prometheus
    static_configs:
      - targets: ['localhost:9090']

  - job_name: node
    static_configs:
      - targets:
          - node-exporter:9100
          - web-1.example.com:9100
          - web-2.example.com:9100
          - db-1.example.com:9100

  - job_name: nginx
    static_configs:
      - targets: ['web-1.example.com:9113']  # nginx-prometheus-exporter

  - job_name: postgres
    static_configs:
      - targets: ['db-1.example.com:9187']   # postgres_exporter

alerting:
  alertmanagers:
    - static_configs:
        - targets: ['alertmanager:9093']

rule_files:
  - alerts.yml

Uygulama Metriklerini Açmak

// Node.js + prom-client
const client = require('prom-client');
const register = client.register;

// Default Node.js metrics
client.collectDefaultMetrics({ register });

// Custom metrics
const httpDuration = new client.Histogram({
    name: 'http_request_duration_seconds',
    help: 'HTTP request duration',
    labelNames: ['method', 'route', 'status'],
    buckets: [0.01, 0.05, 0.1, 0.5, 1, 5]
});

app.use((req, res, next) => {
    const end = httpDuration.startTimer();
    res.on('finish', () => {
        end({ method: req.method, route: req.route?.path || 'unknown', status: res.statusCode });
    });
    next();
});

app.get('/metrics', async (req, res) => {
    res.set('Content-Type', register.contentType);
    res.send(await register.metrics());
});

PromQL — Temel Sorgular

# CPU kullanım yüzdesi (son 5 dk)
100 - (avg by(instance) (rate(node_cpu_seconds_total{mode="idle"}[5m])) * 100)

# RAM kullanım yüzdesi
(1 - (node_memory_MemAvailable_bytes / node_memory_MemTotal_bytes)) * 100

# Disk doluluğu
100 - (node_filesystem_avail_bytes{fstype!~"tmpfs|overlay"} / node_filesystem_size_bytes * 100)

# HTTP P95 latency
histogram_quantile(0.95, sum(rate(http_request_duration_seconds_bucket[5m])) by (le))

# Hata oranı
sum(rate(http_request_duration_seconds_count{status=~"5.."}[5m]))
  / sum(rate(http_request_duration_seconds_count[5m]))

# Requests per second
sum(rate(http_request_duration_seconds_count[1m])) by (route)

Grafana Dashboard

Elinizde bir dashboard yazmak yerine hazır panel import edin: grafana.com/grafana/dashboards → Node Exporter Full (1860), NGINX (12708), PostgreSQL (9628). Grafana''da Dashboard → Import → ID''yi yaz → Data source seç.

Alertmanager + Alert Rules

# alerts.yml
groups:
  - name: host
    rules:
      - alert: HighCPU
        expr: 100 - (avg by(instance) (rate(node_cpu_seconds_total{mode="idle"}[5m])) * 100) > 85
        for: 10m
        labels: { severity: warning }
        annotations:
          summary: '{{ $labels.instance }} CPU > %85 (10 dk)'

      - alert: DiskFull
        expr: (node_filesystem_avail_bytes{mountpoint="/"} / node_filesystem_size_bytes) < 0.1
        for: 5m
        labels: { severity: critical }
        annotations:
          summary: '{{ $labels.instance }} disk %10 altında'

      - alert: HostDown
        expr: up == 0
        for: 2m
        labels: { severity: critical }
        annotations:
          summary: '{{ $labels.instance }} yanıt vermiyor'
# alertmanager.yml
route:
  receiver: slack
  group_wait: 30s
  group_interval: 5m
  repeat_interval: 4h
  routes:
    - match: { severity: critical }
      receiver: pagerduty

receivers:
  - name: slack
    slack_configs:
      - api_url: https://hooks.slack.com/services/XXX
        channel: '#alerts'
        title: '{{ .GroupLabels.alertname }}'
        text: '{{ range .Alerts }}{{ .Annotations.summary }}\n{{ end }}'

  - name: pagerduty
    pagerduty_configs:
      - service_key: YOUR_KEY

Retention ve Storage

  • Default retention 15 gün. --storage.tsdb.retention.time=30d ile uzat
  • Uzun süre için Thanos veya VictoriaMetrics kullan
  • Disk tahmini: 1-2 bytes × samples/second × seconds
  • Örnek: 100 target × 1000 metric × 4 bytes × 86400 sec ≈ 33 GB/gün

Güvenlik

  • Prometheus ve Grafana public açılmamalı — reverse proxy + basic auth
  • Grafana anonymous access kapalı, strong admin password
  • Cloudflare Access veya VPN arkasında
  • TLS zorunlu

Modern Web Hosting ve Sunucu Altyapısı

Performanslı bir web hosting hizmeti üç temel altyapı kararına dayanır: NVMe SSD diskler (klasik SATA SSD'ye göre 4-6 kat IOPS), LiteSpeed Web Server veya Nginx + LSCache kombinasyonu (Apache'ye göre 9 kat istek kapasitesi) ve CloudLinux + Imunify360 izolasyonu. Hosting sağlayıcısının kontrol paneli (cPanel, Plesk, DirectAdmin), günlük yedek politikası, veri merkezi konumu ve destek ekibi yanıt süresi de büyük fark yaratır. Türkiye lokasyonu yerli ziyaretçilere düşük gecikme verirken; Hetzner Frankfurt veya OVH Roubaix gibi Avrupa lokasyonları global trafik için daha uygundur. Site büyüdükçe paylaşımlı hosting'ten VPS, ardından dedicated server'a geçiş; CPU/RAM/disk kaynaklarının web sitemizin ihtiyaçlarına göre ölçeklenmesini sağlar.

Monitoring stack kurulumu

Prometheus, Grafana, Alertmanager kurulumu ve custom dashboard tasarımı için iletişime geçin

WhatsApp