Cloudflare Analytics ile Trafik Analizi: Kapsamlı Rehber
Cloudflare DNS yönetiminin en güzel yanlarından biri, alan adınızı Cloudflare’e taşıdığınız anda trafik analizine de erişim kazanmanızdır. Pek çok sysadmin Cloudflare’i sadece bir DNS sağlayıcısı olarak kullanıyor, oysa arkasında ciddi bir analytics motoru var. Bu yazıda Cloudflare Analytics’i derinlemesine inceleyeceğiz, API üzerinden nasıl veri çekebileceğinizi, bu verileri nasıl yorumlayabileceğinizi ve gerçek dünya senaryolarında nasıl kullanabileceğinizi ele alacağız.
Cloudflare Analytics Neden Önemli?
Geleneksel web analitiği araçları (Google Analytics gibi) JavaScript tabanlı çalışır. Yani kullanıcı tarayıcısında JavaScript’i kapattıysa, reklam engelleyici kullanıyorsa veya bot ise bu araçlar o trafiği göremez. Cloudflare Analytics ise farklı bir katmanda çalışıyor: DNS ve ağ katmanında.
Cloudflare, sitenize gelen her isteği proxy olarak karşıladığı için:
- Bot trafiği de dahil olmak üzere tüm istekleri görür
- Bant genişliği tüketimini gerçek zamanlı izler
- DDoS saldırılarını ve anormal trafik artışlarını tespit eder
- Güvenlik tehditleri hakkında detaylı log tutar
- Edge cache hit/miss oranlarını raporlar
Bu veri seti, sunucu kaynaklarınızı optimize etmek ve güvenlik politikalarınızı şekillendirmek için altın değerinde.
Dashboard Üzerinden Temel Navigasyon
Cloudflare dashboard’a girdiğinizde sol menüde Analytics & Logs bölümünü göreceksiniz. Buradan erişebileceğiniz ana modüller şunlar:
- Traffic: Genel trafik özeti, istek sayıları, bant genişliği
- Security: Firewall event’leri, bot yönetimi raporları
- Cache: Cache hit oranları, origin’e giden istek sayısı
- DNS: DNS sorgu istatistikleri
- Workers: Eğer Cloudflare Workers kullanıyorsanız execution metrikleri
- Web Vitals: Core Web Vitals performans verileri (Pro ve üstü)
Ücretsiz plan kullanıyorsanız verileri son 24 saat ile sınırlı görebilirsiniz. Pro plan 7 gün, Business plan 30 gün, Enterprise plan ise özelleştirilebilir aralıklar sunar. Bu durum ciddi bir kısıtlama gibi görünse de API üzerinden bazı geçici çözümler üretmek mümkün.
Cloudflare API ile Analytics Verisi Çekmek
Cloudflare’in GraphQL tabanlı Analytics API’si, dashboard’da göremediğiniz granülerlikte veri çekmenizi sağlar. Önce API token’ınızı oluşturmanız gerekiyor.
API Token Oluşturma:
- Cloudflare dashboard’da profil ikonuna tıklayın
- API Tokens sekmesine gidin
- Create Token butonuna basın
- Edit zone DNS template’ini seçin veya custom token oluşturun
- Zone Analytics Read iznini mutlaka ekleyin
Token’ı aldıktan sonra temel bir test yapalım:
# API token dogrulama
curl -X GET "https://api.cloudflare.com/client/v4/user/tokens/verify"
-H "Authorization: Bearer YOUR_API_TOKEN"
-H "Content-Type: application/json"
Zone ID’nizi de öğrenmeniz gerekecek:
# Zone listesini al
curl -X GET "https://api.cloudflare.com/client/v4/zones"
-H "Authorization: Bearer YOUR_API_TOKEN"
-H "Content-Type: application/json" | python3 -m json.tool
Çıktıda her domain için bir id alanı göreceksiniz. Bu değeri not edin, sonraki sorgularda kullanacağız.
GraphQL ile Detaylı Trafik Sorguları
Cloudflare’in analytics endpoint’i REST değil GraphQL kullanıyor. Bu başta garip gelebilir ama aslında çok daha esnek sorgular yazmanıza olanak tanıyor.
# Son 24 saatlik trafik ozeti - GraphQL sorgusu
ZONE_ID="your_zone_id_here"
API_TOKEN="your_api_token_here"
curl -X POST "https://api.cloudflare.com/client/v4/graphql"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
--data '{
"query": "{ viewer { zones(filter: {zoneTag: "'"$ZONE_ID"'"}) { httpRequests1dGroups(limit: 7, filter: {date_geq: "2024-01-01", date_leq: "2024-01-07"}) { sum { requests cachedRequests threats bytes cachedBytes pageViews } dimensions { date } } } } }"
}'
Bu sorgu oldukça uzun ve okuması zor. Daha temiz bir Python scripti yazalım:
#!/usr/bin/env python3
# cloudflare_analytics.py
import requests
import json
from datetime import datetime, timedelta
API_TOKEN = "your_api_token_here"
ZONE_ID = "your_zone_id_here"
GRAPHQL_URL = "https://api.cloudflare.com/client/v4/graphql"
headers = {
"Authorization": f"Bearer {API_TOKEN}",
"Content-Type": "application/json"
}
# Son 7 gunun tarihlerini hesapla
end_date = datetime.now().strftime("%Y-%m-%d")
start_date = (datetime.now() - timedelta(days=7)).strftime("%Y-%m-%d")
query = """
{
viewer {
zones(filter: {zoneTag: "%s"}) {
httpRequests1dGroups(
limit: 7
filter: {date_geq: "%s", date_leq: "%s"}
orderBy: [date_ASC]
) {
sum {
requests
cachedRequests
threats
bytes
cachedBytes
pageViews
}
dimensions {
date
}
}
}
}
}
""" % (ZONE_ID, start_date, end_date)
response = requests.post(
GRAPHQL_URL,
headers=headers,
json={"query": query}
)
data = response.json()
zones = data["data"]["viewer"]["zones"][0]
groups = zones["httpRequests1dGroups"]
print(f"{'Tarih':<15} {'Toplam Istek':<15} {'Cache Hit':<12} {'Tehdit':<10} {'Bant (MB)':<12}")
print("-" * 65)
for group in groups:
date = group["dimensions"]["date"]
requests_total = group["sum"]["requests"]
cached = group["sum"]["cachedRequests"]
threats = group["sum"]["threats"]
bytes_mb = round(group["sum"]["bytes"] / 1024 / 1024, 2)
print(f"{date:<15} {requests_total:<15} {cached:<12} {threats:<10} {bytes_mb:<12}")
Bu scripti çalıştırdığınızda günlük bazda trafik özetini terminalde görebilirsiniz.
Gerçek Dünya Senaryosu 1: Anormal Trafik Artışı Tespiti
Bir Cuma sabahı işe geldiğinizde sunucunuzun yavaş çalıştığını fark ettiniz. Cloudflare Analytics’e bakıyorsunuz ve bir önceki güne göre %400 artış var. Peki bu organik mi, bot mu, yoksa DDoS mu?
İşte bu soruyu cevaplamak için detaylı bir script:
#!/bin/bash
# traffic_anomaly_check.sh
# Saatlik trafik dagilimini kontrol eder
ZONE_ID="your_zone_id"
API_TOKEN="your_api_token"
YESTERDAY=$(date -d "yesterday" +%Y-%m-%dT00:00:00Z)
TODAY=$(date +%Y-%m-%dT00:00:00Z)
echo "=== Saatlik Trafik Analizi ==="
echo "Donem: $YESTERDAY - $TODAY"
curl -s -X POST "https://api.cloudflare.com/client/v4/graphql"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
-d @- << 'EOF'
{
"query": "{ viewer { zones(filter: {zoneTag: "ZONE_ID"}) { httpRequests1hGroups(limit: 24, filter: {datetime_geq: "YESTERDAY", datetime_leq: "TODAY"}) { sum { requests threats cachedRequests } dimensions { datetime } } } } }"
}
EOF
Cloudflare Security sekmesinden de destek alabilirsiniz. Firewall Events bölümünde hangi IP’lerin engellediğine bakın. Eğer çok sayıda IP’den kısa sürede yoğun istek geliyorsa ve bu istekler benzer User-Agent’lara sahipse bot saldırısıyla karşı karşıyasınızdır.
Bu tür durumlarda Cloudflare’in Under Attack Mode‘unu aktive etmek anlık çözüm sunar:
# Under Attack Mode'u aktive et (Security Level: under_attack)
curl -X PATCH "https://api.cloudflare.com/client/v4/zones/$ZONE_ID/settings/security_level"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
--data '{"value": "under_attack"}'
# Durumu dogrula
curl -X GET "https://api.cloudflare.com/client/v4/zones/$ZONE_ID/settings/security_level"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
# Saldiri bittikten sonra normal seviyeye dondur
curl -X PATCH "https://api.cloudflare.com/client/v4/zones/$ZONE_ID/settings/security_level"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
--data '{"value": "medium"}'
Cache Hit Oranını Optimize Etmek
Cloudflare Analytics’in en değerli metriklerinden biri cache hit ratio’dur. Bu oran yüksekse origin sunucunuza daha az yük bindirir, maliyetleriniz düşer ve kullanıcılar daha hızlı yanıt alır.
Düşük cache hit oranının yaygın sebepleri:
- Query string çeşitliliği: Her URL farklı kabul edilir, cache’e düşmez
- Cookie bazlı ayrım: Bazı uygulamalar cookie değerine göre farklı içerik dönebilir
- Bypass kuralları: Yanlış yapılandırılmış Page Rules
- Dinamik içerik: API endpoint’leri gibi zaten cache’lenmemesi gereken URL’ler
Cache performansını izlemek için:
#!/usr/bin/env python3
# cache_analysis.py
import requests
from datetime import datetime, timedelta
API_TOKEN = "your_api_token"
ZONE_ID = "your_zone_id"
headers = {
"Authorization": f"Bearer {API_TOKEN}",
"Content-Type": "application/json"
}
query = """
{
viewer {
zones(filter: {zoneTag: "%s"}) {
httpRequests1dGroups(
limit: 30
filter: {date_geq: "%s", date_leq: "%s"}
orderBy: [date_ASC]
) {
sum {
requests
cachedRequests
bytes
cachedBytes
}
dimensions {
date
}
}
}
}
}
""" % (
ZONE_ID,
(datetime.now() - timedelta(days=30)).strftime("%Y-%m-%d"),
datetime.now().strftime("%Y-%m-%d")
)
response = requests.post(
"https://api.cloudflare.com/client/v4/graphql",
headers=headers,
json={"query": query}
)
groups = response.json()["data"]["viewer"]["zones"][0]["httpRequests1dGroups"]
total_requests = sum(g["sum"]["requests"] for g in groups)
total_cached = sum(g["sum"]["cachedRequests"] for g in groups)
total_bytes = sum(g["sum"]["bytes"] for g in groups)
total_cached_bytes = sum(g["sum"]["cachedBytes"] for g in groups)
hit_ratio = (total_cached / total_requests * 100) if total_requests > 0 else 0
bandwidth_saved = (total_cached_bytes / total_bytes * 100) if total_bytes > 0 else 0
print(f"Son 30 Gun Cache Analizi")
print(f"------------------------")
print(f"Toplam Istek : {total_requests:,}")
print(f"Cache'den Gelen : {total_cached:,}")
print(f"Cache Hit Orani : %{hit_ratio:.2f}")
print(f"Toplam Bant : {total_bytes/1024/1024/1024:.2f} GB")
print(f"Tasarruf Edilen : {total_cached_bytes/1024/1024/1024:.2f} GB")
print(f"Bant Tasarruf : %{bandwidth_saved:.2f}")
if hit_ratio < 60:
print("nUYARI: Cache hit orani dusuk! Page Rules veya Cache Rules gozden gecirin.")
elif hit_ratio < 80:
print("nBILGI: Cache hit orani makul ama iyilestirilebilir.")
else:
print("nHAZAN: Cache hit orani iyi seviyede!")
Gerçek Dünya Senaryosu 2: Ülke Bazlı Trafik Analizi
E-ticaret sitesi yöneten bir müşteriniz var. Türkiye’deki kullanıcılar yoğun ama son zamanlarda Rusya ve Çin’den gelen bot trafiğinden şikayet ediyorlar. Ülke bazlı dağılımı görmek için:
# Ulke bazli trafik - GraphQL ile
curl -X POST "https://api.cloudflare.com/client/v4/graphql"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
-d '{
"query": "{ viewer { zones(filter: {zoneTag: "'"$ZONE_ID"'"}) { httpRequests1dGroups(limit: 1, filter: {date_geq: "2024-01-01", date_leq: "2024-01-07"}) { sum { countryMap { clientCountryName requests threats } } } } } }"
}' | python3 -c "
import json, sys
data = json.load(sys.stdin)
country_map = data['data']['viewer']['zones'][0]['httpRequests1dGroups'][0]['sum']['countryMap']
sorted_countries = sorted(country_map, key=lambda x: x['requests'], reverse=True)
print(f'{'Ulke':<25} {'Istek':<12} {'Tehdit':<10}')
print('-' * 50)
for country in sorted_countries[:15]:
print(f"{country['clientCountryName']:<25} {country['requests']:<12} {country['threats']:<10}")
"
Bu analiz sonucunda belirli ülkelerden gelen trafiği engellemek isteyebilirsiniz. Cloudflare Firewall Rules ile bunu yapabilirsiniz:
# Belirli ulkelerden gelen trafikle ilgili kural olustur
curl -X POST "https://api.cloudflare.com/client/v4/zones/$ZONE_ID/firewall/rules"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
--data '[
{
"filter": {
"expression": "(ip.geoip.country in {"RU" "CN" "KP"}) and (cf.threat_score gt 50)",
"paused": false,
"description": "Yuksek tehdit skoru olan ulkelerden gelen trafigi engelle"
},
"action": "block",
"description": "Yuksek riskli ulke + tehdit skoru filtresi"
}
]'
DNS Analytics ile Sorgu İzleme
Cloudflare DNS Analytics, DNS sorgularınızı da izlemenizi sağlar. Bu özellikle subdomain’lerin düzgün çalışıp çalışmadığını kontrol etmek için kullanışlı.
# DNS sorgu istatistikleri
curl -X GET "https://api.cloudflare.com/client/v4/zones/$ZONE_ID/dns_analytics/report"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
-G
--data-urlencode "since=$(date -d '7 days ago' +%Y-%m-%dT%H:%M:%SZ)"
--data-urlencode "until=$(date +%Y-%m-%dT%H:%M:%SZ)"
--data-urlencode "metrics=queryCount,uncachedCount,staleCount"
--data-urlencode "dimensions=queryName,queryType,responseCode"
--data-urlencode "limit=20"
--data-urlencode "sort=-queryCount" | python3 -m json.tool
Bu çıktıda NXDOMAIN (var olmayan domain) yanıtlarının yüksek olduğunu görürseniz ya yanlış yapılandırılmış bir DNS kaydı var ya da birisi subdomain enumeration saldırısı yapıyor demektir.
Otomatik Rapor Oluşturma ve Alerting
Günlük analytics raporunu otomatik almak ve anormal durumları e-posta ile bildirim yapmak için bir cron job hazırlayalım:
#!/usr/bin/env python3
# daily_report.py - Her gece cron'a ekle
import requests
import smtplib
from email.mime.text import MIMEText
from email.mime.multipart import MIMEMultipart
from datetime import datetime, timedelta
API_TOKEN = "your_api_token"
ZONE_ID = "your_zone_id"
ALERT_EMAIL = "[email protected]"
SMTP_SERVER = "smtp.gmail.com"
SMTP_PORT = 587
SMTP_USER = "[email protected]"
SMTP_PASS = "app_password"
THREAT_THRESHOLD = 1000 # Gunluk bu kadar tehdidin ustunde alert gonder
CACHE_HIT_MIN = 60 # Bu oranin altinda alert gonder
def get_yesterday_stats():
yesterday = (datetime.now() - timedelta(days=1)).strftime("%Y-%m-%d")
query = """
{
viewer {
zones(filter: {zoneTag: "%s"}) {
httpRequests1dGroups(
limit: 1
filter: {date_geq: "%s", date_leq: "%s"}
) {
sum {
requests
cachedRequests
threats
bytes
pageViews
}
}
}
}
}
""" % (ZONE_ID, yesterday, yesterday)
response = requests.post(
"https://api.cloudflare.com/client/v4/graphql",
headers={"Authorization": f"Bearer {API_TOKEN}", "Content-Type": "application/json"},
json={"query": query}
)
groups = response.json()["data"]["viewer"]["zones"][0]["httpRequests1dGroups"]
if not groups:
return None
stats = groups[0]["sum"]
cache_ratio = (stats["cachedRequests"] / stats["requests"] * 100) if stats["requests"] > 0 else 0
return {
"date": yesterday,
"requests": stats["requests"],
"cached": stats["cachedRequests"],
"threats": stats["threats"],
"bytes_gb": stats["bytes"] / 1024 / 1024 / 1024,
"page_views": stats["pageViews"],
"cache_ratio": cache_ratio
}
def send_report(stats):
alerts = []
if stats["threats"] > THREAT_THRESHOLD:
alerts.append(f"KRITIK: {stats['threats']:,} tehdit tespit edildi!")
if stats["cache_ratio"] < CACHE_HIT_MIN:
alerts.append(f"UYARI: Cache hit orani %{stats['cache_ratio']:.1f} - cok dusuk!")
subject = f"Cloudflare Gunluk Rapor - {stats['date']}"
if alerts:
subject = "ALERT! " + subject
body = f"""
Cloudflare Analytics - Gunluk Rapor
Tarih: {stats['date']}
OZET
----
Toplam Istek : {stats['requests']:,}
Sayfa Gorunumu : {stats['page_views']:,}
Cache Hit : %{stats['cache_ratio']:.1f}
Tehdit Sayisi : {stats['threats']:,}
Bant Genisligi : {stats['bytes_gb']:.2f} GB
{"UYARILAR" + chr(10) + "-" * 20 + chr(10) + chr(10).join(alerts) if alerts else "Herhangi bir anormal durum tespit edilmedi."}
"""
msg = MIMEMultipart()
msg['From'] = SMTP_USER
msg['To'] = ALERT_EMAIL
msg['Subject'] = subject
msg.attach(MIMEText(body, 'plain', 'utf-8'))
with smtplib.SMTP(SMTP_SERVER, SMTP_PORT) as server:
server.starttls()
server.login(SMTP_USER, SMTP_PASS)
server.send_message(msg)
print(f"Rapor gonderildi: {ALERT_EMAIL}")
if __name__ == "__main__":
stats = get_yesterday_stats()
if stats:
send_report(stats)
else:
print("Veri alinamadi!")
Bu scripti cron’a eklemek için:
# Crontab'a ekle - Her sabah 08:00'de calistir
crontab -e
# Su satiri ekle:
0 8 * * * /usr/bin/python3 /opt/scripts/daily_report.py >> /var/log/cf_reports.log 2>&1
Cloudflare Logs ile Derinlemesine İnceleme
Enterprise plan kullanıyorsanız Logpush özelliğiyle ham logları S3, R2 veya başka bir hedefe aktarabilirsiniz. Business plan sahipleri ise Log Retention özelliğiyle geçmişe dönük log sorgusu yapabilir.
Logpush yapılandırması için temel endpoint:
# Logpush job olustur - S3'e gonder
curl -X POST "https://api.cloudflare.com/client/v4/zones/$ZONE_ID/logpush/jobs"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
--data '{
"name": "http-logs-s3",
"destination_conf": "s3://bucket-adi/klasor/{DATE}?region=eu-central-1",
"dataset": "http_requests",
"logpull_options": "fields=ClientIP,ClientRequestHost,ClientRequestMethod,ClientRequestURI,EdgeResponseStatus,EdgeResponseBytes,CacheCacheStatus,ClientCountry,BotScore×tamps=rfc3339",
"enabled": true
}'
Performans Metrikleri ve Web Vitals
Pro plan ve üzeri kullanıcılar için Web Analytics modülü Core Web Vitals verisi sunar. Bu veriler JavaScript SDK’sı olmadan, doğrudan Cloudflare’in edge’inden toplanır.
Dashboard’daki bu verileri API üzerinden çekmek için:
# Web Analytics - Sayfa performansi sorgusu
curl -X POST "https://api.cloudflare.com/client/v4/graphql"
-H "Authorization: Bearer $API_TOKEN"
-H "Content-Type: application/json"
-d '{
"query": "{ viewer { accounts(filter: {accountTag: "ACCOUNT_ID"}) { rumPageloadEventsAdaptiveGroups(limit: 10, filter: {date_geq: "2024-01-01"}, orderBy: [count_DESC]) { count dimensions { requestPath } avg { pageLoadTime } quantiles { pageLoadTimeP50 pageLoadTimeP75 pageLoadTimeP95 } } } } }"
}' | python3 -m json.tool
Bu çıktıda pageLoadTimeP95 değerine dikkat edin. P95 değeri 3000ms’i (3 saniye) aşıyorsa ciddi bir performans sorunu var demektir.
Sonuç
Cloudflare Analytics, DNS yönetiminin çok ötesine geçen kapsamlı bir monitoring ve güvenlik aracıdır. Bu yazıda ele aldığımız konuları özetlersek:
- GraphQL API ile özelleştirilmiş sorgular yazarak ihtiyacınıza göre veri çekebilirsiniz
- Cache hit oranı en kritik metriklerden biridir, düşük kalırsa hem maliyet hem performans zarar görür
- Tehdit analizi ile saldırıları erkenden tespit edip under attack mode veya firewall kurallarıyla müdahale edebilirsiniz
- Ülke bazlı analiz ile hedeflenmiş bot trafiğini tespit edip engelleyebilirsiniz
- Otomatik raporlama kurarak sabah kahvenizle birlikte sitenizin gece boyunca nasıl davrandığını görebilirsiniz
- Logpush ile ham logları kendi sistemlerinize aktararak Elasticsearch ya da Grafana gibi araçlarla daha derin analizler yapabilirsiniz
Cloudflare’i sadece “DNS’i yönetiyorum” diye kullanmak, bir yarış arabasını park yeri bekçisi olarak kullanmaya benziyor. Analytics modüllerine zaman ayırın, API’yi öğrenin ve veriyi çalışır hale getirin. Sunucularınızın sağlığı ve sitenizin güvenliği için bu yatırım kesinlikle karşılığını verecektir.
