JWT (JSON Web Token) nedir, üç parçası nasıl çalışır, nerelerde kullanılır ve yaygın token hatalarından kaçınmak için temel güvenlik ipuçlarını öğrenin.

Bir JWT (JSON Web Token), sistemler arasında taşınabilen, bilgi (genellikle bir kullanıcı veya oturum hakkında) temsil eden kompakt, URL-uyumlu bir dizgedir. Genellikle eyJ... ile başlayan uzun bir değer görürsünüz ve Authorization: Bearer \u003ctoken\u003e gibi bir HTTP header'ında gönderilir.
Geleneksel girişler genellikle sunucu oturumlarına (server sessions) dayanır: oturum açtıktan sonra sunucu oturum verisini saklar ve tarayıcıya bir oturum kimliği cookie'si verir. Her istek o cookie'yi içerir ve sunucu oturumu arar.
Token tabanlı kimlik doğrulama ile sunucu her kullanıcının isteği için durum saklamak zorunda kalmaz. Bunun yerine istemci bir token (ör. JWT) tutar ve API çağrılarıyla birlikte gönderir. Bu, API'ler için popülerdir çünkü:
Önemli nüans: “durumsuz” demek “hiçbir sunucu tarafı kontrolü yok” anlamına gelmez. Birçok gerçek sistem hâlâ kullanıcı durumunu, anahtar rotasyonunu veya iptal mekanizmalarını kontrol eder.
JWT'ler genellikle kimlik doğrulama kanıtı (oturum açık) ve basit yetkilendirme ipuçları (roller, izinler, scope'lar) taşır—ama sunucunuz yine de yetkilendirme kurallarını uygulamalıdır.
JWT'leri genellikle erişim tokenı olarak şu yerlerde görürsünüz:
Bir JWT, her biri base64url ile kodlanmış ve nokta ile ayrılmış üç parçadan oluşan kompakt bir dizgedir:
header.payload.signature
Örnek (kısaltılmış):
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwiaWF0IjoxNzAwMDAwMDAwfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c…
Header, tokenin nasıl oluşturulduğunu açıklar—özellikle imzalama algoritması (ör. HS256, RS256/ES256) ve token türü.
Yaygın alanlar:
typ: genellikle "JWT" (çoğunlukla göz ardı edilir)alg: kullanılan imzalama algoritmasıkid: doğrulayıcının rotasyon sırasında doğru anahtarı seçmesine yardımcı olan anahtar tanımlayıcısıGüvenlik notu: header'a körü körüne güvenmeyin. Gerçekten kullandığınız algoritmaların bir allowlist'ini uygulayın ve alg: "none" kabul etmeyin.
Payload, kullanıcı ve token bağlamı hakkında "claim" (alan) tutar: kimin için olduğu, kimin oluşturduğu ve ne zaman süresinin dolacağı gibi.
Önemli: JWT'ler varsayılan olarak şifrelenmez. Base64url kodlama tokeni URL-uyumlu yapar; veriyi gizlemez. Tokeni alan herkes header ve payload'u çözebilir.
Bu yüzden parolalar, API anahtarları veya hassas kişisel verileri JWT'ye koymaktan kaçının.
Signature, header + payload'in bir anahtarla imzalanmasıyla oluşturulur:
İmza bütünlük sağlar: sunucu tokenin değiştirilmediğini ve güvenilir bir imzalayıcı tarafından oluşturulduğunu doğrulayabilir. Bu, gizlilik sağlamaz.
Bir JWT her istekle birlikte header ve payload'ı içerdiğinden, daha büyük tokenlar daha fazla bant genişliği ve ek yük demektir. Claim'leri sade tutun ve fazla veri yerine tanımlayıcıları tercih edin.
Claim'ler genelde iki kategoriye ayrılır: registered (standart isimler) ve custom (uygulamanıza özel alanlar).
iss (issuer): tokeni kim oluşturdusub (subject): tokenin kim hakkında olduğu (çoğunlukla kullanıcı ID'si)aud (audience): tokenin hedefi (ör. belirli bir API)exp (expiration time): tokenin kabul edilmemesi gereken zamaniat (issued at): tokenin oluşturulma zamanınbf (not before): tokenin bu zamandan önce kabul edilmemesi gerekirHizmetin gerçekten yetkilendirme kararı vermesi için ihtiyaç duyduğu kadar bilgi koyun.
İyi örnekler:
user_id)Profil verisini kopyalayan "kolaylık" claim'lerinden kaçının. Bunlar tokeni şişirir, çabuk bayatlar ve token sızarsa etkisini artırır.
Payload okunabildiği için koymayın:
Hassas bilgi gerekiyorsa, sunucuda saklayın ve token'da sadece bir referans (ör. ID) bulundurun—ya da uygun olduğunda şifreli token formatı (JWE) kullanın.
İmzalama şifreleme değildir.
Token verildiğinde sunucu header + payload'i imzalar. Token daha sonra sunulduğunda sunucu imzayı yeniden hesaplar ve karşılaştırır. Bir karakter bile değişse doğrulama başarısız olur ve token reddedilir.
JWT bir token formatıdır. OAuth 2.0 ve OpenID Connect (OIDC) tokenlerin nasıl talep edileceğini, verileceğini ve kullanılacağını tanımlayan protokollerdir.
OAuth 2.0 esas olarak yetkilendirme ile ilgilidir: bir uygulamanın kullanıcının şifresini paylaşmadan bir API'ye erişmesine izin vermek.
Access tokenlar genellikle kısa ömürlüdür (dakikalar). Kısa süre, bir token sızarsa zararını sınırlar.
OIDC OAuth 2.0 üzerine kimlik doğrulamayı ekler ve genellikle bir ID token (çoğunlukla JWT) sunar.
Temel kural: ID token'ı bir API çağrısı yapmak için kullanmayın.
Eğer akışlar hakkında daha fazla pratik bilgi isterseniz, şu kaynağa bakın: /blog/jwt-authentication-flow.
Tipik bir akış şöyle işler:
Kullanıcı (e-posta/parola, SSO vb.) ile oturum açar. Başarılıysa sunucu subject ve expiration gibi temel claim'lerle bir JWT (genellikle bir access token) oluşturur.
Sunucu tokeni imzalar ve istemciye (web uygulaması, mobil uygulama veya başka bir servis) döner.
Korumalı uç noktalarda istemci JWT'yi Authorization header'ında gönderir:
Authorization: Bearer \u003cJWT\u003e
İstek işlenmeden önce API genellikle şu kontrolleri yapar:
exp (süresi dolmadı)iss (beklenen issuer)aud (bu API için mi)Tüm kontroller geçerse API kullanıcıyı kimliklendirilmiş kabul eder ve yetkilendirme kurallarını uygular (ör. kayıt düzeyi izinleri).
Sistem saatleri kayabilir; bu yüzden exp ve bazen nbf gibi zaman bazlı claimleri doğrularken küçük bir saat kayması (clock skew) toleransı verilir. Toleransı küçük tutun ki token ömrü gereğinden fazla uzamasın.
Depolama seçimi saldırganların hangi tokenleri çalabileceğini ve bunları ne kadar kolay tekrar kullanabileceğini değiştirir.
Bellekte saklama (çeşitli SPA'larda önerilir) erişim tokenını JS state'te tutar. Yenilemede temizlenir ve "sonradan çalma" riskini azaltır; ancak bir XSS açıkken yine okunabilir. Kısa ömürlü access tokenlar ve bir yenileme akışı ile kullanın.
localStorage/sessionStorage kullanımı kolaydır ama risklidir: herhangi bir XSS açığı tokenleri çalabilir. Eğer kullanıyorsanız XSS önlemlerini kesinlikle uygulayın (CSP, output escaping, bağımlılık temizliği) ve token sürelerini kısa tutun.
Güvenli cookie'ler (çoğunlukla web için en güvenli varsayılan) tokenleri HttpOnly cookie'de saklayarak JavaScript'in okumamasını sağlar—bu, XSS ile token hırsızlığını azaltır. Dezavantajı CSRF riskidir, çünkü tarayıcı cookie'leri otomatik olarak gönderir.
Cookie kullanıyorsanız şunları ayarlayın:
HttpOnlySecure (yalnızca HTTPS)SameSite=Lax veya SameSite=Strict (bazı çapraz-site akışlar SameSite=None; Secure gerektirebilir)Ayrıca durum değiştiren istekler için CSRF tokenlerini düşünün.
iOS/Android'de tokenleri platformun güvenli depolamasında (Keychain / Keystore destekli) saklayın. Düz dosya veya preferences içinde saklamaktan kaçının. Tehdit modeliniz köklü/jailbreak yapılmış cihazları içeriyorsa, çıkarımı mümkün kabul edin ve kısa ömürlü tokenlar ile sunucu tarafı kontrollerine güvenin.
Bir tokenin yapabileceği şeyi sınırlandırın: minimum scope/claim'ler kullanın, access tokenları kısa ömürlü tutun ve hassas verileri gömmekten kaçının.
JWT'ler kullanışlıdır, ancak birçok olay tahmin edilebilir hatalardan kaynaklanır. Bir JWT'yi nakit gibi değerlendirin: onu alan genellikle onu harcayabilir.
Token günler veya haftalar boyunca geçerliyse, sızıntı bir saldırgana geniş bir pencere verir.
Access tokenları için mümkün olduğunca kısa süre (dakikalar) tercih edin ve güvenli bir mekanizma ile yenileyin. "Beni hatırla" gerekiyorsa bunu refresh tokenlar ve sunucu tarafı kontrollerle yapın.
Geçerli bir imza tek başına yeterli değildir. iss ve aud doğrulayın ve exp/nbf gibi zaman bazlı claimleri kontrol edin.
Decode etmek doğrulama değildir. Her zaman sunucuda imzayı doğrulayın ve izinleri sunucu tarafında uygulayın.
JWT'leri sorgu parametresine koymaktan kaçının. Tarayıcı geçmişinde, sunucu loglarında, analiz araçlarında veya referrer başlıklarında yer alabilirler.
Bunun yerine Authorization: Bearer ... kullanın.
Anahtarların ve tokenların sızabileceğini varsayın. İmza anahtarlarını döndürün, kid kullanarak yumuşak rotasyonu destekleyin ve iptal stratejiniz olsun (kısa süreler + hesap/oturum devre dışı bırakma gibi). Depolama kılavuzu için şu kaynağa bakın: /blog/where-to-store-jwts-safely.
JWT'ler faydalıdır, ama otomatik olarak en iyi seçenek değiller. Asıl soru, her istekte veritabanı sorgusu yapmadan doğrulanabilecek kendi içinde yeterli bir tokenten fayda sağlayıp sağlamadığınızdır.
Geleneksel sunucu tarafı render edilen web uygulamaları için, hızlı geçersiz kılma gerekiyorsa sunucu tarafı oturumlar ve HttpOnly cookie'ler genelde daha basit ve daha güvenlidir.
JWT seçin eğer doğrulamanın servislere dağıtılmış halde durumsuz yapılması gerekiyorsa ve tokenları kısa ömürlü tutabiliyorsanız.
JWT'den kaçının eğer anında iptal gerekiyorsa, token içine hassas veri koyacaksanız veya oturum cookie'leri sorunsuz uygulanabiliyorsa.
Doğru anahtar ve beklenen algoritma ile doğrulayın. Geçersiz imzaları reddedin—istisna yok.
exp (süresi dolma)Tokenin süresi dolmamış olmalı.
nbf (kullanılmadan önce)Varsa tokenin erken kullanılmadığından emin olun.
aud (audience)Tokenin sizin API/service için olup olmadığını doğrulayın.
iss (issuer)Tokenin beklenen issuer tarafından verildiğini doğrulayın.
Token formatını doğrulayın, maksimum boyut uygulayın ve beklenmeyen claim türlerini reddederek kenar durum hatalarını azaltın.
HS256 (simetrik anahtar): tek bir gizli anahtar hem imzalar hem doğrular.
RS256 / ES256 (asimetrik anahtarlar): özel anahtar imzalar; genel anahtar doğrular.
Genel kural: birden fazla bağımsız sistem tokenleri doğrulayacaksa (veya her doğrulayıcıya güvenmiyorsanız), RS256/ES256 tercih edin.
iss, aud, ve politika izin veriyorsa bir kullanıcı ID'si) loglayın.JWT şifreli mi?
Varsayılan olarak hayır. Çoğu JWT imzalıdır, şifreli değildir. İçerik tokeni edinen herkes tarafından okunabilir. Gizlilik gerekiyorsa JWE kullanın veya hassas verileri JWT'de tutmayın.
Bir JWT'yi iptal edebilir miyim?
Sadece kendi başına duran access tokenlar kullanıyorsanız zor. Yaygın yaklaşımlar kısa ömürlü access tokenlar, yüksek riskli olaylar için kara listeler veya dönen refresh tokenlar kullanmaktır.
exp ne kadar olmalı?
UX ve mimarinizin izin verdiği kadar kısa. Birçok API erişim tokenlarını dakikalar düzeyinde tutar ve daha uzun oturumlar için refresh token kullanır.
JWT kimlik doğrulamasını yeni bir API veya SPA'da uyguluyorsanız, işin birçok kısmı tekrarlayıcıdır: middleware bağlamak, iss/aud/exp doğrulamaları, cookie bayraklarını ayarlamak ve token işleme sırasında loglara düşmemesini sağlamak.
Koder.ai ile bir web uygulaması (React), backend servisleri (Go + PostgreSQL) veya Flutter mobil uygulaması sohbet tabanlı bir akışla hızla oluşturabilir, güvenlik ayarlarını planlama modunda iyileştirip snapshot/rollback ile deneyebilir ve hazır olduğunuzda kaynak kodu dışa aktarabilirsiniz. Bu, JWT tabanlı kimlik doğrulama akışlarını hızlandırırken doğrulama mantığı, anahtar rotasyonu stratejisi ve dağıtım/host ayarları üzerinde kontrol sahibi olmanızı sağlar (custom domains dahil).
Bir JWT (JSON Web Token), iddiaları (alanları) taşıyan ve sunucu tarafından doğrulanabilen kompakt, URL-uyumlu bir dizgedir. Genellikle API isteklerinde aşağıdaki gibi gönderilir:
Authorization: Bearer \u003ctoken\u003eTemel fikir: sunucu tokenin bütünlüğünü (imza aracılığıyla) doğrulayabilir ve her istek için ayrı bir oturum kaydı tutmak zorunda kalmaz.
Oturum (session) kimlik doğrulaması genellikle sunucuda durum saklar (cookie/session ID ile ilişkilendirilmiş oturum kaydı). JWT tabanlı kimlik doğrulamada istemci her istekte imzalı bir token sunar ve API bunu doğrular.
JWT'ler, doğrulamanın yerel olarak yapılabilmesi sayesinde API'ler ve çoklu servis mimarileri için popülerdir; bu da paylaşılan oturum depolama ihtiyacını azaltır.
“Durumsuz” demek, hiçbir sunucu tarafı kontrolü olmadığı anlamına gelmez—çoğu sistem hâlâ kara liste, kullanıcı durumu kontrolleri veya anahtar rotasyonu gibi sunucu kontrolleri uygular.
Bir JWT, nokta ile ayrılmış üç Base64URL-kodlu parçadan oluşur:
header.payload.signatureHeader (başlık) nasıl imzalandığını belirtir, payload iddiaları (ör. sub, exp, aud) içerir ve signature (imza) tokenin değiştirilmediğini doğrulamaya yarar.
Hayır. Standart JWT'ler genellikle imzalıdır, şifreli değildir.
Gizlilik gerekiyorsa JWE (şifreli tokenler) kullanın ya da hassas verileri sunucuda saklayıp JWT'de sadece bir referans bulundurun.
İmza, tokenin değiştirilip değiştirilmediğini ve imzayı oluşturan anahtara sahip birinden geldiğini doğrular.
İmza şunları garanti etmez:
exp süresinden önce iptalini otomatik olarak sağlamaTokeni bir kimlik bilgisi gibi değerlendirin: sızarsa, çoğu durumda süresi dolana kadar yeniden kullanılabilir.
alg doğrulayıcıya hangi algoritmanın kullanıldığını söyler (ör. HS256 veya RS256). kid anahtar seçimini kolaylaştıran bir anahtar tanımlayıcısıdır; anahtar rotasyonunda işe yarar.
Güvenlik için kısa kurallar:
Önce standart (registered) iddialarla başlayın ve özel (custom) claim'leri minimumda tutun.
Yaygın kayıtlı claim'ler:
JWT bir token formatıdır; OAuth 2.0 ve OpenID Connect (OIDC) ise protokollerdir.
Tipik eşleştirme:
Tarayıcı tabanlı uygulamalar için yaygın seçenekler:
En azından şu kontrolleri yapın:
exp (süresi dolmadı)alg değerlerini kabul etmeyin.alg: "none" kabul etmeyin.kid'in güvensiz anahtar arama davranışına yol açmasına izin vermeyin.iss (issuer / tokeni oluşturan)sub (subject / kullanıcı kimliği)aud (audience / hedef API)exp (expiration)iat (issued at)nbf (not before)Secret veya hassas kişisel verileri payload'a koymayın; token açığa çıkarsa okunur.
Önemli: bir ID token'ı API çağrısı için kullanmayın sadece çünkü görünüşte bir access token gibi.
Cookie kullanıyorsanız şunları ayarlayın:
HttpOnlySecure (yalnızca HTTPS)SameSite=Lax veya SameSite=Strict (bazı çapraz-site akışlar SameSite=None; Secure gerektirebilir)Ayrıca durum değiştirici istekler için CSRF tokenlerini düşünün.
iss (beklenen issuer)aud (token sizin API'niz için mi)nbf (varsa, token erken kullanılmıyor mu)Ayrıca pratik önlemler ekleyin: