GCP Maliyeti: Bir Kararın 8 Yıllık Faturası
Bu yazıyı okuduğunuz sayfa, anlatacağım sistemin kendisi.
Aynı kod tabanı üç ayrı canlı web sitesini ve bir beta ortamını çalıştırıyor. Bu sayfayı size sunucuda hazırlayan kod da, içeriğini yazdığım yönetim paneli de, arka planda çalışan işler de tek bir depoda (repository) duruyor.
Bir süredir kodun bir bölümünü yapay zekâ ajanları (AI agents) yazıyor. Onların kullandığı araçlar, çağırdıkları yetenekler (skills) ve uymak zorunda oldukları kurallar da aynı deponun içinde — şu an okuduğunuz yazıyı yayına alan ajan dahil. Yani depo yalnızca siteyi çalıştırmıyor; sitenin nasıl geliştirileceğini de tarif ediyor.
Durum: 2018'de bir gelecek planı
2018'e kadar sitem Drupal üzerinde çalışıyordu ve ayrılma kararım bir şikâyetin sonucu değildi; bir planın parçasıydı. PHP'den uzaklaşıp Node.js ve Angular'a geçmem gerekiyordu, ama daha belirleyici olan madde şuydu: bir şeyi önerebilmek için önce onu kendim kullanmalıyım. Müşterilerime Google Cloud ve Firebase önereceksem, “peki ben neden kullanmıyorum?” sorusuna cevap aramaktansa doğrudan kullanmayı tercih ederim. Bulut benim için yeni değildi — o dönemde Azure üzerinde çalışıyordum ve sertifikalarım vardı; yine de kendi sistemim için GCP'yi seçtim.
Mimariyi seçerken üç gerekçem vardı: maliyet, güvenlik ve basitlik. Yönetilen bir platformda bakımını üstlendiğim bir sunucu, ayarladığım bir web sunucusu ya da açık kalmış bir eklenti yok; içerik veri olarak duruyor, yürütülebilir şablon olarak değil.
Yama işi büsbütün ortadan kalkmıyor elbette — yer değiştiriyor. İşletim sistemi ve web sunucusu yerine çalışma zamanı sürümleri ve bağımlılıklar geliyor; Cloud Functions çalışma zamanlarını takvimle kullanımdan kaldırıyor, Angular'ın da kendi sürüm takvimi var. Aradaki fark şu: bu yamalar acil değil planlı, ve büyük kısmı dağıtım hattında otomatik yapılıyor.
Basitlik kısmı kişisel bir tercih ama tarifi net: GCP daha az soru soruyor. Bir şeyi kurarken kararların çoğunu makul bir varsayılanla kendisi veriyor. Azure ise her ince ayrıntıyı size soruyor — ki bu bazen tam olarak istediğiniz şeydir, ama her soru cevaplanması ve sonra yıllarca hatırlanması gereken bir karar demek. Az soru, az bakım.
Maliyetle güvenlik ise 2018'de birer tahmindi. Bu yazının sonundaki tablo, o tahminin sekiz yıl sonraki karşılığı.
O ilk sistem 2018'den itibaren iki ortam çalıştırıyordu: beta ve supermurat.com. Dağıtım hattı, testler ve sürüm akışı ilk günden otomatikti — kodu bugün hâlâ açıp bakabilirsiniz. Ama beta'yı ikinci bir site saymak dürüst olmaz: teknik olarak bir kopyaydı, SEO'ya kapalı ve dışarıya gizli.
Nisan 2024'te bugünkü depoyu açtım ve iki karar aldım: Angular'da büyük bir sürüm sıçraması yapmak ve geliştirmeyi kapalı kaynağa taşımak. Sebebi şuydu — artık şirketin kendi sitesi de sisteme eklenecekti ve daha çok özelliği olan, daha ileri bir sistem kurmayı planlıyordum. Yapay zekâ tarafı o gün yoktu; o 2026'da geldi.
Ne kurdum
Angular üzerine kurulu tek bir monorepo: herkese açık site, yönetim paneli ve ikisinin paylaştığı ortak kütüphane. Üç canlı web sitesi ve beta, dört ayrı GCP projesi olarak duruyor — verileri, kotaları ve erişim hakları birbirinden tamamen ayrı.
İçerik Firestore'da: makaleler, sayfalar, menü, altbilgi, iletişim bilgileri. Sayfalar Cloud Functions üzerinde sunucuda hazırlanıyor (SSR) ve Firebase Hosting'in önbelleğinden dağıtılıyor. Siteler arasındaki fark koda değil, derleme yapılandırmasına yazılı — bir bileşenin içinde “burası şu site ise” diye bir koşul yok.
Bakım işlerinin çoğu elle tetiklenen işler olarak duruyor: site haritasını üretmek, llms.txt'yi yenilemek, eksik açıklama ve SEO alanlarını doldurmak, çeviri eşlerini tazelemek. Bunlar dağınık betikler değil, hepsi aynı iş kuyruğundan geçiyor ve her koşu kendi kaydını bırakıyor. Temmuz'daki arıza da tam olarak bunlardan birini çalıştırmayı unutmamdan çıktı.
Her dağıtımın ardından canlı sitede testler koşuyor; başarısız olurlarsa sürüm kendiliğinden geri alınıyor (rollback). Yedekleme de sistemin bir parçası: her pazar gecesi Firestore'un tamamı otomatik olarak dışa aktarılıyor.
Nasıl çalıştığının ayrıntısı ayrı bir yazıda: Ziyaret Ettiğiniz Mimari: Bu Site GCP'de Nasıl Çalışıyor?
Mimarinin sınavı: iki kez
Sistemin asıl iddiası şuydu: birbirinden gerçekten farklı siteleri tek kod tabanından çalıştırmak. Bunu iki kez sınadı.
Birincisi 2024'te utopical.dev oldu — supermurat.com'un kopyası değil, varlıkları ve yapılandırmasının tamamı ayrı bir site. İkincisi 2026'da sevgiyle.org: teması, varlıkları ve amacı da farklı, 11 Mayıs 2026'da yayına girdi. İkisinde de mimaride hiçbir değişiklik gerekmedi — bir ortam dosyası, bir stil sayfası ve bir dağıtım hattı. Ortak kodda tek satır koşul yok.
Bunu şu an dışarıdan doğrulayamazsınız; sistem 2024'ten beri kapalı kaynak. Doğrulayabileceğiniz şey, aynı yaklaşımın 2018-2024 arasındaki hâli: o depo hâlâ açık ve arşivde duruyor.
Bunun ne kadara mal olduğunu da tam olarak biliyorum, çünkü aşağıdaki tablo o ayın faturası: yeni sitenin toplam içindeki payı ₺2,13 — bugünkü kurla dört buçuk sent.
Peki bu ne kadara mal oluyor?
Mayıs 2026 faturasının tamamı — dört ortamın hepsi, yani üç canlı web sitesi ve beta ortamı birlikte.
| Kalem | O ay ne çalıştı | Fatura |
|---|---|---|
| Cloud DNS — yönetilen bölge | 3,7 bölge/ay | ₺33,38 |
| Secret Manager | 8,1 sır sürümü/ay | ₺5,67 |
| Cloud Scheduler | 4 iş · 114 iş-günü | ₺3,05 |
| Cloud DNS — sorgu | 162.408 sorgu | ₺2,93 |
| Cloud Storage | 0,46 GiB | ₺0,43 |
| Cloud Run Functions | 39.739 çağrı · 49.221 CPU-saniye | ₺0,00 |
| Firestore | 132.015 okuma · 238 yazma | ₺0,00 |
| Firebase Hosting | 2,34 GiB giden trafik | ₺0,00 |
| Cloud Build | 40,65 dakika | ₺0,00 |
| App Check (reCAPTCHA Enterprise) | 1.729 doğrulama | ₺0,00 |
| Toplam | ₺45,46 |
Dolar karşılıkları 8 Eylül 2026 kuruyla verilmiştir (1 USD ≈ ₺48,5). Faturalar TRY olarak kesildiği ve kur bu sekiz ayda değiştiği için dolar rakamları yaklaşıktır — aylık toplam ₺45,46 ≈ $0,94.
Bu tablonun ilginç yanı toplamı değil, dağılımı. Faturanın yüzde 80'i Cloud DNS. Sayfaların sunucuda hazırlanması, iş kuyruğu, veritabanı okumaları, hosting trafiği, derlemeler — hepsi ücretsiz kotanın (free tier) içinde kaldı. Bu kota proje başına işliyor, yani dört proje dört kat alan demek; sınırların güncel hâli Firebase'in fiyatlandırma sayfasında duruyor. Yani ödenen para hesaplamaya değil, alan adı bölgelerine, sırlara ve zamanlayıcıya gidiyor.
Neden Cloud DNS?
Çünkü her şeyi tek yerden yönetmek istiyorum ve alan adı çözümlemesinde hizmet kalitesi benim için pazarlık konusu değil. Azure ve AWS'nin dengi hizmetleri de aşağı yukarı aynı fiyatta; ücretsiz alternatiflerin çoğu ise bir SLA/SLO taahhüdü vermiyor. Çözümleme sitenin en alttaki katmanı — orada tasarruf etmek, üstteki her şeyin ayakta kalmasını garantisiz bir hizmete bağlamak demek. Faturanın en büyük kalemi olması beni rahatsız etmiyor; bilerek verilmiş bir karar.
Faturanın içine saklanmış tarih
Cloud Scheduler satırında 114 birim görünüyor, oysa sistemde haftada bir çalışan tek bir zamanlanmış iş türü var. Sebebi şu: Cloud Scheduler tetiklenme başına değil, işin tanımlı durduğu gün başına faturalanıyor — çalışsa da çalışmasa da. Dört projenin her birinde birer iş var; üçü mayısın 31 gününün tamamında tanımlıydı, dördüncüsü ise ayın 11'inde kuruldu. 3 × 31 + 21 = 114. Ücretsiz hak (üç iş) da proje başına değil fatura hesabı başına verildiği için dördüncüsü ücrete giriyor. Ücretsiz kotanın kapsamı hizmete göre değişiyor — Firestore, Functions ve Hosting proje başına sayıyor, Cloud Scheduler fatura hesabı başına. Çok projeli kurulumlarda en sık yapılan hesap hatası da tam burada.
Aynı kesirli yapı DNS satırında da var: 3,7 bölge/ay. Üç bölge ayın tamamı boyunca, dördüncüsü de ayın yaklaşık üçte ikisi kadar tanımlıydı — yani yine 11 Mayıs civarı. İki ayrı kalem, birbirinden bağımsız olarak aynı şeyi söylüyor: sevgiyle.org o gün doğdu. Yukarıda bu tarihi dağıtım hattının kurulduğu günden almıştım; fatura da aynı günü gösteriyor.
2026'nın ilk sekiz ayında toplam ₺414 (~$8,5) ödedim: aylık ₺28 ile ₺143 arasında, ortalaması ₺52 (~$1,07). Bu rakamı “bulut ucuz” diye sunmuyorum, çünkü bu site yüksek trafikli bir site değil. Sunduğum şey başka: üç canlı web sitesi ve yanlarındaki beta ortamı, sunucuda hazırlanan sayfalar, yönetim paneli, arama, bot koruması, haftalık otomatik yedek ve başarısız dağıtımı geri alan bir hat — hepsi her saniye ayakta ve hazır. Bu ölçekte hazır bulunurluğun fiyatı bu.
Temmuz: sistemin kendini haber verdiği ay
Temmuz 2026'da otomatik uyarı (alert) e-postaları gelmeye başladı. Sebep trafik değildi, bendim: sitemap.xml'i Firestore koleksiyonundan silmiş, yenisini üretecek işi çalıştırmayı unutmuştum. Kaynak yerinde olmayınca bu isteği karşılayan fonksiyondaki promise zinciri hiçbir yolda sonlanmıyordu; istek hata vermiyor, öylece bekliyordu. Devreye Cloud Functions'ın 60 saniyelik zaman aşımı (timeout) giriyor ve isteği kendisi iptal ediyordu. Günlükler bunu açıkça gösteriyordu — her sitemap.xml isteği bir dakika boyunca işlemci yakıp zaman aşımıyla kesiliyordu. Ziyaretçinin gezindiği sayfalar ise çalışmaya devam ediyordu.
İlginç olan şu: bunu hiçbir test yakalamadı. Dağıtım sonrası koşan canlı test paketi sayfaları geziyordu, sitemap.xml'i değil — sayfalar da gayet çalışıyordu. Ortada bir istisna fırlamadığı için klasik hata izleme de sessizdi. Haber veren şey platformun kendi izlemesi oldu: otomatik uyarı, günlükler ve sistem raporları.
Fatura ise hatanın teşhisi değil, sonucuydu. O ay ₺143'e (~$2,95) çıktı — bir önceki ayın neredeyse üç katı. Buradan çıkan asıl ders şu: zaman aşımı bir güvenlik ağıdır, çözüm değil. Firebase isteği 60 saniyede kesip kendini koruduğu için sistem çökmedi ve ziyaretçi hiçbir şey fark etmedi; ama o 60 saniyelerin her biri faturaya yazıldı. Bir arızanın sessizce yutulması, olmadığı anlamına gelmiyor — bunu size ancak izleme (monitoring) söyler.
İkinci ağ da parayı doğrudan izliyor: GCP'nin bütçe yönetimi bir eşik aşıldığında e-posta gönderiyor ve ayarına göre hizmeti duraklatabiliyor da. Zaman aşımı sistemi ayakta tutar, bütçe uyarısı ise sizi haberdar eder; ikisi farklı işler ve ikisi de gerekli.
Dosya geri kondu, promise zinciri her yolda sonlanacak şekilde düzeltildi ve Ağustos faturası ₺56'ya (~$1,16) döndü.
Asıl düzeltme: iki katman
Dosyayı geri koymak düzeltme değildi; asıl iş iki katmanda oldu.
Birincisi kodda. Bu uçları karşılayan yol artık her durumda bir cevap üretiyor: kaynak yoksa istek askıda kalmıyor, 404 dönüyor. İncelik şurada — o adres sabit bir liste değil, bir isim ailesi eşleştiriyor. Yani llms-full.txt gibi, bir tarayıcının kolayca tahmin edeceği ve arkasında hiçbir doküman olmayan isimler de aynı yola düşüyor. Üretilmiş bir çıktının kaynağı eksikken yapması gereken şey bozulmak değil, zarifçe düşmek. Benim hatam bir işi çalıştırmayı unutmaktı; asıl kusur ise o unutmanın bu sonucu doğurabilmesiydi.
Ve bu, ilk düşündüğümden kritikti: SSR fonksiyonu en fazla iki örnekle çalışıyor, askıda kalan istekler de bu eşzamanlılığı sitedeki bütün sayfalarla paylaşıyor. Yani Temmuz'daki arıza sadece para yakmadı — biraz daha yoğun bir bot trafiğiyle çakışsaydı siteyi de yavaşlatabilirdi. Faturayla öğrenmiş olmam, ucuz atlattığım anlamına geliyor.
İkincisi testte. Dağıtım sonrası koşan canlı test paketi o güne kadar yalnızca sayfaları geziyordu; artık sitemap.xml, llms.txt ve robots.txt'i de istiyor ve sitemap.xml'in gerçekten bir site haritası döndürdüğünü doğruluyor — çünkü fonksiyon bir hata sayfasını da 200 ile dönebilir. Aynı arıza bir dağıtımla gelirse artık dağıtım yeşile dönmez; sistem kendiliğinden eski çalışan sürüme döner.
Kapatamadıklarım
Bu ağ her deliği kapatmıyor, ve kalanları da yazmam gerekiyor:
- İçerik tarafından gelen arızada geri alınacak bir sürüm yok. Benimki gibi bir durumda ortada dağıtım olmadığı için o hat hiç devreye girmiyor; orada beni hâlâ uyarılar koruyor.
- Uptime kontrolüm yok. Bilerek: sistemi sürekli dışarıdan yoklamak da kendi başına bir yük ve bu ölçekte karşılığını vermiyor. Dolayısıyla yukarıdaki “her saniye ayakta” ifadem bir ölçüm değil, bir gözlem — ve Temmuz bunun sınırını gösterdi.
- Harcamanın tavanı iki yerden bağlı. Fonksiyon en fazla iki örnekle çalışıyor ve bütçe yönetiminde tanımlı bir eşik var; eşik aşılırsa haber geliyor, ayarına göre hizmet durdurulabiliyor da. Rakamı paylaşmıyorum ama sınırsız bir kart değil.
- Ziyaretçi sayısı bu yazıda yok. Analytics var, ama çerez onayına bağlı çalıştığı için gerçek sayıyı değil bir alt sınırı gösteriyor. Doğru ölçemediğim bir şeyi rakamla sunmak istemem — faturayı sunabilmemin sebebi de tam olarak bu: orada tahmin yok.
Fazla mühendislik mi?
Birkaç web sitesi için fazla mühendislik (over-engineering) gibi görünebilir. Sadece o siteleri ayakta tutmak için bakarsanız öyledir de.
Yalnız fazla mühendisliğin faturası genelde paradır, ve burada o fatura aylık bir dolar — bu sistemin “fazlalığı” kimseye pahalıya patlamıyor. Asıl bedeli tablo hiç göstermiyor: o bedel zaman.
Zamanı da bilerek harcadım, çünkü bu sistemin benim için ikinci bir işi var: öğrenmek. Teknolojiyi takip etmenin, öğrendiğimi gerçekten uygulamanın ve bir platformu içeriden tanımanın bulabildiğim en iyi yolu oldu. Pratiği olmayan teorik bilgi bir yere kadar götürür; bir sistemi yıllarca üretimde tutmak ise hiçbir kursun öğretemeyeceğini öğretiyor — neyin bozulduğunu, ne zaman bozulduğunu ve neye mal olduğunu.
Bir pişmanlığım var ve tam da bu başlıkla ilgili: yapay zekâyı öğrenmeye çok daha erken başlamalıydım. Ajan katmanını 2024'te kuramazdım — araçlar o gün bunu taşıyacak olgunlukta değildi. Ama olgunlaştıklarında ben hazır değildim; öğrenmeye onlar işe yarar hâle geldikten sonra başladım ve o gecikme araçlara değil bana ait. Öğrenmeyi merkezine koyduğunu söyleyen bir sistemde teknolojinin önünde değil arkasında kalmak, en pahalı hatam oldu.
Bir ayrım da yapmam gerekiyor: kendi laboratuvarımda kurduğum şeyle bir müşteri için kurduğum şey aynı değil. Burada dört ortamı, dört test paketini ve ajan katmanını bilerek taşıyorum, çünkü burası aynı zamanda bir laboratuvar. Müşteri sisteminde ölçüyü ihtiyaç belirler.
Neden bunu anlatıyorum
Müşteri işlerinin çoğu yazıya dökülemez. Bu proje dökülebilir: bize ait, üretimde çalışıyor ve anlattığım her şeyi şu anda bulunduğunuz sayfada deneyebilirsiniz. 2018'de verdiğim karar zaten buydu — önereceğim şeyi önce kendim çalıştırmak.
Bu yazıda yaptığım üç şey, müşteri sistemlerinde yaptığımız işin ta kendisi:
- Faturayı okumak. Çoğu ekip bulut faturasının en büyük kaleminin ne olduğunu bilmiyor. Bilmek, çoğu zaman tasarruftan önce gelir.
- Sessiz arızayı bulmak. Sayfaları açılan, hata fırlatmayan, testleri yeşil kalan ama para yakan bir sistem en pahalı sistemdir.
- Kararı yazılı hâle getirmek. “Neden Cloud DNS?” sorusunun bir cevabı olmalı; cevabı olmayan her karar birkaç yıl sonra kimsenin dokunmaya cesaret edemediği bir kaleme dönüşüyor.
Sizin sisteminizde bu üçünden biri eksikse konuşalım. Başlamanın en kolay yolu da bu yazının kendisi: faturanıza birlikte bakalım. En büyük kaleminizin ne olduğunu, neden orada durduğunu ve gerçekten orada durması gerekip gerekmediğini çıkaralım — yukarıda kendi faturama yaptığımın aynısı.
Ne yaptığımızın tamamı hizmetlerimiz sayfasında, GCP tarafı GCP danışmanlığı yazısında; doğrudan yazmak isterseniz iletişim sayfası burada.