8 Haziran 2014 Pazar

Django'da Oturumlar (Sessions)


          Django; oturumları (session), çerezleri kullanarak sağlar.  İstemcinin sunucuya ilk bağlanmasında 32 bit uzunluğunda onaltılık sayı sistemde rastgele üretilmiş bir sayı oluşturulur, sessionid (örn: ac514a03cbd1f2343c22ed3bd2ba8y76.  Bu sessionid daha sonra yapılacak her bağlanmada istemciden sunucuya gönderilir. Django oturum bilgilerini bu sessionid 'yi anahtar kabul eden bir sözlükte tutar ve veritabanındaki django_session isimli tabloya kaydeder. Kullanıcı artık her bağlantı yaptığında çerez bilgileri ile veritabanındaki veriler kıyaslanır. Ayrıca oturum bilgileri sözlük gibi davranan request.session nesnesinde saklanır. Tabiki tüm bunlar otomatik olarak Django tarafından yapılır. Bize sadece oturum bilgilerini kullanarak işlemlerimizi yapmak kalır. Örnek vermek gerekirse :

# Oturum'a deger atama:
request.session["favori_renk"] = "mavi"

# Oturum'daki degeri alma :
favori_renk = request.session["favori_renk"]                            
# Oturum silme:                                                       del request.session["favori_renk"]                                           
# İstenilen anahtar kelimenin oturumda olup olmadığını kontrol etme:  if "favori_renk" in request.session:                                     ...
       Ayrıca keys() ve items() gibi sözlük fonksiyonlarını da request.session nesnesi üzerinden kullanabiliriz. Bu durum, ihtiyaca göre şekillenecektir.

       Django'da oturumları daha etkili kullanmak için birkaç  kural vardır. Bunlar :
  • request.session nesnesi için kullanacağınız anahtar kelimeleri Python string kurallarına uyacak şekilde seçilmesi :
request.session['favori_renk'] = '5favori_renk'   #Hatalı kullanım
  • Oturum için kullanacağınız sözlük anahtarlarınızı asla '_' ile başlayacak şekilde kullanılmaması, çünkü bu tür kullanımları Django kendi sözlük anahtarları olarak kullanır. Elbette Django'nun bu tür kullanımları çok fazla sayıda değildir ama Django'nun neleri kullandığını bilmediğimiz için bu durumdan uzak durmalıyız. 
  request.session['_favori_renk'] = 'mavi'    #Hatalı kullanım
  • request.sessions nesnesine yapacağınız atamalara dikkat edin. Aşağıdaki kullanımlardan uzak durun : 
request.session = herhangi_bir_nesne    #Hatalı kullanım
request.session.foo = 'bar'             #Hatalı kullanım
Şimdi oturum kullanımına güzel bir örnekle bakalım. Bu örnekte bir gönderiye yorum yapma durumunu request.session nesnesi ile nasıl kontrol edildiğine bakalım :  
def yorum_yap(request):
    if request.method != 'POST':
        raise Http404('Sadece POSTlara izin var')

    if 'yorum' not in request.POST:
        raise Http404('Yorum yapılmamıştır !!')
                                                                          #Daha önce yorum yapıldı mı? 
    if request.session.get('yorum_yapıldı', False):
        return HttpResponse("Daha önce yorum yaptınız .")                   
    #Daha önce yorum yapılmadıysa yorum oluştur 
    y = yorumlar.Yorum(yorum=request.POST['yorum'])    y.save()                                                                                                       
    request.session['yorum_yapıldı'] = True    return HttpResponse('Yorum için teşekkürler !')

Şimdi de  tüm bu öğrendiklerimizi görsel bir örnek ile pekiştirelim. Geçen haftalarda üzerinde çalıştığımız okul projesinde öğretim elemanlarının listesini sayfalamıştık. Orada dikkat ettiyseniz bir sayfada sıralama yaptıktan sonra başka bir sayfaya geçişte ya da bilgi güncelleme yaptıktan sonra yaptığımız sıralamalar bozuluyordu. Şimdi bu sorunumuzu kullanıcının oturum bilgilerini kullanarak çözelim. ogretim_elemanlari_listesi() adlı görünümümüzü aşağıdaki gibi güncelleyelim : 


def ogretim_elemanlari_listesi(request):
                                                                          # Kullanıcıdan sıralama ölçütünün geldiğini kontrol et
    if request.GET.get('sirala'):
        request.session['ogretim_elemani_siralama']=request.GET['sirala']
     # Kullanıcıdan herhangi bir sıralama ölçütü gelmediyse                # ad'a göre sıralama ölçütü ata 
    if not 'ogretim_elemani_siralama' in request.session:
        request.session ['ogretim_elemani_siralama']='1'
    
    olcut = request.session['ogretim_elemani_siralama']                           
     #Kullanıcıdan gelen sayfa numarası var mı?
    if request.GET.get('sayfa'):
       request.session['ogretim_elemani_sayfa'] = request.GET['sayfa'] 
     #Yoksa sayfa ata 
    if not 'ogretim_elemani_sayfa' in request.session:
        request.session['ogretim_elemani_sayfa'] ='1'

    sayfa = request.session['ogretim_elemani_sayfa']
    
    if olcut :
        siralamaOlcutleri={
            '1':'adi',
            '2':'soyadi',
            '3':'e_posta_adresi'
            
            }
        if olcut in siralamaOlcutleri:
            siralama = siralamaOlcutleri[olcut]
            
    ogretim_elemanlari_tumu = OgretimElemani.objects.order_by(siralama)

    arama_formu = AramaFormu()

    if request.GET.get('aranacak_kelime'):
        arama_formu = AramaFormu(request.GET)
        
    if arama_formu.is_valid():
        aranacak_kelime = arama_formu.cleaned_data['aranacak_kelime']
        ogretim_elemanlari_tumu = OgretimElemani.objects.filter(
            Q(adi__contains=aranacak_kelime) | Q(soyadi__contains = aranacak_kelime))

    ogretim_elemanlari_sayisi = ogretim_elemanlari_tumu.count()
    ogretim_elemanlari_sayfalari = Paginator(ogretim_elemanlari_tumu,5)
    ogretim_elemanlari = ogretim_elemanlari_sayfalari.page(int(sayfa))
    
    return render_to_response('ogretim_elemanlari_listesi.html',locals())

Şimdi de Django'nun oturum bilgilerini nasıl kaydettiğini görelim. Öncelikle kullandığınız tarayıcınızın localhost çerezleri arasından sessionid isimli çerezin değerini kopyalayalım (Şu anda bendeki sessionid değeri = e0814a03cbd1f2343c22ed3bd2ba859f). Django kabuğunu açıp aşağıdaki gibi kontrol edin. Kolay gelsin :)  
>>> from django.contrib.sessions.models import Session
>>> s = Session.objects.get (pk='e0814a03cbd1f2343c22ed3bd2ba859f')
>>> s.expire_date
datetime.datetime(2014, 6, 25, 1, 8, 58, 117000, tzinfo=<UTC>)
 
>>> s.get_decoded()
{'ogretim_elemani_siralama': u'1', 'ogretim_elemani_sayfa': u'1'}
>>>

NOT: Tüm bunları yapmadan önce projenizin Settings.py dosyasında bulunan INSTALLED_APPS =()
           listesine 'django.contrib.sessions' 'ı eklemeyi unutmayın. 


Referanslar :
  1. https://docs.djangoproject.com/en/dev/topics/http/sessions/
  2. http://www.djangobook.com/
  3. http://stackoverflow.com/
  4. http://www.djangobook.com/en/2.0/chapter14.html
  5. BAŞER, Mustafa (2013). Django 

Hiç yorum yok:

Yorum Gönder