Rediste Basit Veri Tipleri

Metin Ağaoğlu
Kodcular
Published in
6 min readDec 27, 2020
https://keestalkstech.com/2019/04/building-a-high-performing-last-viewed-list-using-redis/

Arkadaşlar merhaba. Redis’i anlatan yazımın ardından bu yazıda ise redis’teki veri tiplerine değinmeye çalışacağım.Bunu yaparken herhangi bir programlama dilindeki client’ı kullanmadan redis’in kendi cli’ı üzerinden örneklendiriyorum.

Önceki yazıma buradan ulaşabilirsiniz.

Önceki yazıdada değindiğimiz gibi redis’in aslında en büyük avantajlarınndan bir tanesi yüksek seviye veri yapılanı saklama ve kullanma yeteneği idi.Bu veri türlerinin nasıl çalıştığını anladıktan sonra, daha iyi uygulamalar tasarlayabilecek ve mevcut kaynakları daha iyi kullanabileceğinize inanıyorum. Ayrıca, Redis’in sorununuz için doğru çözüm olup olmadığına karar vermenizede yardımcı olacağını düşünüyorum. Redis’in birçok veri türüne sahip olmasının temel nedeni çok basittir: bir veri tipi her senaryo için uygun olmayabilir ve genellikle farklı sorunlar için farklı çözümlere ve veri tiplerine ihtiyaç duyuyoruz.

Tüm veri türlerini kullanmanız gerekmese de, doğru olanları seçebilmeniz için nasıl çalıştıklarını anlamanız önemlidir. Bu yazını sonunda, bu veri türleri hakkında temel bilginiz olacağını umuyorum.

Redis-cli

Bu yazıdaki örnekleri herhangi bir programlama dilindeki redis client’ı ile değil redis’in kendi cli’ı üzerinden yapacağım.Siz dilerseniz hem cli’den hemde kullandığınız programlama dilinin client library’sini kullanarak bunu yapabilirsiniz.

Redis’in birçok programlama dili için library’si vardır.İncelemek isterseniz linkini bıraktım.

Not: Biraz sonra göreceğimiz veri tiplerinden ile ilgili en temellerinden bahsedeceğim. Analtılan veri türünün rediste birden fazla komut’u ve kullanım şekli bulunmaktadır.Her veri türünün sonuna komut listesinin url’sini bıraktım.Buralara girip ilgili veri tip’i ile ilgili örnekler yapmanızı , en azından bir göz gezdirmenizi tavsiye ediyorum.

String

Rediste göreceğimiz ilk veri türü string’ler.Stringler redis’teki en basit ve çok yönlü veri türleridir.Aslında temelde bir bayt dizisidir.C dilindeki char veri tipi gibi düşünebilirsiniz.Bir string, değerine ve kullanılan komutlara göre bir tamsayı, ondalıklı sayı, metin veya bitmap olarak davranabilir. Her türlü veriyi depolayabilir: String (XML, JSON, HTML veya pure text), tam sayılar, değişkenler veya binary veriler(videolar, görüntüler veya ses dosyaları). Bir String değeri 512 MB metin veya binary veriyi aşamaz.

Redis cli’ı içerisinde string değerler ile işlem yapmak oldukçta basittir.Temel olarak get/set ve del komutları ile işlem yapabilirsiniz.Aşağıdaki örnekte basitçe bir string’i kayıt edip görüntüleyelim.

redis 127.0.0.1:6379> SET username "agaoglumetin" 
OK
redis 127.0.0.1:6379> GET username
"agaoglumetin"

Ayrıca bunların yanında çoklu ekleme , gösterme işlemlerinide MGET ve MSET ile yapabilirsiniz.

redis 127.0.0.1:6379> SET test1 "Hello"
OK
redis 127.0.0.1:6379> SET test2 "World"
OK
redis 127.0.0.1:6379> MGET test1 test2 nonexisting
1) "Hello"
2) "World"
3) (nil)

Kullanabileceğiniz senaryolar:

Önbellek mekanizmaları: HTML sayfalarından ve API yanıtlarından görüntülere ve videolara kadar herhangi bir şey olabilecek Redis’te string veya binary olarak önbelleğe alabilirsiniz. SET, GET, MSET ve MGET komutlarıyla basit bir önbellek sistemi uygulanabilir.

Otomatik son kullanma tarihine sahip önbellek: Otomatik anahtar son kullanma tarihi ile birleştirilen dizeler, SETEX, EXPIRE ve EXPIREAT komutlarını kullanarak sağlam bir önbellek sistemi oluşturabilir. Bu, veritabanı sorgularının çalıştırılması uzun zaman aldığında ve belirli bir süre için önbelleğe alınabiliyorsa çok kullanışlıdır. Sonuç olarak, bu sorguları çok sık çalıştırmaktan kaçınır ve uygulamalarda performans artışı sağlayabilir.

Redis string veri yapısı ile ilgili daha fazla komuta aşağıdaki url’den ulaşabilirsiniz.

https://redis.io/commands#string

List

Listeler Redis’te çok esnek bir veri türüdür.Basitçe bir collection, stack veya list veri türleri gibi davranabilirler.Redisteki list komutları atomiktir. Bu nedenle birçok event sistemi, redis’in listelerini sıra olarak kullanır.Sebebi ise listelerin işlemleri, eşzamanlı sistemlerin sırayla gelen öğelerin üst üste binmemesidir.Redisteki list veri türü aslında bir linked listtir, bu nedenle O (1) ‘de çalıştırılan bir listenin başından veya sonundan ekler ve siler.

Linked list bu yazının konusu olmadığı için değinmeyeceğiz.Ancak internette yapacağınız arama ile ne olduğu hakkında bilmiyorsanız bilgi edinmenizde fayda vardır.

Redisteki bir listenin sahip olabileceği maksimum öğe sayısı liste başına 4 milyardan fazladır

Kullanılabileceği senaryolar

  • Olay kuyruğu.
  • En son kullanıcı gönderilerini saklama: Twitter bir kullanıcının en son tweet’lerini bir redis listesine kaydeder..

Örnek:

redis 127.0.0.1:6379> lpush user:1:tweets example1 
(integer) 1
redis 127.0.0.1:6379> lpush user:1:tweets example2
(integer) 2
redis 127.0.0.1:6379> lpush user:1:tweets example3
(integer) 3
redis 127.0.0.1:6379> lrange user:1:tweets 0 10

1) "example1"
2) "example2"
3) "example3"

Hash

Benim redis’teki en sevdiğim veri türlerinden olan hash’e geldi sıra.Hash veri türü, nesneleri depolamak için harika bir veri yapısıdır çünkü alanları herhangi bir değer ile eşleyebiliyoruz. Belleği verimli kullanmak ve verileri çok hızlı aramak için en iyi duruma getirilmişlerdir. Bir hash’te, hem key hem de value string veri türündedir.Bu nedenle, bir Hash aslında bir string’in string ile eşlenmesidir.

Örneğin bir detay sayfasında bir makaleyi cachelemek istiyorsak , her bir alanı tek tek az önce gördüğümüz string olarak eklemek yerine veya (json encode edip tek string’e yazmak yerine), makale:1:title , makale:1:content vs gibi bunu tek bir hash’te toplamak çok daha mantıklı ve verimlidir.

Örnek:

HMSET article:1 title "Rediste veri türleri" content 
"Lorem ipsum" created_user "Metin"
redis 127.0.0.1:6379> HGETALL article:1
1) "title"
2) "Rediste veri türleri"
3) "content"
4) "Lorem ipsum"
5) "created_user"
6) "Metin"

Hash’lere sonrasında hgetall komutu ile tamamını veya parametre vererk sadece içerisindeki bir key’e ulaşabilirsiniz.

Hash ile ilgili diğer komutlara aşağıdaki url’den ulaşabilirsiniz.

https://redis.io/commands#hash

Sets

Redis’teki sets veri türünü farklı verilerin sıralanmamış bir koleksiyonu olarak düşünebilirsiniz .Set’e tekrarlanan öğeler eklemek mümkün değildir. Dahili olarak, bir sets, bazı işlemlerin optimize edilmesinin nedeni olan bir hash tablosu olarak uygulanır: O (1) zaman karmaşıklığındaki üyelerin varlığını ekleyebilir, silebilir ve exists yani varmı işlemi yapabilirsiniz.

Örnek:

redis 127.0.0.1:6379> sadd blacklist 192.168.100.50
(integer) 1
redis 127.0.0.1:6379> sadd blacklist 192.168.100.50
(integer) 1
redis 127.0.0.1:6379> sadd blacklist 192.168.100.69
(integer) 1
redis 127.0.0.1:6379> sadd blacklist 192.168.100.10 192.168.100.100
(integer) 1
redis 127.0.0.1:6379> sadd blacklist 192.168.100.10
(integer) 0
redis 127.0.0.1:6379> smembers blacklist

1) "192.168.100.50"
2) "192.168.100.69"
3) "192.168.100.10"

Örnekte gördüğümüz gibi 100.50 ile biten ip adresi 2 kere eklenmesine rağmen listede 1 kere gözükmektedir.

SADD komutu ile arasına boşluk koyarak aynı anda birden fazla veri eklemeside yapabilirsiniz.

Ayrıca yukarıda bahsettiğim gibi SISMEMBER gibi komutlarla list’te eleman varmı diye kolayca sorgulayabilirsiniz.

127.0.0.1:6379> SISMEMBER blacklist 192.168.100.50
(integer) 1

Set’veri türlü ile ilgili farklı komutlar bulunmaktadır.Bu yazıdaki amacım daha basitçe veri yapısını anlatmak istediğim için hepsini örneklemedim. Ancak aşağıdaki url’den tüm komutları denemenizi tavsiye ediyorum.

https://redis.io/commands#set

Sorted Sets

İsmindende anlaşılacağı üzere sorted sets sıralanmış bir set’tir. Set’e benzer, ancak bir kümesinin her bir öğesinin ilişkili bir puanı vardır. Başka bir deyişle, sorted sets, skora göre sıralanan, uniq verilerden oluşan bir koleksiyonudur. Tekrarlanan skorlara sahip elemanlara sahip olmak mümkündür. Bu durumda, tekrarlanan elemanlar alfabetik sırayla sıralanır.

Sıralanan Küme işlemleri hızlıdır ancak Set kadar hızlı değildir, çünkü puanların karşılaştırılması gerekir. Sıralı Kümedeki bir öğenin eklenmesi, çıkarılması ve güncellenmesi, logaritmik zamanda, yani O(Log (N)) ‘de çalışır; burada N, kümedeki öğelerin sayısıdır. Dahili olarak sıralanmış Kümeler iki ayrı veri yapısı olarak uygulanır.

Sorted setsler’e verileri çok hızlı bir şekilde ekleyebilir, kaldırabilir veya güncelleyebilirsiniz. (öğe sayısının logaritmasıyla orantılı bir zamanda). Öğeler sırayla çekildiği ve sonradan sıralanmadığı için, çok hızlı bir şekilde puana göre göre çekebilirsiniz.Bir sorted sets’te ortasına erişim de çok hızlıdır, bu nedenle Sıralı Kümeleri ihtiyacınız olan her şeye hızlı bir şekilde erişebileceğiniz, tekrar etmeyen öğelerin akıllı listesi olarak kullanabilirsiniz: sıralı öğeler, hızlı varlık testi, ortadaki öğelere hızlı erişim !

Örnek:

redis 127.0.0.1:6379> ZADD winners 1 user:1 
(integer) 1
redis 127.0.0.1:6379> ZADD winners 2 user:2
(integer) 1
redis 127.0.0.1:6379> ZADD winners 3 user:3
(integer) 1
redis 127.0.0.1:6379> ZADD winners 3 user:3
(integer) 0
redis 127.0.0.1:6379> ZADD winners 4 user:3
(integer) 0
redis 127.0.0.1:6379> ZRANGE tutorials 0 10 WITHSCORES
1) "user:1"
2) "1"
3) "user:2"
4) "2"
5) "user:3"
6) "4"

Sorted set’te işin içine skorlamada girdiği için oyun , sosyal medya vs gibi etkileşime göre listeleme kısımlarında kullanabilirsiniz.

Ayrıca sorted set ile yapılan bu örneği de inceleyebilirsiniz.

https://keestalkstech.com/2019/04/building-a-high-performing-last-viewed-list-using-redis/

Sorted set’lere ait komutlar listeside aşağıdaki gibidir.

Son olarak yazıyı bitirmeden önce gördüğümüz veri yapılarnın hepsinde geçerli ortak komutlar bulunmaktadır.

  • expire Expire methodu ismindende anlaşılacağı üzerine oluşturduğunuz herhangi bir key’e hangi veri türünde olursa olursun saniye cinsinden bi ttl(time to live) atayacaktır.Parametre olarak verdiğiniz bu saniye süresi dolduğunda belirlediğiniz key silinecektir.
  • del komutu ile oluşturduğunuz herhangi bir key’i anında silebilirsiniz.
  • exists komutu ile bir atadıdığınız key’in var olup olmadığına bakıyoruz.Geriye true ve false değerleri döner.
  • persist daha önce gördüğümüz expire komutu ile key’imize bir yaşama süresi atamıştık.Uygulamadaki senaryonuza göre eğer ttl’i iptal etmek isterseniz persist komutu ile bunu sağlayabilirsiniz.
  • ttlkomutu ile expire ile bir yaşam süresi belirlediğimiz key’in silinmesine kaç saniye kaldığını görebiliyoruz.Eğer expire atanmadı ise -1 atandı ise saniye sini return eder.

Redis’teki temel veri yapılarını ve komutlarını inceledik.Tabiki bununla sınırlı değil. Gelişmiş veri yapıları ve daha farklı komutlar bulunmaktadır. Sonraki yazıda komutları ve diğer veri yapılarını ele almayı planlıyorum.

Okuduğunuz için teşekkürler.Herhangi bir hata/tavsiye bildirmek isterseniz bana profilimden ulaşabilirsiniz.

Teşekkürler…

Kaynaklar

https://keestalkstech.com/2019/04/building-a-high-performing-last-viewed-list-using-redis/

--

--