Redis
 sql >> Cơ Sở Dữ Liệu >  >> NoSQL >> Redis

Giao dịch và xem sao kê trong Redis

Có một số câu hỏi ở đây.

1) Tại sao chúng tôi không thể thực hiện tăng dần trong giao dịch không thể bị gián đoạn bởi lệnh khác?

Trước tiên, xin lưu ý rằng "giao dịch" của Redis hoàn toàn khác với những gì hầu hết mọi người nghĩ rằng giao dịch trong DBMS cổ điển.

# Does not work
redis.multi() 
current = redis.get('powerlevel') 
redis.set('powerlevel', current + 1) 
redis.exec()

Bạn cần hiểu những gì được thực thi ở phía máy chủ (trong Redis) và những gì được thực thi ở phía máy khách (trong tập lệnh của bạn). Trong đoạn mã trên, các lệnh GET và SET sẽ được thực thi ở phía Redis, nhưng việc gán cho hiện tại và tính toán dòng + 1 phải được thực hiện ở phía máy khách.

Để đảm bảo tính nguyên tử, khối MULTI / EXEC trì hoãn việc thực thi các lệnh Redis cho đến khi thực thi. Vì vậy, máy khách sẽ chỉ tích lũy các lệnh GET và SET trong bộ nhớ, và thực hiện chúng trong một lần và cuối cùng là nguyên tử. Tất nhiên, nỗ lực gán hiện tại cho kết quả của GET và tăng dần sẽ xảy ra trước đó. Trên thực tế, phương thức redis.get sẽ chỉ trả về chuỗi "QUEUED" để báo hiệu lệnh bị trì hoãn và quá trình tăng dần sẽ không hoạt động.

Trong các khối MULTI / EXEC, bạn chỉ có thể sử dụng các lệnh mà các tham số của nó có thể được biết đầy đủ trước khi bắt đầu khối. Bạn có thể muốn đọc tài liệu để biết thêm thông tin.

2) Tại sao chúng ta cần lặp lại thay vào đó và đợi cho đến khi không có ai thay đổi giá trị trước khi giao dịch bắt đầu?

Đây là một ví dụ về mô hình lạc quan đồng thời.

Nếu chúng tôi không sử dụng WATCH / MULTI / EXEC, chúng tôi sẽ gặp phải tình trạng chạy đua tiềm năng:

# Initial arbitrary value
powerlevel = 10
session A: GET powerlevel -> 10
session B: GET powerlevel -> 10
session A: current = 10 + 1
session B: current = 10 + 1
session A: SET powerlevel 11
session B: SET powerlevel 11
# In the end we have 11 instead of 12 -> wrong

Bây giờ hãy thêm một khối WATCH / MULTI / EXEC. Với mệnh đề XEM, các lệnh giữa MULTI và EXEC chỉ được thực thi nếu giá trị không thay đổi.

# Initial arbitrary value
powerlevel = 10
session A: WATCH powerlevel
session B: WATCH powerlevel
session A: GET powerlevel -> 10
session B: GET powerlevel -> 10
session A: current = 10 + 1
session B: current = 10 + 1
session A: MULTI
session B: MULTI
session A: SET powerlevel 11 -> QUEUED
session B: SET powerlevel 11 -> QUEUED
session A: EXEC -> success! powerlevel is now 11
session B: EXEC -> failure, because powerlevel has changed and was watched
# In the end, we have 11, and session B knows it has to attempt the transaction again
# Hopefully, it will work fine this time.

Vì vậy, bạn không phải lặp lại để đợi cho đến khi không có ai thay đổi giá trị, mà là thử thao tác lặp đi lặp lại cho đến khi Redis chắc chắn rằng các giá trị là nhất quán và báo hiệu nó thành công.

Trong hầu hết các trường hợp, nếu "giao dịch" đủ nhanh và khả năng xảy ra tranh chấp thấp, thì các bản cập nhật rất hiệu quả. Bây giờ, nếu có tranh cãi, một số hoạt động bổ sung sẽ phải được thực hiện cho một số "giao dịch" (do lặp đi lặp lại và thử lại). Nhưng dữ liệu sẽ luôn nhất quán và không cần khóa.




  1. Redis
  2.   
  3. MongoDB
  4.   
  5. Memcached
  6.   
  7. HBase
  8.   
  9. CouchDB
  1. Làm cách nào để định cấu hình các phiên Spring hoạt động với Redis trong xml?

  2. Sử dụng Redis để lưu kết quả SQL vào bộ nhớ cache

  3. Sự khác biệt giữa Microsoft.Extensions.Cashing.Redis và Microsoft.Extensions.Caching.StackExchangeRedis.RedisCache

  4. Nén trong node.js

  5. Làm thế nào tôi có thể nhận được tất cả các bộ trong redis?