Bloga Dön

Cloudflare Workers KV Instant: 1,62 ms Oyun Konfigürasyon Okumaları için Runbook

Yayınlanma tarihi 2 Ekim 2026
Cloudflare Workers KV Instant: 1,62 ms Oyun Konfigürasyon Okumaları için Runbook Yapay zekâ yardımıyla oluşturuldu

Özet olarak

Öğrenin: KV Instant ile oyun konfigürasyon okumalarını 1,62 ms p99'a indirin; eski veri hatalarını tespit edin, adımları ve sınırları keşfedin.

Canlı operasyon ekibiniz kritik bir konfigürasyon güncellemesi yayınladığında — bozuk bir ekonomi açığını düzeltme, acil etkinlik programı değişikliği, bakım penceresi bayrağı — gezegenin diğer ucundaki oyuncular 4,38 saniye boyunca eski veriyi okumamalı. Bu, klasik Cloudflare Workers KV için p99 yazma çoğaltma süresidir. Statik bir pazarlama sayfası için kimin umurunda? Para veya rekabet bütünlüğünün söz konusu olduğu canlı bir oyunda bu yayılma boşluğu bir risktir.

Cloudflare kısa süre önce Workers KV Instant'ı duyurdu: Workers KV için, kendi dahili Quicksilver v2 deposuyla çalışan yeni bir mod. Aynı tanıdık get(), put(), list(), delete() API'si. Altta tamamen farklı bir motor — Cloudflare'in küresel ağındaki her istek için konfigürasyon aramalarını yöneten motorun aynısı. Sonuç: 300+ uç konumda 1,62 ms p99 okuma ve 256 ms p99 yazma çoğaltma.

Bu runbook; gerçekte neyin değiştiğini, oyununuzun eski-konfigürasyon hata modlarına çarpıp çarpmadığını nasıl tespit edeceğinizi, uçta barındırılan oyun konfigürasyonu için adım adım uygulamayı, KV Instant'ı bazı iş yükleri için yanlış kılan katı sınırları ve bunu kendiniz inşa etmek yerine yönetilen bir uzak konfigürasyon hizmetinin ne zaman daha mantıklı olduğunu kapsar.


Gerçekte Ne Değişti: KV Instant vs KV Classic

Workers KV Classic nihai tutarlıdır (eventually consistent). Bir anahtar yazarsınız ve Cloudflare bunu uç konumlarına asenkron olarak çoğaltır. Bu pencerede okuyucular eski değerler alabilir. Tutarlılık modeli "TTL tabanlı önbellek geçersiz kılma ile son yazan kazanır" şeklindedir. Bu, statik varlıklar ve kullanıcı tercihleri için çalışır — seyrek yazılan ve saniyelerce eskilik toleransı olan veriler.

KV Instant, Cloudflare'in kendi konfigürasyon dağıtımı için geliştirdiği dahili depo olan Quicksilver v2'yi kullanır. Her Cloudflare isteği zaten Quicksilver'a dokunur — yönlendirme kuralları, güvenlik duvarı konfigürasyonları, hız sınırlama eşikleri için. Çoğu oyun backend'inin asla yaklaşamayacağı bir ölçekte savaşta test edilmiştir.

İşte somut performans karşılaştırması:

Metrik KV Instant KV Classic
p99 okumalar (tümü) 1,62 ms 287 ms
p99 yazma çoğaltma 256 ms 4,380 ms
Medyan yazma çoğaltma 107 ms < 1 s (saniye altı doğruluk yok)

Bu, 177 kat okuma gecikmesi iyileştirmesi ve 17 kat yazma çoğaltma iyileştirmesidir. Bu rakamlar Cloudflare'in 300+ uç konumun tamamında yaptığı kendi kıyaslama testlerinden geliyor.

Bir oyun backend'i için sonuç doğrudandır: her oyuncu isteğinde konfigürasyonu okuyabilirsiniz — girişte, maç başlangıcında, envanter çekmede, mağaza açılışında — ve okuma maliyeti p99'da bile 2 ms'nin altındadır. Beklenecek TTL yok. Oyuncu A'nın açık düzeltmesini görüp Oyuncu B'nin görmediği önbellek tutarlılık penceresi yok.


Runbook: Oyununuzda Eski Konfigürasyon Hatalarını Tespit Etme

Herhangi bir şeyi taşımadan önce bu soruna sahip olup olmadığınızı bilmeniz gerekir. İşte hata modları, bunları nasıl tespit edeceğiniz ve size maliyeti.

Hata Modu 1: TTL'si Dolmuş Eski Okumalar

Ne bozulur: Konfigürasyon deponuz TTL tabanlı önbellekleme kullanır. Bir özellik bayrağı güncellenir, ancak Tokyo'daki oyuncular uç önbellek süresi dolana kadar 30–60 saniye boyunca eski değeri okumaya devam eder.

Nasıl tespit edilir:

  • Konfigürasyonun son güncellendiği yazma zaman damgasıyla birlikte her istemciye döndürülen konfigürasyon sürüm hash'ini loglayın.
  • Yazmadan 2 saniye sonra daha eski bir konfigürasyon sürümü alan istemcileri sorgulayın.
  • Bir dashboard oluşturun: count of (stale_reads) / count (total_reads). Konfigürasyon gönderimi sırasında %0'ın üzerindeki her şey eski okuma penceresidir.

Hızlı bir tanılama sorgu deseni (loglama yığınınıza uyarlayın):

SELECT
  received_config_version,
  expected_config_version,
  COUNT(*) AS stale_count,
  MAX(received_at - config_updated_at) AS max_staleness
FROM config_read_log
WHERE config_updated_at > NOW() - INTERVAL '1 hour'
  AND received_config_version != expected_config_version
GROUP BY received_config_version, expected_config_version
ORDER BY max_staleness DESC;

Size maliyeti: Eski okuma penceresindeki oyuncular farklı oyun durumları yaşar. Rekabetçi bir oyunda bir oyuncu açığın kapatıldığını görürken diğeri görmez. Etkinlik odaklı bir oyunda bazı oyuncular sınırlı süreli pencereleri tamamen kaçırır. Bu bir güven sorunudur.

Hata Modu 2: Sıcak Yoldaki Konfigürasyon Okumaları Gecikme Artışlarına Neden Oluyor

Ne bozulur: Konfigürasyon deponuzun okuma gecikmesi (100–300 ms) her istekte okumayı kaldıramayacağınız kadar yüksektir. Bunun yerine onu istemci tarafında veya hızlı ama eski bir yerel önbellekte önbelleklersiniz. Önbellek zamanın %99'unda doğrudur, ancak yanlış olduğunda çok yanlıştır.

Nasıl tespit edilir:

  • Konfigürasyon okuma çağrınızın p50, p95 ve p99 gecikmesini ölçün. p99 50 ms'nin üzerindeyse istek başına kontroller için çok yavaştır.
  • Önbellek isabet oranlarını takip edin. Depoya erişmekten kaçınmak için konfigürasyonu istemci tarafında önbellekliyorsanız, eskilik takasını zaten kabul etmişsinizdir.
  • Bir gönderimden sonra kötü bir konfigürasyon değerinin devam ettiği olayları izleyin — bunu istemci başına önbellek TTL'sine kadar izleyin.

Size maliyeti: Eskilik sorunu getiren bir gecikme sorununun etrafında mühendislik yapıyorsunuz. Bir fiyatına iki sorun.

Hata Modu 3: Olay Baskısı Altında Yazma Amplifikasyonu

Ne bozulur: Acil bir konfigürasyon güncellemesi göndermeniz gerekir — bir özelliği devre dışı bırakma, bakım modunu etkinleştirme, bozuk bir ekonomiyi işaretleme — ve yazmalar yavaştır veya hız sınırlıdır. Klasik Workers KV anahtar başına saniyede bir yazmaya izin verir ve çoğaltma saniyeler sürer.

Nasıl tespit edilir:

  • Olay müdahalesi sırasında yazmadan görünür olana kadar geçen gecikmeyi izleyin. Operasyon ekibiniz "konfigürasyon birkaç saniyede yayılmalı" diye hesap yapıyorsa ve 10+ saniye sürüyorsa, konfigürasyon deponuz bir olay darboğazıdır.
  • Yüksek aciliyetli gönderimler sırasında yazma hatalarını ve 429 hız sınırı yanıtlarını izleyin.

Bu üç hata modunun üçüyle de karşılaşıyorsanız, KV Instant değerlendirmeye değer.


KV Instant'ı Oyun Konfigürasyonu için Uygulamak: Adım Adım

KV Instant şu anda private beta aşamasındadır. Cloudflare'in beta formuna kaydolabilirsiniz. API klasik Workers KV ile aynı olduğu için uygulama basittir — yalnızca namespace oluşturma farklıdır.

Adım 1: KV Instant Namespace Oluşturun

Namespace'inizi oluştururken mode: "instant" özniteliğini iletin:

wrangler kv namespace create "GAME_CONFIG" --mode instant

Bu bir namespace bağlaması oluşturur. wrangler.toml dosyanızı güncelleyin:

[[kv_namespaces]]
binding = "GAME_CONFIG"
id = "&lt;your-namespace-id>"

Adım 2: Oyun Konfigürasyonunuzu Yazın

KV Instant namespace'leri toplam namespace boyutu 1 MB olacak şekilde 10.000 anahtar-değer çiftiyle sınırlıdır. Her anahtar 300 bayta kadar olabilir. Bu küçüktür — kasıtlı olarak. Oyuncu verileri için değil, konfigürasyon bayrakları ve ayarları için tasarlanmıştır.

Anahtarlarınızı oyununuzun konfigürasyon katmanı için yapılandırın:

// In a Cloudflare Worker that manages config
async function updateGameConfig(env) {
  const config = {
    maintenanceMode: false,
    maintenanceMessage: "Servers are updating. Back in 5 min.",
    eventSchedule: {
      currentEvent: "summer_showdown_2025",
      startTime: "2025-07-15T18:00:00Z",
      endTime: "2025-07-22T18:00:00Z",
    },
    economyTuning: {
      xpMultiplier: 1.5,
      goldDropRate: 0.85,
      shopRefreshHours: 6,
    },
    featureFlags: {
      newMatchmaking: true,
      rankedModeV2: false,
      socialLobby: true,
    },
    buildVersion: {
      minimumClient: "1.4.2",
      forceUpdate: false,
    },
  };

  await env.GAME_CONFIG.put("active_config", JSON.stringify(config));
  // Propagates to 300+ edge locations in ~256ms at p99
}

Yazma sıklığı sınırı: Namespace başına saniyede bir yazma. Bu bir tasarım kısıtıdır, hata değildir — güncelleme sıralamasını deterministik yapar. Saatte birkaç kez (veya olay başına) değişen konfigürasyon için bu bir darboğaz değildir.

Adım 3: Konfigürasyonu Uçtan Sunun

Her istekte konfigürasyonu okuyan ve oyun istemcinize sunan bir Cloudflare Worker oluşturun:

export default {
  async fetch(request, env, ctx) {
    // Every player request reads fresh config — 1.62ms p99
    const raw = await env.GAME_CONFIG.get("active_config");
    if (!raw) {
      return new Response(JSON.stringify({ error: "config_missing" }), {
        status: 503,
        headers: { "Content-Type": "application/json" },
      });
    }

    const config = JSON.parse(raw);

    // Conditional logic at the edge — maintenance mode check
    if (config.maintenanceMode) {
      return new Response(
        JSON.stringify({
          status: "maintenance",
          message: config.maintenanceMessage,
        }),
        {
          status: 503,
          headers: { "Content-Type": "application/json" },
        }
      );
    }

    // Return relevant config slice for the client
    const clientConfig = {
      event: config.eventSchedule,
      economy: config.economyTuning,
      features: config.featureFlags,
      build: config.buildVersion,
    };

    return new Response(JSON.stringify(clientConfig), {
      headers: {
        "Content-Type": "application/json",
        "Cache-Control": "public, max-age=5", // Short cache for freshness
      },
    });
  },
};

Adım 4: Konfigürasyonu Oyun İstemcinizde Tüketin

İstemci tarafında, konfigürasyonu başlatma veya oturum başlangıcında çekin. İşte bir Godot oyunu için GDScript örneği:

extends Node

var config_url: String = "https://config.yourgame.com/api/config"
var current_config: Dictionary = {}

func _ready():
    fetch_config()

func fetch_config():
    var http = HTTPRequest.new()
    add_child(http)
    http.request_completed.connect(_on_config_received)
    http.request(config_url)

func _on_config_received(result: int, response_code: int, headers: PackedStringArray, body: PackedByteArray):
    if response_code != 200:
        push_warning("Config fetch failed: %d" % response_code)
        return

    var json = JSON.new()
    var parse_result = json.parse(body.get_string_from_utf8())
    if parse_result != OK:
        push_warning("Config parse error")
        return

    current_config = json.data
    _apply_config(current_config)

func _apply_config(config: Dictionary):
    # Apply feature flags
    if config.has("features"):
        if config["features"].get("rankedModeV2", false):
            enable_ranked_mode()
        if config["features"].get("newMatchmaking", false):
            enable_new_matchmaking()

    # Check build version
    if config.has("build"):
        var min_version = config["build"].get("minimumClient", "0.0.0")
        if version_compare(get_app_version(), min_version) &lt; 0 and config["build"].get("forceUpdate", false):
            show_force_update_screen()

    # Apply economy tuning
    if config.has("economy"):
        EconomyManager.set_xp_multiplier(config["economy"].get("xpMultiplier", 1.0))
        EconomyManager.set_gold_drop_rate(config["economy"].get("goldDropRate", 1.0))

    print("Config applied successfully — all players now on same state")

Okumalar 2 ms'nin altında olduğundan ve TTL eskilik olmadığından, fetch_config() işlevini her oturum başlangıcında, her maç kuyruğu girişinde veya her önemli istemci eyleminde gecikme yükü veya önbellek tutarlılığı konusunda endişelenmeden çağırabilirsiniz.


KV Instant'ın Yapamadıkları (Katı Sınırlar)

KV Instant kendi nişi için güçlüdür, ancak kısıtlar gerçektir. Bir uygulamaya başlamadan önce bunları değerlendirin:

1 MB toplam namespace boyutu. Oyuncu verilerini, lider tablosu anlık görüntülerini, envanteri veya oyuncu sayınızla büyüyen herhangi bir şeyi depolayamazsınız. Bu yalnızca küresel olarak uygulanan konfigürasyon ve bayraklar içindir.

Maksimum 10.000 anahtar-değer çifti. Yüzlerce özellik bayrağı ve konfigürasyon nesnesi için yeterlidir. Oyuncu başına hiçbir şey için yeterli değildir.

Namespace başına saniyede bir yazma. Saniyenin altında yazma sıklığına ihtiyacınız varsa bu sizin deponuz değil. Saatlik veya olaylar sırasında güncellenen oyun konfigürasyonu için bu iyidir. Gerçek zamanlı oyun durumu senkronizasyonu için başka bir yere bakın.

Meta veri desteği yok. getWithMetadata null döndürür. Anahtarlara özel meta veri ekleyemezsiniz. Sürümleme veya etiketleme için meta veriye bağımlıysanız, bunu değerin içine gömmek zorunda kalırsınız.

list üzerinde sayfalama yok. Her list çağrısı namespace'teki tüm eşleşen anahtarları döndürür. 10.000 anahtar için bu büyük bir yanıttır. List çağrılarınızı kapsamlandırmak için anahtar adlandırma ve önek ekleme konusunda bilinçli olun.

Maliyet asimetrisi. Depolama aylık $100/MB'dir (Classic için aylık $0.50/GB'a karşı). Class A yazma işlemleri her biri $0.10'dur (Classic için milyon başına $5.00'a karşı). Bu rakamlar yüksek yazma iş yükleri için caydırıcıdır. Ancak okumalar milyon başına $0.20'dir — Classic'ten %60 daha ucuzdur. Fiyatlandırma modeli "nadiren yaz, sürekli oku" yönüne ciddi şekilde eğiktir; bu da tam olarak oyun konfigürasyonu desenidir.


KV Instant'ta Oyun Konfigürasyonu için En İyi Uygulamalar

  1. Anahtarlarınızı bilinçli olarak namespace'leyin. Özellik bayrakları için ff_, ekonomi ayarları için econ_, etkinlik programları için evt_ gibi önekler kullanın. Bu, list çağrılarını taranabilir yapar ve tüm namespace'i okumadan belirli kategorileri yöneten konfigürasyon yönetim arayüzleri oluşturmanıza olanak tanır.

  2. Değerlerinize sürüm hash'leri gömün. Meta veri desteklenmediğinden, her konfigürasyon değerinin içine bir configVersion alanı ekleyin. İstemciniz bu sürümü loglarda ve analitiklerde bildirebilir, böylece gerçek zamanlı bir yayılma doğrulama panosu elde edersiniz.

  3. Konfigürasyonu durumdan ayırın. KV Instant konfigürasyonu depolar — kurallar, bayraklar, ayar düğmeleri, programlar. Durumu depolamaz — oyuncu envanterleri, maç sonuçları, lider tablosu sıralamaları. Bunları ayrı depolama backend'lerine sahip iki ayrı sistem olarak tasarlayın. "config" namespace'iniz haftada birkaç KB'den fazla büyüyorsa, bu verileri başka bir yere koyun.

  4. 503 durumunu ele alın. GAME_CONFIG.get() null döndürürse, worker'ınız zarif bir şekilde hata vermeli. Bakım modu veya bir acil kapatma anahtarı döndürün. Eksik bir konfigürasyon anahtarı oyun istemcinizi asla çökertmemelidir. Geri dönüşü istemciye değil, uç worker'a inşa edin.

  5. Baskı altında yazma sıralamasını test edin. Namespace başına saniyede bir yazma, eşzamanlı yazmaların sıralanacağı anlamına gelir. İki mühendis aynı saniye içinde konfigürasyon değişikliği gönderirse, sonuncusu kazanır. Eşzamanlı yazmalara güvenmek yerine açık sıralamalı bir konfigürasyon değişikliği kuyruğu oluşturun.


Bunun Yerine Ne Zaman Yönetilen Bir Konfigürasyon Hizmeti Kullanmalı?

Ekibinizin uç worker'ı, konfigürasyon yönetim arayüzünü, sürümleme şemasını, istemci tarafı çekme mantığını ve etrafındaki olay müdahale prosedürlerini sahiplenme bant genişliği varsa, KV Instant üzerinde bir konfigürasyon dağıtım hattı oluşturmak sağlam bir mühendislik kararıdır. Bu gerçek bir altyapı işidir — tek tek zor değildir, ancak çıkış zaman çizelgeniz boyunca birikir.

Altyapıyı işletmeden konfigürasyon dağıtımı isteyen ekipler için horizOn, yönetilen bir hizmet olarak Remote Configuration sunar. Özellik bayraklarınızı, oyun ayarlarınızı ve ayar parametrelerinizi dashboard veya API üzerinden tanımlarsınız; platform dağıtımı oyun istemcilerinize yönetir. Yazılacak veya bakımı yapılacak uç worker yok, üzerinde düşünülecek KV namespace boyut kısıtı yok — ancak altta yatan çoğaltma motoru ve gecikme profili üzerinde daha az kontrol var.

Bu takas, klasik build-vs-buy eksenidir. KV Instant size uçta tam kontrolle ham performans verir. Yönetilen bir hizmet size daha hızlı entegrasyon süresi ve daha az operasyonel yüzey alanı verir. Konfigürasyon dağıtımının stüdyonuzun çekirdek yetkinliği mi yoksa altyapı yükü mü olduğuna göre seçim yapın.

Dağıtık oyun istemcileri arasında konfigürasyon eskiliğini tespit etmeniz gerekiyorsa, yukarıdaki runbook bölümündeki loglama ve sorgu desenleri hangi konfigürasyon backend'ini seçerseniz seçin çalışır. Tanılama katmanı taşıma katmanından bağımsızdır.


Özet: Oyununuzla Aynı Hızda Giden Konfigürasyon Okumaları

KV Instant, "küçük, kritik, küresel olarak okunan konfigürasyon verisi" deseni için anlamlı bir yükseltmedir. Oyun backend'leri için bu desen doğrudan özellik bayraklarına, ekonomi ayarlarına, etkinlik programlarına, bakım anahtarlarına ve build sürüm kapılarına karşılık gelir.

Rakamlar pazarlama yuvarlaması değil: 300+ uç konumda 1,62 ms p99 okuma ve 256 ms p99 yazma çoğaltma. API klasik Workers KV ile aynıdır. Kısıtlar (1 MB, 10.000 anahtar, saniyede 1 yazma) iyi tanımlanmıştır ve kullanım durumu için uygundur.

Oyununuz şu anda konfigürasyonu merkezi bir depodan okuyor ve gecikmeyi önlemek için istemci tarafında önbellekliyorsa, bu eskilik penceresinin hâlâ kabul edilebilir olup olmadığını değerlendirin. Gerçek zamanlı ekonomi ayarlarına sahip rekabetçi oyunlar ve canlı hizmet oyunları için cevap giderek artan şekilde hayır.

KV Instant private beta'sına kaydolun, en gecikme duyarlı konfigürasyonunuzla bir test namespace'i kurun ve kazandığınız yayılma payını ölçün. Rakamlar Cloudflare'in bildirdikleriyle eşleşiyorsa, eski-konfigürasyon olayları sınıfını tamamen ortadan kaldırmak için net bir yolunuz var.

Konfigürasyon mimariniz veya backend topolojiniz için ikinci bir çift göze mi ihtiyacınız var? horizOn dokümanlarına göz atın — platform konfigürasyon dağıtımını, çökme raporlamayı ve oyuncu oturum yönetimini yönetir, böylece altyapı runbook'ları yerine oyun geliştirmeye odaklanabilirsiniz.


Kaynak: Workers KV Instant Tanıtımı — Quicksilver Destekli