AWS Türkçe Blog
Amazon DynamoDB transactions ile birden çok kayıtta koordineli değişiklikler yapma
Orijinal makale: Link (Baris Yasin ve Serdar Nevruzoglu)
Gittikçe daha fazla kuruluş, NoSQL veritabanlarını, ilişkisel veritabanı yönetim sistemleri (RDBMS) kısıtlamalarından kurtaran çözümler olarak buldukça, NoSQL veritabanlarının kullanımı da son yıllarda önemli ölçüde artmıştır. NoSQL veritabanlarının esnekliği, çevikliği ve performansı; bu yöne geçişi tetikleyen temel avantajlar olarak görülse de, yine de RDBMS’in popülaritesi, kuruluşların bazı önemli gereksinimleri nedeniyle aynı kaldı.
RDBMS’ler, en yaygın bilinen ve üstünde konuşulan özelliği olan transactional desteği nedeni ile, kritik veri işlemleri için genellikle NoSQL veritabanları yerine tercih edilmektedir.
Amazon DynamoDB transactions’u neden kullanmalıyız?
Bazı uygulamalar, genelde bir veya daha fazla öge üzerinde ‘atomik’, yani ya-hep-ya-hiç denilen bir veritabanı işlemi gerektiren mantığı takip etmeye ihtiyaç duyar. Bu mantık, herhangi bir hatalı işlem durumunda, yapılan tüm veritabanı işlemlerini geriye alma anlamına gelir. Bu ihtiyacı yerine getirmek, bağlı tüm işlemleri takip etmek ve buna göre tersine çevirmek demek olduğundan, genellikle uygulama geliştirmesini zorlaştırmaktadır.
Transactions, DynamoDB‘nin yeni bir özelliği olarak re:Invent 2018’de duyuruldu. Tek bir AWS hesabı ve bir Bölge’deki birden çok öğeye ACID (atomiklik, tutarlılık, izolasyon, dayanıklılık) özellikleri verebilmek için, veritabanı içindeki işlemlerde kendinden bir destek sağlar.
Daha önceden DynamoDB bu özellikleri yalnızca tek bir öge için desteklemekteydi. Verilerin erişilebilirliğini ve dayanıklılığını sağlamak için böyle tasarlanmıştı. Transactions; birden fazla ögede, bir veya daha fazla tablo için atomiklik (ya-hep-ya-hiç) ve izolasyon (birbirini etkilemeyen işlemler) desteği ekledi.
Ayrıca, transactions ClientRequestToken anahtarı, API isteklerinin eşgüçlü (idempotent) olmasını sağlar. Böylece birden çok özdeş istek, aynı işlemi tekrarlamaz ve tek bir istek ile aynı etkiyi yapar.
Transactions ile artık veritabanı içindeki geri alma işlemleri için endişelenmenize veya onlarla uğraşmanıza gerek yok. Transactions, birden çok öge ve tablodaki eylemleri koordine ederek veri bütünlüğünü korumanıza yardımcı olur.
Nasıl çalışır
DynamoDB transactions, TransactWriteItems ve TransactGetItems diye adlandırılan iki temel API eylemi sunuyor. Bu sayede, birkaç eylemi birleştirebilir ve bunları tek bir ya-hep-ya-hiç işlemi olarak gönderebilirsiniz.
Örneğin, otelinizin rezervasyon yönetimi uygulamasını ilişkisel bir veritabanından DynamoDB’ye taşımaya karar verdiniz. Aşağıdaki şema ER yapınızı temsil eder. Diyagramda, 3 birim var: Misafir, Rezervasyon ve Oda. Misafir ve Rezervasyon arasında çoktan çoka (many-to-many) bir ilişki ve ayrıca Rezervasyon ile Oda arasında da çoktan çoka bir ilişki bulunuyor.
Burada heterojen tablo yaklaşımını uyguluyoruz ve üç eski tabloyu tek bir DynamoDB tablosunda eşliyoruz. DynamoDB’deki örnek verilerle birlikte otel rezervasyonu veri modeli aşağıdaki tabloda bulunmakta.
HotelManagement | Record Type | Id (PK) | Attributes |
Guest | “John” | ActiveReservations : { “501” } OccupiesRooms : { “20014” } |
|
Reservation | “501” | GuestId: “John” ReservationStatus: “FULFILLED” FulfilledByRoom: “20014” |
|
Room | “R20014” | RoomStatus: “OCCUPIED” RentedToReservation : “501” |
Örnek kod
Misafirler üç çeşit işlem yapabiliyor: rezervasyon oluşturma, check in, ve check out. Bu makalede, DynamoDB’nin işlemsel yeteneklerini gösterme amaçlı olarak, aşağıdaki şemadaki biçimiyle, üç farklı Java metoduna konulmuş üç senaryo var. Kullanıcı sıralı olarak üç işlemi gerçekleştirebiliyor. Birincisi Create reservation (Rezervasyon oluştur), ikincisi Check-in ve üçüncüsü de Check-out.
İlk olarak, üstünde çalışabileceğiniz bir tablo oluşturmalısınız.
Rezervasyon oluşturma
Ardından, sistemde örnek bir rezervasyonu temsil eden bir dizi kayıt oluşturun.
Create reservation işleminden sonra tablomuz aşağıdaki gibi.
HotelManagement | Record Type | Id (PK) | Attributes |
Guest | “John” | ActiveReservations : { “500”} OccupiesRooms : null |
|
Reservation | “500” | GuestId: “John” ReservationStatus: “PENDING” FulfilledByRoom: null |
|
Room | “R20014” | RoomStatus: “FREE” RentedToReservation : null |
Check-in
Bir sonraki işlemse Check-in. Bu işlem sırasında tablodaki üç öge (Misafir, Rezervasyon ve Oda) güncellenir.
Check-in işleminin ardından tablomuzun durumu da aşağıda görülmektedir.
HotelManagement | Record Type | Id (PK) | Attributes |
Guest | “John” | ActiveReservations : { “500”} OccupiesRooms : { “R20014” } |
|
Reservation | “500” | GuestId: “John” ReservationStatus: “FULFILLED” FulfilledByRoom: “20014” |
|
Room | “R20014” | RoomStatus: “OCCUPIED” RentedToReservation : “500” |
Check-out
Son işlem de Check-out. DynamoDB’de null veya boş bölümlere izin verilmediğinden, bazı nitelikleri de kaldıralım.
Check-out işleminden sonraki tablo da aşağıda gösterilmiştir.
HotelManagement | Record Type | Id (PK) | Attributes |
Guest | “John” | ActiveReservations : {} | |
Reservation | “500” | GuestId: “John” ReservationStatus: “CLOSED” FulfilledByRoom: “20014” |
|
Room | “R20014” | RoomStatus: “FREE” |
Sonuç
DynamoDB transactional API’leri, herhangi bir DynamoDB tablosundaki herhangi bir öge için ek ücret ödemeden ACID desteği sağlayarak geliştirme deneyimini basitleştirir. Transactions varsayılan olarak tüm single-region DynamoDB tabloları için aktiftir ve isteğe bağlı olarak da global tablolarda etkinleştirilebilir. Bağlı veritabanı işlemleri için uzun süredir bulunan ihtiyaca cevap vererek, DynamoDB’nin ölçeğini, performansını ve ticari kullanıma hazır olan avantajlarını daha geniş bir iş yüküne de genişletecektir.
Transactions ile ilgili daha fazla bilgiyi Amazon DynamoDB Geliştirici Kılavuzu‘nda bulabilirsiniz.