iT邦幫忙

0

推薦符合創讀改刪 (CRUD, Create/Read/Update/Delete)、分散式鍵值儲存庫?

  • 分享至 

  • xImage

Hi,

敝人使用node.js+socket.io由多人多間網路聊天室開始建立遊戲系統。一開始存放房間設定(例如:用戶列表、可否加入、最多幾人等等)是使用JavaScript物件寫的,而這種做法在多服務器負載均衡下會出問題。曾經考慮過memcache,發現它無法進行修改操作(協定只有set/del...,不支援update)。redis也不適用,理由與memcache同。其他的要不慢了一點(e.g. MySQL -- 有人加入或離開房間都要query一次,不是速度挺慢的嗎?)、要不無法輕易伸縮。故請推薦符合創讀改刪、分散式鍵值儲存庫。

另,有甚麼第三方開源軟件可以套在memcache前面讓它支援CRUD的也行。不想輕易放棄memcache的原因是Amazon ElastiCache。

就 redis 而言,把 update 想成
SMOVE 到不同的 set,
或者有時間方面的限定,expire key 也算是一種的 update 操作;
如果我想得太簡單的話。
zanhsieh iT邦新手 4 級 ‧ 2012-04-26 09:46:36 檢舉
key 改不動 (也許您可以建議更好的資料結構)。代碼在:
http://pastebin.com/SjHHhntH
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

1 個回答

4
逮丸逮丸
iT邦大師 1 級 ‧ 2012-04-26 11:49:42
最佳解答

也許用 key-value 時 value 的部份,
不要放那麼多 要更動 的資料,
若是放 hash 通常只是用來讀出來而已。

用 redis 來模擬會類似這樣子操作:

初始化一個room

<pre class="c" name="code">sadd game:init poker:token:ABCDEFGHI
set poker:token:ABCDEFGHI someinfo
expire poker:token:ABCDEFGHI 30000
set poker:token:ABCDEFGHI:slots 4

因為 poker:token:ABCDEFGHI 超過時間 expire 掉,
key 會不見,系統裡會留一些 poker:token:ABCDEFGHI:* 的key,
所以要 game:init 的目的,
就是去掃 poker:token:ABCDEFGHI 這 key 在不在,
不在的話,把 poker:token:ABCDEFGHI:* 給清掉。
slots 數目、 users 拉出來各成個 key。

一個user加入時,加入到list並更動slots數(如果一個user佔一個slot的話):
<pre class="c" name="code">sadd poker:token:ABCDEFGHI:users user1
decr poker:token:ABCDEFGHI:slots

在 poker:token:ABCDEFGHI 未 expire 且 poker:token:ABCDEFGHI:slots 是 0 時,

&lt;pre class="c" name="code">smove game:init game:start

如果要知道 poker:token:ABCDEFGHI 剩多少時間:

&lt;pre class="c" name="code">ttl poker:token:ABCDEFGHI

這種會用到因時間而區分狀態的情況,
就會利用 redis 裡的 Sets, expire, incr, decr 的特性。

看更多先前的回應...收起先前的回應...
zanhsieh iT邦新手 4 級 ‧ 2012-04-26 16:58:56 檢舉

@twtw: 其實快速變化的部分有兩個,一個是用戶有意/無意的斷線;另一個是記分板 (poker 可能不是太好的例子,問答遊戲可能就影響到部分的記分板)。不曉得您的看法如何?

如果要偵測user是否斷線,一個user的session為一key:

&lt;pre class="c" name="code">expire user:user1:sesion:xxxxx 120

有任何動作都作這個動作。
只要超過兩分鐘沒作到這動作,key會消失掉就算斷線。

分數也可設這樣的 key 來做累計:

&lt;pre class="c" name="code">incrby user:user1:sesion:xxxxx:score 5

若要同時做該 user 的有史以來的總累計可再加上:

&lt;pre class="c" name="code">incrby user:user1:total:score 5

當然這些是 score 是在線時在 redis 裡進行,
離線後 redis 仍存有一堆資料,
那時可再看若太大量久未存取變動的score資料,
再選擇放到傳統的資料庫裡。
user上線,再拉到redis做累計。

zanhsieh iT邦新手 4 級 ‧ 2012-04-27 10:41:42 檢舉

@twtw:那redis如何在Amazon AWS達成分散式架構?

目前自己未用到數據大量的情況,
而欠缺相關的經驗。
而 redis 目前最多只有 replication 主從架構,
cluster 還只有規格而已 Redis cluster Specification (work in progress)
雖然如此,仍有用 Scale redis 的例子:
1,000,000 daily users and no cache
新浪微博開放平台redis實踐

這篇也提了怎麼擴展的方式:
Scaling Redis

我要發表回答

立即登入回答