Hacker DirectoryHacker Directory
Öğrenmeye devam et
ENHTML kaydet ↓

WEB / WEB-13.02

Session store ve distributed sessions

Browser aynı session handle’ını taşırken request farklı application node’larına gidebilir. Shared store, güncel binding’i ortaklaştırır; consistency, expiry ve failure kararları yine tasarlanır.

CORE · RED · BLUE · ARTIFACT · PRACTICE

1. Core · Mekanizma

Hareket olmadan bütün senaryoları oku

Güncel binding

  1. Browser request B’ye zaten ulaştı

    Sahne store lookup’tan hemen önce başlar. Handle doğrulama girdisi alınmıştır; credential gösterilmez.

    Browser / Duru
    Request sonucu bekleniyor
    Application Node A
    Idle; bu request’te kullanılmıyor
    Application Node B
    Received request; session unresolved
    Shared session store
    ledger-duru: active v7
  2. Lookup store’a ulaştı

    Node B’nin driver/protocol lookup’ı remote store’a varır. Record hâlâ active v7.

    Browser / Duru
    Request sonucu bekleniyor
    Application Node A
    Idle; bu request’te kullanılmıyor
    Application Node B
    Lookup pending; session unresolved
    Shared session store
    Lookup received; active v7
  3. Binding yanıtı B’ye ulaştı

    Store active v7 binding’ini ve policy alanlarını döndürdü. B bu veriyi değerlendirmeli.

    Browser / Duru
    Request sonucu bekleniyor
    Application Node A
    Idle; bu request’te kullanılmıyor
    Application Node B
    Resolved: active v7; lifetime check pending
    Shared session store
    ledger-duru: active v7
  4. Session ve resource kararları geçer

    Bu branch’te lifetime valid ve ayrı resource authorization supplied allowed’dur. HTTP response hazırlamak artık uygundur.

    Browser / Duru
    Request sonucu bekleniyor
    Application Node A
    Idle; bu request’te kullanılmıyor
    Application Node B
    Session accepted; resource allowed
    Shared session store
    ledger-duru: active v7
  5. Application response Browser’a ulaştı

    Browser request sonucunu öğrenir. Store wire ile HTTP response farklı bağlantılardır.

    Browser / Duru
    Protected request accepted
    Application Node A
    Idle; bu request’te kullanılmıyor
    Application Node B
    Response: 200
    Shared session store
    ledger-duru: active v7

Revoked · eski touch

  1. A’nın eski snapshot’ı

    A daha önce active v7 gördü; B’nin logout’u bu case başlamadan authoritative record’u revoked v8 yaptı.

    Browser / Duru
    A request’i bekleniyor
    Application Node A
    Old snapshot: active v7
    Application Node B
    Earlier logout committed v8
    Shared session store
    Authoritative: revoked v8
  2. Conditional touch store’a ulaştı

    A expected version 7 ile touch ister. Remote receiver’ın current record’u v8 kalır.

    Browser / Duru
    A request’i bekleniyor
    Application Node A
    Touch pending; expected v7
    Application Node B
    Earlier logout committed v8
    Shared session store
    Touch received: expected7/current8; revoked
  3. Atomic koşul mutation’ı reddeder

    Version eşleşmez ve record revoked’dur. Store eski active snapshot’ı yazmaz; v8 değişmez.

    Browser / Duru
    A request’i bekleniyor
    Application Node A
    Touch pending; expected v7
    Application Node B
    Earlier logout committed v8
    Shared session store
    Rejected; revoked v8 unchanged
  4. Rejection A’ya ulaştı

    Authoritative yanıt current revoked v8’i bildirir; A eski snapshot’a dayanamaz.

    Browser / Duru
    A request’i bekleniyor
    Application Node A
    Current resolved: revoked v8; reject session
    Application Node B
    Earlier logout committed v8
    Shared session store
    Rejected; revoked v8 unchanged
  5. Session reddi Browser’a ulaştı

    Fixture HTTP 401 döner; authenticated binding yeniden oluşturulmaz.

    Browser / Duru
    Session invalid; authenticated processing rejected
    Application Node A
    Response: 401
    Application Node B
    Earlier logout committed v8
    Shared session store
    Rejected; revoked v8 unchanged

Lookup error

  1. Lookup gerekli

    Browser request B’dedir. B’nin current binding’i yok; store service bu branch’te erişilemez.

    Browser / Duru
    Request sonucu bekleniyor
    Application Node A
    Idle
    Application Node B
    Session unresolved; lookup required
    Shared session store
    Unreachable; authoritative state not observed
  2. Lookup failure alındı

    Driver error bildirir; completed remote arrival/response yoktur. Wire hareketi uydurulmaz.

    Browser / Duru
    Request sonucu bekleniyor
    Application Node A
    Idle
    Application Node B
    Lookup error; current state unknown
    Shared session store
    Unreachable; authoritative state not observed
  3. Authenticated processing kabul edilmez

    Yeterli trusted state çözülemedi. Error, missing record veya expired session diye yeniden etiketlenmez.

    Browser / Duru
    Request sonucu bekleniyor
    Application Node A
    Idle
    Application Node B
    Fail closed; service failure response prepared
    Shared session store
    Unreachable; authoritative state not observed
  4. Hizmet hatası Browser’a ulaştı

    Fixture HTTP 503 seçer. Browser login state’inin kesin expired olduğunu bu yanıttan çıkaramaz.

    Browser / Duru
    Service unavailable; retry later
    Application Node A
    Idle
    Application Node B
    Response: 503
    Shared session store
    Unreachable; authoritative state not observed

ROLLER · STATE · VERİ AKIŞI

Handle aynı, application node farklı

WEB-13.01’de Browser’ın opaque handle’ı server-side binding’e bağlandı. Şimdi Duru’nun bir request’i Node A’ya, sonraki request’i Node B’ye ulaşsın. İki node’ın aynı handle metnini görmesi, aynı authenticated record’u gördüklerini kendiliğinden kanıtlamaz.

Bu ders opaque server-store session tasarımını ele alır. Record, verified subject, tenant context, lifetime ve revocation state gibi server tarafından yönetilen bilgileri içerir. Browser handle’ı referans taşır; bu record’un authoritative alanlarını client’tan yeniden kurmaz.

Fixture’daki ledger-duru bir audit correlation alias’ıdır; credential değildir. Wire credential ve verifier değeri gösterilmez. Duru/Atlas subject binding’inin önceki güvenli login akışında kurulmuş olduğu bu modelin supplied başlangıç koşuludur.

Process memory neyi sağlar, neyi kaybeder?

Tek application process’i session object’lerini kendi memory’sinde tutabilir. Bu tasarım basittir, fakat başka bir process aynı alanı otomatik paylaşmaz. Process restart olduğunda yalnız volatile memory’de duran record kalıcı disk kaydı gibi geri gelmez.

Bir load balancer’ın sticky session kullanıp Duru’yu Node A’ya yönlendirmesi, node-local tasarımın request’lerini aynı yere götürebilir. Bu routing tercihi ortak session authority yaratmaz. A kaybolursa B’nin elinde record bulunmaması beklenebilir; routing ile state durability aynı sorun değildir.

Tasarımı değerlendirirken “Server session’ı nerede tutuyor?” sorusunu somutlaştır: hangi process veya service owner, hangi lifecycle, hangi loss boundary? “Server-side” demek tek başına restart, scaling veya failover davranışını açıklamaz.

Shared session store: ortak record, ayrı request kararı

Node A ve B ortak bir store üzerinden aynı binding’i çözebilir. Store ayrı bir service olduğunda application↔store mesajı driver/protocol üzerinden gider; Browser↔Application HTTP exchange’iyle aynı bağlantı değildir. Sahne Node B’nin Browser request’ini zaten aldığı noktadan başlar ve remote lookup’ı gösterir.

Başarılı lookup, record’un kullanıma uygun olduğunu tek başına söylemez. Application record’un active/revoked state’ini ve server-side lifetime politikasını kontrol eder; sonra hedef resource için authorization uygular. Session recognition ile resource permission ayrı kararlardır.

Birçok store teknolojisi bu görevi üstlenebilir. “Redis kullandık” veya “database kullandık” demek access isolation, consistency, persistence ve failure policy’nin çözüldüğü anlamına gelmez. Bu ders Redis belgelerini belirli trade-off’ları göstermek için kullanır; her store’a aynı default’u atfetmez.

Stale state: eski active kopya, güncel revoke kararını ezmesin

Fixture’ın başka branch’inde Node A daha önce version 7 active snapshot’ı almıştır. Node B’nin logout akışı shared record’u version 8 revoked durumuna getirmiştir. A’nın eski snapshot’ı bir historical observation’dır; güncel authority değildir.

A eski snapshot üzerinden lastSeen güncellemesi yapıp bütün record’u koşulsuz overwrite ederse revocation’ı kaybedebilir. Savunma için update’i yalnız expected version hâlâ eşleştiğinde, record active olduğunda ve lifetime geçerliyken atomically kabul et. Field update’i de aynı policy sınırını korumalıdır.

Bu fixture’daki conditional touch expected=7 ile current=8’i karşılaştırır, mutation yapmaz ve revoked record’u korur. Version conflict’te son state yeniden okunur ve policy tekrar uygulanır; eski “active” state’i yeniden yazmak için kör retry yapılmaz. Redis’in WATCH/CAS yaklaşımı conditional update için bir örnektir; bu sahne belirli Redis command dizisini çalıştırmaz.

Bir tombstone veya generation/version stratejisinin ne kadar tutulacağı lifecycle tasarımına bağlıdır. Silinmiş session kaydını eski writer’ın yeniden oluşturmasını engellemek de aynı sınırın parçasıdır; missing record üzerinden authenticated upsert yapılmaz.

Consistency ile durability’yi ayrı değerlendir

Shared endpoint kullanmak, bütün reader’ların anında en son state’i gördüğü garantisi değildir. Redis’in temel replication’ı default olarak asynchronous’tur. Replica’dan okuma stratejisi eski state gösterebilir; revocation için kabul edilen consistency boundary’si ayrıca belirlenmelidir.

Redis WAIT, belirtilen sayıda replica’nın acknowledgement bilgisini sağlar; sistemi otomatik strong-consistency sağlayan bir CP sistemine dönüştürmez. Failover sonrasında acknowledged write kaybı ihtimali persistence configuration ile ilişkilidir. Bir acknowledgement ile her türlü crash/failover dayanıklılığını eşitleme.

Persistence için RDB point-in-time snapshot, AOF ise write log ve startup replay yaklaşımı sunar; persistence kapatılabilir de. Bu seçenekler farklı loss ve recovery sınırları taşır. Login veya logout sonucu kullanıcıya başarı olarak bildirilecekse hangi store acknowledgement’ının yeterli olduğu ürünün güvenlik ve availability kararına bağlanır.

Expiry, eviction, missing ve failure aynı sonuç değildir

Session expiry application’ın server-side lifetime kararıdır. Store TTL, artık gerekmeyen record’u temizlemeye yardımcı olabilir; record henüz fiziksel olarak duruyor diye policy deadline geçmiş session kullanılmaz. Expiry enforcement’ı yalnız temizlik zamanına bağlama.

Eviction ise kapasite politikasından doğan veri kaybıdır. Redis eviction policy memory sınırında key’i kaldırabilir. noeviction bunu önlese de yeni veri ekleyen write’lar hata verebilir; sınırsız kapasite veya availability sağlamaz. Session store tek authoritative kopyaysa missing record’u ordinary cache miss gibi client’tan “yeniden üretmek” doğru değildir.

Başarılı lookup’ın “record yok” demesi ile lookup service’inin yanıt verememesi ayrı observation’dır. İlki bu handle için geçerli binding bulunmadığını söyler; ikincisi current state’in bilinmediğini söyler. Bu fixture her ikisinde de authenticated processing’i kabul etmez; service failure’ı expiry gibi etiketlemez.

Duru’nun cookie’sinin hâlâ Browser’da bulunması kaybolan server binding’i geri getirmez. Güvenli yeni authenticated session ancak bağımsız, geçerli authentication akışının sonucu kurulabilir; eski client iddiası missing record’un yerine geçmez.

2. Red · Güven ve etki

Hareket olmadan bütün senaryoları oku

Eski touch

  1. Node’ın girdisi hazır

    Node A’nın historical active snapshot’ı version 7’dir. Güncel store version 8 revoked durumundadır; node bu sonucu henüz yeni lookup ile öğrenmemiştir.

    Application node
    Expected version 7 touch hazır
    Remote session store
    Current version 8 revoked
    Acceptance gate
    Session kararı bekliyor
  2. Operation remote store’a ulaştı

    Node A operation’ı shared authoritative store’a ulaştı. Bu application–store mesajıdır; browser HTTP request’i değildir ve driver protocol ayrıntısı seçilmemiştir.

    Application node
    Store sonucu bekleniyor
    Remote session store
    Expected 7 touch alındı
    Acceptance gate
    Session kararı bekliyor
  3. Authoritative koşul değerlendirildi

    Conditional update expected version 7’yi current version 8 ile karşılaştırır. Ayrıca active ve lifetime koşulları gerekir; revoked kayıt eski active snapshot ile overwrite edilmez.

    Application node
    Store sonucu bekleniyor
    Remote session store
    Version 8 revoked korundu
    Acceptance gate
    Session kararı bekliyor
  4. Store sonucu hazırlandı

    Store conditional-write-rejected sonucunu node’a iletmek üzere hazırlar. Bu aşamada node’ın yeni sonucu aldığını varsaymayız.

    Application node
    Store sonucu bekleniyor
    Remote session store
    Rejected; version 8 unchanged
    Acceptance gate
    Session kararı bekliyor
  5. Store sonucu node’a ulaştı

    Node A version conflict ve revoked state sonucunu aldı. Eski local state güncel authenticated authority gibi kullanılmaz.

    Application node
    Current revoked biliniyor
    Remote session store
    Version 8 unchanged
    Acceptance gate
    Session kararı bekliyor
  6. Authenticated işlem durduruldu

    sessionAccepted=false kalır. Conflict’te trusted state yeniden okunup policy uygulanır; eski snapshot’ı kör retry ile diriltmek gerekçelendirilmez.

    Application node
    Session accepted=false
    Remote session store
    Revoked version 8 unchanged
    Acceptance gate
    Resource işlemi kabul edilmedi

Missing record

  1. Node’ın girdisi hazır

    Node B normal lookup için alias context’ini hazırlar. Browser’da bir handle bulunması, authoritative store’da record bulunduğunu kanıtlamaz.

    Application node
    Lookup hazır; client handle alias
    Remote session store
    Authoritative record missing
    Acceptance gate
    Session kararı bekliyor
  2. Operation remote store’a ulaştı

    Node B operation’ı shared authoritative store’a ulaştı. Bu application–store mesajıdır; browser HTTP request’i değildir ve driver protocol ayrıntısı seçilmemiştir.

    Application node
    Store sonucu bekleniyor
    Remote session store
    Lookup alındı
    Acceptance gate
    Session kararı bekliyor
  3. Authoritative koşul değerlendirildi

    Başarılı lookup record yok sonucunu verir. OnMissing policy, client claim’den yeni authenticated binding oluşturmaz; missing burada transport failure değildir.

    Application node
    Store sonucu bekleniyor
    Remote session store
    Record missing; upsert yok
    Acceptance gate
    Session kararı bekliyor
  4. Store sonucu hazırlandı

    Store success-missing sonucunu node’a iletmek üzere hazırlar. Bu aşamada node’ın yeni sonucu aldığını varsaymayız.

    Application node
    Store sonucu bekleniyor
    Remote session store
    Missing sonucu hazır
    Acceptance gate
    Session kararı bekliyor
  5. Store sonucu node’a ulaştı

    Node B başarılı lookup’ın missing record sonucunu aldı. Eski local state güncel authenticated authority gibi kullanılmaz.

    Application node
    Missing binding biliniyor
    Remote session store
    Record missing
    Acceptance gate
    Session kararı bekliyor
  6. Authenticated işlem durduruldu

    sessionAccepted=false kalır. Yeni session ancak bağımsız geçerli authentication ile kurulabilir; kayıp record cookie metninden yeniden üretilmez.

    Application node
    Session accepted=false
    Remote session store
    Authenticated upsert yok
    Acceptance gate
    Resource işlemi kabul edilmedi

VARSAYIM · SINIR · KONTROL

Sadece happy path node’ını inceleme

Defensive review’da bir session’ın Node A’da tanınmasıyla Node B’de tanınmasını ayrı observation olarak kaydet. Lookup source, observed version ve decision birlikte gerekir. Local cache’in eski active state’i gösterdiği branch, güncel revoke kararının uygulanıp uygulanmadığını anlamaya yarar.

Logout response’u ile bütün okuyucuların revocation’ı görmesi arasındaki boundary’yi sor. Network ve replica davranışı tasarımın parçasıdır. Her stale record anında bir compromise değildir; güvenlik etkisi application’ın o kaydı hangi kararda kabul ettiğine bağlıdır.

Store erişimi de credential sınırıdır

Session store yalnız “performans cache’i” olarak etiketlenip geniş erişime açılmamalıdır. Raw random token saklayan bir store’u okuyabilen taraf, hâlâ geçerli credential elde edebilir. High entropy disclosure’ı önlemez.

OWASP, read-only store disclosure threat model’inde one-way verifier saklamayı değerlendirir. Bu koruma read-only disclosure’a yöneliktir; record modification veya application compromise’ı çözmez. Bu derste hiçbir raw token ya da verifier bulunmaz; ledger alias’ı authentication proof gibi kullanılamaz.

3. Blue · Güvenli geliştirme ve savunma

Hareket olmadan bütün senaryoları oku

Policy expiry

  1. Session decision satırı seçildi

    Bu inceleme policy-expired satırını ele alır. İki branch’te de sessionAccepted=false olmasına rağmen trusted state hakkındaki kanıtları aynı değildir.

    Decision kaydı
    case=policy-expired
    Lookup incelemesi
    Lookup incelenmedi
    Evidence hükmü
    Neden belirlenmedi
  2. Lookup kaynağı ayrıldı

    Lookup success ve source=authoritative’tir; observedVersion=7 bilinir. Physical record active görünürken application lifetime policy ayrıca değerlendirilir.

    Decision kaydı
    case=policy-expired
    Lookup incelemesi
    Success; authoritative; version 7
    Evidence hükmü
    Neden belirlenmedi
  3. Lifetime kanıtı değerlendirildi

    lifetimeValid=false policy expiry sonucunu açıklar. Record’un fiziksel olarak durması geçerli session authority’yi sürdürmez; TTL cleanup ayrı mekanizmadır.

    Decision kaydı
    case=policy-expired
    Lookup incelemesi
    Lifetime invalid; record present
    Evidence hükmü
    Expiry biliniyor
  4. Fail-closed kararı sınırlandı

    Artifact authenticated processing’i kabul etmez. Bu karar bilinen expiry’ye dayanır; iki reason tek logout/expiry etiketi altında birleştirilmez.

    Decision kaydı
    case=policy-expired
    Lookup incelemesi
    sessionAccepted=false
    Evidence hükmü
    Known expiry
  5. Selector sonucu kapsamıyla okundu

    Ana selector accepted=true olup known/active/lifetime koşulu eksik satırları arar ve 0 verir. Ayrı positive fixture 1 verir; bu kayıtlar gerçek Redis metric veya latency ölçümü değildir.

    Decision kaydı
    case=policy-expired
    Lookup incelemesi
    Integrity count=0; positive=1
    Evidence hükmü
    Reason ayrı korunuyor
  6. Recovery iddiası eklenmedi

    Bu satır session policy expiry’yi açıklar; eviction, crash veya replication nedenleri bu sonuçtan türetilmez.

    Decision kaydı
    case=policy-expired
    Lookup incelemesi
    Authenticated acceptance yok
    Evidence hükmü
    Policy expiry biliniyor

Store error

  1. Session decision satırı seçildi

    Bu inceleme store-unavailable satırını ele alır. İki branch’te de sessionAccepted=false olmasına rağmen trusted state hakkındaki kanıtları aynı değildir.

    Decision kaydı
    case=store-unavailable
    Lookup incelemesi
    Lookup incelenmedi
    Evidence hükmü
    Neden belirlenmedi
  2. Lookup kaynağı ayrıldı

    Lookup error ve source=unknown’dur; observedVersion=null kalır. Application current record state’ini öğrenememiştir.

    Decision kaydı
    case=store-unavailable
    Lookup incelemesi
    Error; unknown source/version
    Evidence hükmü
    Neden belirlenmedi
  3. Lifetime kanıtı değerlendirildi

    Store yanıt veremediği için lifetime veya revoked state sonucu çıkarılmaz. Service unavailable product sonucu expiry’nin gözlendiği anlamına gelmez.

    Decision kaydı
    case=store-unavailable
    Lookup incelemesi
    Current lifecycle bilinmiyor
    Evidence hükmü
    UNKNOWN: lifecycle
  4. Fail-closed kararı sınırlandı

    Artifact authenticated processing’i kabul etmez. Bu karar trusted state çözülememesine dayanır; iki reason tek logout/expiry etiketi altında birleştirilmez.

    Decision kaydı
    case=store-unavailable
    Lookup incelemesi
    sessionAccepted=false
    Evidence hükmü
    UNKNOWN: record state
  5. Selector sonucu kapsamıyla okundu

    Ana selector accepted=true olup known/active/lifetime koşulu eksik satırları arar ve 0 verir. Ayrı positive fixture 1 verir; bu kayıtlar gerçek Redis metric veya latency ölçümü değildir.

    Decision kaydı
    case=store-unavailable
    Lookup incelemesi
    Integrity count=0; positive=1
    Evidence hükmü
    Reason ayrı korunuyor
  6. Recovery iddiası eklenmedi

    Bu satır service error’ı açıklar; session record’un silindiğini veya expired olduğunu kanıtlamaz. Recovery için trusted store state’i tekrar çözülmelidir.

    Decision kaydı
    case=store-unavailable
    Lookup incelemesi
    Authenticated acceptance yok
    Evidence hükmü
    UNKNOWN: current store state

UYGULAMA · GÜVENLİK KONTROLÜ · DOĞRULAMA

Authoritative state ve read policy’yi belirle

Her node için aynı binding kaynağını, revocation visibility beklentisini ve approved read path’i tanımla. Replica veya local cache kullanılıyorsa stale state’in hangi kararlar için kabul edilebildiğini açıkça sınırla; yalnız kısa cache TTL söylemek güçlü consistency garantisi değildir.

Store erişimini gerekli application bileşenleriyle sınırla, transport ve at-rest/backup korumalarını uygula. Credential’ların gözlem sistemlerine sızmaması için opaque audit correlation kullan. Persistence ve failover policy’sini session lifecycle beklentisiyle birlikte değerlendir.

Lifetime update’ini atomic policy yap

Touch/refresh için expected version, active state ve lifetime koşulunu aynı atomik boundary’de değerlendir. Conflict’te yeniden oku; revoked/missing/expired state’i valid authentication olmadan active’a çevirmeyi reddet. Generic upsert bu policy’nin yerini tutmaz.

Conditional primitive’lerin hata semantiğini backend belgesinden doğrula. IndexedDB transaction abort’unun bütün değişiklikleri geri alması, Redis transaction’ın execution-time hatalarda rollback yaptığı anlamına gelmez; Redis bu tür rollback sağlamaz. “Transaction” adını bütün teknolojiler için aynı garanti sanma.

Failure’ı güvenli ve anlaşılır göster

Record missing, policy expired, capacity eviction ve service unavailable observation’larını ayır. Authenticated processing için yeterli trusted state çözülemiyorsa bu fixture fail closed davranır; kullanıcıya hizmet hatasını logout kanıtı diye sunmaz. Retry ve recovery authenticated authority uyduramaz.

Capacity takibinde eviction, expiry ve write rejection göstergelerini farklı izle. Bu dersin defteri ölçülmüş latency, throughput veya gerçek Redis metric sonucu vermez; yalnız kendi deterministic branch’lerinin karar gerekçesini gösterir.

ŞİMDİ VAKAYA UYGULA

Eski snapshot ve store failure hangi kararı değiştiremez?

Node’lar ortak authoritative binding’i kullanır. Conditional touch güncel revoke kararını korur; bilinmeyen lookup state’i expiry diye sunulmaz.

Vakadaki handle, server binding ve session lifetime için ayrı observation ara. Browser’da kalan değer server’ın güncel kabul kararını tek başına anlatır mı?

Bağlı vaka dosyasını aç ↗

ÖRNEĞİ BİRLİKTE OKUYALIM

İki node ve authoritative session defteri

Bir alan seç; hangi sonucu desteklediğini ve nerede yetersiz kaldığını incele.

Ham kaydı ve alan açıklamalarını oku
{
  "architecture": "opaque handle + remote authoritative session store; driver protocol unspecified",
  "auditCorrelation": "ledger-duru; not a credential",
  "subject": {
    "displayName": "Duru",
    "tenant": "Atlas",
    "binding": "supplied previously verified authentication; wire token omitted"
  },
  "cases": [
    {
      "case": "normal",
      "node": "B",
      "lookup": "success",
      "source": "authoritative",
      "observedVersion": 7,
      "recordState": "active",
      "lifetimeValid": true,
      "sessionAccepted": true,
      "resourceAuthorization": "separate required decision"
    },
    {
      "case": "stale-touch",
      "node": "A",
      "lookup": "conditional-write-rejected",
      "source": "authoritative",
      "expectedVersion": 7,
      "observedVersion": 8,
      "recordState": "revoked",
      "recordAfter": "revoked version 8 unchanged",
      "sessionAccepted": false
    },
    {
      "case": "missing-after-eviction",
      "node": "B",
      "lookup": "success-missing",
      "source": "authoritative",
      "observedVersion": null,
      "recordState": "missing",
      "capacityObservation": "authored eviction branch; not a measured Redis event",
      "sessionAccepted": false
    },
    {
      "case": "policy-expired",
      "node": "B",
      "lookup": "success",
      "source": "authoritative",
      "observedVersion": 7,
      "recordState": "active physical record",
      "lifetimeValid": false,
      "sessionAccepted": false
    },
    {
      "case": "store-unavailable",
      "node": "B",
      "lookup": "error",
      "source": "unknown",
      "observedVersion": null,
      "recordState": "unknown to application",
      "sessionAccepted": false,
      "productOutcome": "service unavailable; not proof of expiry"
    }
  ],
  "conditionalUpdatePolicy": {
    "required": [
      "record exists",
      "expected version matches",
      "record active",
      "lifetime valid"
    ],
    "onConflict": "reread trusted state and reapply policy; no blind resurrection",
    "onMissing": "do not create authenticated binding from client claim"
  },
  "selector": {
    "xml": "<sessions><decision case=\"normal\" accepted=\"true\" known=\"true\" active=\"true\" lifetime=\"true\"/><decision case=\"stale-touch\" accepted=\"false\" known=\"true\" active=\"false\" lifetime=\"true\"/><decision case=\"missing-after-eviction\" accepted=\"false\" known=\"false\" active=\"false\" lifetime=\"false\"/><decision case=\"policy-expired\" accepted=\"false\" known=\"true\" active=\"true\" lifetime=\"false\"/><decision case=\"store-unavailable\" accepted=\"false\" known=\"false\" active=\"false\" lifetime=\"false\"/></sessions>",
    "xpath": "count(/sessions/decision[@accepted=\"true\" and (@known!=\"true\" or @active!=\"true\" or @lifetime!=\"true\")])",
    "expected": 0,
    "positiveFixtureXml": "<sessions><decision accepted=\"true\" known=\"false\" active=\"false\" lifetime=\"false\"/></sessions>",
    "positiveExpected": 1
  }
}
lookup / source
Lookup sonucu ve freshness kaynağı; error, missing ve eski snapshot birbirinden ayrıdır.
expectedVersion / observedVersion
Conditional update’in concurrency koşulu; güvenlik credential’ı değildir.
recordState / lifetimeValid
Fiziksel record varlığı active ve lifetime uygunluğu yerine geçmez.
sessionAccepted
Bu fixture’ın session decision’ı; resource authorization sonucu değildir.
selector
Accepted için known+active+lifetime invariant’ını sorgular; gerçek telemetry değildir.

Remote store tek logical authority olarak varsayılır; replica/failover etkileri açıklanır ama bu sahnede simüle edilmez. Version 7/8 alias’tır; latency ve TTL sayısı verilmez. HTTP 401/503 bu fixture’ın seçilmiş response’larıdır. Gerçek store, credential veya load balancer çalıştırılmadı.

İki yanlış kanı

Shared session store bütün node’lara anında aynı güncel state’i ve kayıpsız failover’ı garanti eder.

Read path, replication consistency ve persistence ayrı tasarım kararlarıdır. Redis default async replication kullanır; WAIT tek başına strong consistency veya her failover’a karşı durability garantisi vermez.

Store’da record yoksa cookie’den yeniden authenticated session kurulur; store error da expiry demektir.

Missing binding client iddiasıyla yeniden authenticated hale getirilemez. Lookup error current state’i unknown bırakır; expiry application’ın lifetime kararıdır. Bu fixture yeterli trusted state yoksa authenticated processing’i reddeder.

SIRA SENDE

Bu hikâyeyi sen çöz.

Sonucu tahmin et, kanıtın sınırını bul ve nedenini kendi cümlenle anlat.

NodeA expectedVersion=7 ile touch yapıyor. Authoritative record version=8 ve revoked. Write sonucu ne olur?

  1. Version=7 snapshot’ı revoked state’i yeniden active yapar.
  2. Reddedilir. Revoked version=8 değişmez.
Gerekçeli cevabı oku

Reddedilir. Revoked version=8 değişmez. — Eski touch, revoked binding’i yeniden açamaz. Conflict sonrasında güncel güvenilen state’in yeniden okunması gerekir.

Store lookup hatası, session’ın expired olduğunu kanıtlar mı?

Dersten seçilen artifact alanları; öğretim örneği

cases[4]
{"case":"store-unavailable","node":"B","lookup":"error","source":"unknown","observedVersion":null,"recordState":"unknown to application","sessionAccepted":false,"productOutcome":"service unavailable; not proof of expiry"}
  1. Hayır. Record bilinmiyor; kabul durur ve service unavailable olur.
  2. Evet. Her store hatasının nedeni session expiry’dir.
Gerekçeli cevabı oku

Hayır. Record bilinmiyor; kabul durur ve service unavailable olur. — Bu sonuç expiry kanıtı değildir. Missing ve expired branch’leri ayrı gözlemler sağlar; burada record state’i bilinmiyor.

Eviction sonrasında success-missing ile fiziksel olarak bulunan fakat lifetime-invalid record neden farklıdır? İkisinde de accepted=false.

Gerekçeli cevabı oku

Başarılı missing lookup binding bulamaz; client iddiasından yeniden oluşturulmaz. Süresi dolmuş record ise fiziksel olarak durabilir ama lifetime kontrolünden geçmez. Eviction, durability ve replication mekanizmaları login policy’sinin yerine geçmez. Shared store’un session’ı kabul etmesi de resource izni değildir.

□ Fiziksel yokluk ile logical expiry’yi ayırdım.

□ Store mekanizmalarını authentication policy’sinin yerine koymadım.

Uygulama konsolunu aç · request / response / browser
Request, URL, cookie ve DOM örneklerini ayrıca aç

Kaynaklar ve kapsam

  • OWASP — Session Management Cheat SheetSession ID Content (or Value) · Built-in Session Management Implementations · Server-Side Session Token Storage · Session Expiration · Logging Sessions Life Cycle
  • OWASP — Authorization Cheat SheetValidate the Permissions on Every Request · Verify that Authorization Checks are Performed in the Right Location
  • Redis — Key evictionUsing the maxmemory configuration directive · Eviction policies: noeviction · Using the INFO command: evicted_keys versus expired_keys
  • Redis — ReplicationRedis replication: asynchronous default and WAIT limitations
  • Redis — PersistencePersistence options: RDB, AOF, no persistence · RDB disadvantages
  • Redis — TransactionsOptimistic locking using check-and-set · WATCH explained · Errors inside a transaction · What about rollbacks?