Derinlemesine yazılım eğitimleri için kanalımı takip edebilirsiniz...

JSON Web Token(JWT) Nedir?

Merhaba,

Bu içeriğimizde klasik oturum yönetimi araçlarından olan Session yahut Cookie yapılarına alternatif RFC 7519 standartı JSON Web Token(JWT) üzerine konuşuyor olacağız.

Günümüzde RESTFull API’lar da oturum işlemlerini eski usul Session yahut Cookie araçlarıyla değil JSON Web Token(JWT) ile gerçekleştirmekteyiz. Daha doğrusu JWT ile oturum işlemlerimizi icra etmeyi tercih etmekteyiz demem daha doğru olacaktır. “Peki hoca, Session ya da Coockie neyimize yetmedi?” şeklinde sorunuzu duyar gibiyim…

Evet… Bunca zamandır kullandığımız Session, Cookie vs. gibi yapılar ihtiyaçlarımıza yeterince cevap verebilme kabiliyetine sahiptiler. Ama günümüzde internet trafiğinin yoğunlaşması ve kullanıcı etkileşiminin artmasından dolayı eskiye nazaran misliyle oturum işlemleri gerçekleştirilmektedir. Dolayısıyla bu yoğunlukta bizlere performans ve maliyet açısından ve tüm bunların yanında hızlı işlevsellikte olan yapılar gerekmektedir. İşte bundan dolayı eski teknolojilere nazaran JWT yapısı geliştirilmiştir.

Mesela, oluşturulan her bir session için arkaplanda gerçekleştirilen IO işlemlerinin artan yoğunlukta performans açısından sunucuya ne kadar maliyetli olduğunu düşünün… Ya da aynı anda hem web hem de mobilde çalışan ve tek bir API üzerinden işlevsellik gösteren uygulamalarda session bazlı oturum bilgilerini platformlar arasında taşımaya yeltenince karşılaşılabilecek problemleri… İşte bu durumlara istinaden JWT’de hem IO işlemlerinden yalıtılmışlık söz konusuyken hem de platformlar arasında oturum transferi hiçbir probleme mahal vermeksizin sadece tokenı taşımakla sorunsuz gerçekleştiriliyor.

Token – Session Karşılaştırması

Session Login Token Login
Client -> Siteyi aç.
Server -> SessionID ver.
Client -> UserName & Password gir ve SessionID ile yolla.
Server -> Bilgileri kontrol et. Doğru ise Session’a user bilgilerini set et. Yönlendirmeyi gerçekleştir.
Client -> Settings sayfasını iste. SessionID gönder.
Server -> SessionID için giriş yapmış kullanıcı var mı kontrol et. Cevap ver.
Client -> Siteyi aç.
Client -> UserName & Password yolla.
Server -> Bilgileri kontrol et. Doğru ise token oluştur ve Client’a yolla. Yönlendirmeyi gerçekleştir.
Client -> Settings sayfasını iste. Token gönder.
Server -> Token geçerli mi kontrol et. Cevap ver.

Tüm bunların yanında token yapılanmasının kendine has avantajlarıda mevcuttur;

  • Tokenlar cookie istemezler. Bundan dolayı mobil browserlar gibi cookie desteklemeyen platformlarda çalışabilirler.
  • Tokenler browsera özel değildir. Dolayısıyla, uygulamaya hangi platformdan login olunursa olunsun elde edilen token bir başka platformda rahatça kullanılabilir.

Token’ın Fiziksel Yapısı

Token, oturumla ilgili kritik bilgilerin şifrelendiği bir fotmattır. Yapısı aşağıdaki gibidir;

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c

Yukarıdaki token örneğine yapısal olarak dikkat edilirse eğer bir tokenın üç bölümden oluştuğu görülmektedir. Bu üç alanın ne olduğunu incelersek eğer;

HEADER
“Algoritma & Token Tipi”
PAYLOAD
“Veri”
{
  "alg": "HS256",
  "typ": "JWT"
}
{
  "sub": "1234567890",
  "name": "John Doe",
  "iat": 1516239022
}
Başlıklar, kullanılacak algoritma ve token tipi belirlenmektedir. Oturum için taşınması gereken datalar barındırılmaktadır.(surname, password, id vs.)
Kritik bilgiler taşınabilir.
VERIFY SIGNATURE
“İmza”
HMACSHA256(
  base64UrlEncode(header) + "." +
  base64UrlEncode(payload),
  your-256-bit-secret
)
Tokenın imzasıdır. İki parametre mevcuttur.
1. Header ve Payload alanlarının BASE64 ile şifrelenmiş verileri.
2. Bizim tarafımızdan belirlenmiş olan gizli anahtar.

Tüm bu bilgilerin şifrelenerek harmanlanmış hali token yapısında bir veriyi ortaya çıkarmakta ve bizler sadece o veriyi kullanarak tüm işlemlerimizi gerçekleştirebilmekteyiz.

İlgilenenlerin faydalanması dileğiyle…
Sonraki yazılarımda görüşmek üzere…
İyi çalışmalar…

Bunlar da hoşunuza gidebilir...

16 Cevaplar

  1. Mehmet dedi ki:

    Merhaba,

    Bir sorum olacaktı. Verilen bu token ile session ile yapabildiğimiz her şeyi yapabilir miyiz, e ticaret sitelerindeki gibi sepet uygulaması yapılabilir mi ? Yoksa session ile jwt yapılarını birlikte kullanmak daha mı iyidir böyle bir şeyi nasıl yapabiliriz ?

    • Gençay dedi ki:

      Merhaba,

      JWT genellikle authentication durumlarında içerisine gerekli datalar yerleştirildikten sonra üretilen ve süresi bitene kadar stabil kullanılan bir değerdir/jetondur. E-Ticaret uygulamalarındaki sepet, favori vs. gibi uygulamalarda ilgili verileri JWT’ye eklemek demek, JWT’yi güncellemek demektir ve bu durumda kullanıcı doğrulama aparatını güncellemek demek olacaktır. Bu durum ilgili senaryolar için pekte uygun gözükmemektedir. Sizlere tavsiyem daha spesifik ve efektif çözümler üretmeniz yahut session veya cookie gibi anahtar yapılar üzerinden verisel işlemlerinizi gerçekleştirmenizdir…

      Sevgiler.

  2. Mehmet dedi ki:

    Soruma cevap verdiğiniz için teşekkür ederim. Peki modern web sitelerinde authentication mı sadece kullanılıyor ? Örneğin bir alışveriş sitesinde sepete eklenen ürün birkaç gün geçmesine rağmen hala sepette duruyor bu olay session ile olmuyor mu ? Yani ben kullanıcıyı doğrulama için jwt kullanmak ve aynı zamanda da bu tarz sepet , favori işlemlerini yapabilmem mümkün mü ?

    • Gençay dedi ki:

      Estafurullah. Şahsen bu tarz durumlarda sepetteki ürünlerin veritabanına kaydedildiğine de, 20 gün expire sürelik session’da da tutulduğuna şahit oldum 🙂 Kullanıcı işlemleri için authentication boyutunda JWT’yi kullanabilirsiniz lakin sepet, favori vs. gibi işlemleri farklı yaklaşımla çözmenizi tavsiye ederim.

  3. Ali dedi ki:

    Merhabalar yazınız için teşekkür ederim. Jwt ile şifrelenmiş veriler üzerinde kontrol işlemi yapıyoruz. Peki bu bilgilere server tarafında ihtiyacımız olursa(mevcut kullanıcının bilgileri) ne yapmamız gerekir; şifreyi çözümleyip kullanmamız mı yoksa bu bilgileri aynı zamanda session gibi araçlarla saklayıp mı kullanmamız gerekir. Gerçek hayat projelerinde nasıl bir yol izleniyor ?

    • Gençay dedi ki:

      Merhaba,

      Sisteme giriş yapan kullanıcılara dair bilgi edinilmek istenildiği taktirde mevcut token değerleri veritabanları yahut Redis gibi sistemlerde tutulmaktadır.

      Kolay gelsin.

  4. Ekrem dedi ki:

    Merhabalar,
    Güzel yazı için teşekkürler. Fakat bir sorum olacaktı. Node.js ile uygulama geliştiriyorum. Oluşturduğum token cookie de tutuyorum. Fakat iki farklı browserdan farklı kullanıcılar ile giriş yapıyorum. Mesela mozilladan girdiğim kullanıcının token bilgisini chrome daki kullanıcıya yazdığımda kullanıcı değişiyor. Yani token ele geçirildiği zaman kullanıcının bilgileri çalınmış oluyor. Bunu nasıl önleyebilirim?

    • Gençay dedi ki:

      Merhaba,

      İlk olarak JWT’nin ne olduğunu tam anlayarak istişarede bulunalım.

      JWT’ler kimlik doğrulama standartlarından yalnızca bir tanesidir. Lakin kimlik doğrulama dışında hemen hemen ihtiyaca binaen her şey için kullanılabilirler. Kimlik doğrulamalarında genellikle kullanılmasının sebebi, üretilen token’a fazladan bilgi yükleyebilmemiz ve bu token’ı yeryüzündeki diğerlerinden ayırabilmek için kendinize has imzalayabilmemizdir(signature).

      Yani anlayacağınız esasında JWT’lerin salt güvenlik ile pekte alakası yoktur.

      Esasında burada sorunuzla bizzat alakalı olan konu kullanılan protokoldür. OAuth2; işlevsel olarak, belirli bir süreliğine(tabi ki de kısa bir süre) kimlik doğrulamak için geçici token değerleri üretmek ve client’lara göndermek için tasarlanmıştır. Nasıl ki sizler kredi kartınızı çaldırdığınızda yahut kaybettiğinizde kötü niyetli kişiler tarafından ilgili kartın kısa süreli kullanılması mümkünse ve bundan dolayı kartın iyi muhafaza edilip korunması gerekliyse tüm bunlar JWT içinde geçerlidir.

      Peki bu olası duruma istinaden ne gibi önerilerde bulunursunuz?
      Öneri olarak aşağıdaki durumlar göz önüne alınarak geliştirme gerçekleştirilebilir.

      • JWT ömrü kısa tutulabilir ve böylece kısa aralıklarla sürekli sunucudan token üretilebilir. Böylece JWT, kötü niyetli kişiler tarafından elde edilsede ellerindeki veri hızlı bir şekilde çürüyecek ve sizi takip etmesi güçleşecektir.
      • Üretilecek token değerlerinin ömrünü 30 dakika, yenilenebilirlik sürelerini ise 3 gün gibi değerlerle sabitleyebilirsiniz. Yenilenebilirlik süresi dolan token değerlerini bir blacklist’e alınız ve refresh edilmelerini engelleyiniz.
      • Teorik olarak token hırsızlığını önlemek neredeyse imkansızdır. Bu yüzden refresh token stratejisinin kullanımına odaklanılmalıdır.

      Token değerinizin çalınması için genellikle kötü niyetli bir kişi yahut eavesdropper(kulak misafiri) tarafından ağ trafiğinizin gözetlenmesi gerekmektedir. İşte burada SSL devreye girmekte ve ihlallerin önlenmesine yardımcı olmaktadır. SSL, client ile server arasındaki dataların şifrelenerek dışarıdan manipüle edilmesini engelleyen bir güvenlik protokolüdür. Tabi ki de SSL kul yapısıdır ve başka yöntemlerle aşılabilmektedir. İşte bu durumda yapılabilecek önlemler yukarıda da bahsettiğimiz gibi kötü niyetli kullanıcının ayağına mümkün mertebe taş değmesini sağlayacak zaruri özelleştirilmiş önlemlerdir.

      Kolay gelsin…

  5. Ekrem dedi ki:

    Yardımcı olduğunuz için çok teşekkür ederim.

  6. sorağan dedi ki:

    Ben bu jwt tokeni tam anlamadım. Bundan biz kazanabiliyor muyuz, nasıl kazanılıyor?

  7. kubilay dedi ki:

    Selamlar, olusturulan token celint tarafına gönderildi diyelim, ve localStoreage’de duruyor token. logout işlemi yaparken localStoreage’de tokeni silicez ve cıkıs yapmak olucaz. Bunu client tarafında sunucu tarafında mı yapmalıyız. Neticede her ikiside token’i silmiş olcak. Cevap verirseniz sevinirim SAYGILAR..

    • Gençay dedi ki:

      Client token’ı silebilir. Lakin token expired olmadığı sürece hala geçerliliğini korumaktadır. Sunucu tarafında ilgili token’ı geçersiz kılmak istiyorsanız eğer redis’e kaydedip bir blacklist tarzı çalışma gerçekleştirebilirsiniz.

Bir yanıt yazın

E-posta adresiniz yayınlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir