想不到redis會(huì)提供pub/sub功能土陪。消息訂閱發(fā)布模式就不說(shuō)了,跟觀察者模式很接近。
redis 作為一個(gè)publish/subscribe server罗捎,起到了消息路由的功能。訂閱者可以通過(guò)subscribe和psubscribe命令向redis server訂閱自己感興趣的消息類(lèi)型拉盾,當(dāng)發(fā)布者通過(guò)publish命令向redis server發(fā)送特定類(lèi)型的消息時(shí)。訂閱該消息類(lèi)型的全部client都會(huì)收到此消息。這里消息的傳遞是多對(duì)多的巢价。一個(gè)client可以訂閱多個(gè)channel,也可以向多個(gè)channel發(fā)送消息农渊。
下面用代碼做一下試驗(yàn)。采用的是jedis客戶端夭禽,代碼如下
public class PubSubTest extends JedisPubSub {
@Override
public void onMessage(String channel, String message) {
// TODO Auto-generated method stub
super.onMessage(channel, message);
System.out.println("收到渠道為"+channel+"的消息:"+message);
}
@Override
public void onSubscribe(String channel, int subscribedChannels) {
// TODO Auto-generated method stub
super.onSubscribe(channel, subscribedChannels);
System.out.println("訂閱渠道"+channel);
}
@Override
public void onUnsubscribe(String channel, int subscribedChannels) {
// TODO Auto-generated method stub
super.onUnsubscribe(channel, subscribedChannels);
System.out.println("取消訂閱渠道"+channel);
}
}
代碼解讀霞掺,創(chuàng)建一個(gè)類(lèi),繼承自JedisPubSub讹躯,這是jedis中實(shí)現(xiàn)pub/sub的類(lèi)菩彬。該類(lèi)中會(huì)有一些方法需要重寫(xiě)。比如onMessage潮梯,收到訂閱消息時(shí)會(huì)調(diào)用該類(lèi)中的方法骗灶。onSubscribe,訂閱某個(gè)渠道時(shí)秉馏,會(huì)調(diào)用該方法矿卑。onUnsubscribe,取消訂閱某個(gè)渠道時(shí)沃饶,調(diào)用該方法母廷。
然后在main方法里面調(diào)用以下代碼
jedis=new Jedis("localhost");
PubSubTest test=new PubSubTest();
jedis.subscribe(test, "cctv5");
這段代碼很簡(jiǎn)單,就是訂閱名稱(chēng)為cctv5的渠道糊肤。當(dāng)我在其他客戶端publish消息時(shí)琴昆,就會(huì)觸發(fā)onMessage方法。
看完這個(gè)小例子后應(yīng)該對(duì)pub/sub功能有了一個(gè)感性的認(rèn)識(shí)馆揉。需要注意的是當(dāng)一個(gè)連接通過(guò)subscribe或者psubscribe訂閱通道后就進(jìn)入訂閱模式业舍。在這種模式除了再訂閱額外的通道或者用unsubscribe或者punsubscribe命令退出訂閱模式,就不能再發(fā)送其他命令。另外使用psubscribe命令訂閱多個(gè)通配符通道舷暮,如果一個(gè)消息匹配上了多個(gè)通道模式的話态罪,會(huì)多次收到同一個(gè)消息。
redis的pub/sub還是有點(diǎn)太單毕旅妗(實(shí)現(xiàn)才用150行代碼)复颈。在安全,認(rèn)證沥割,可靠性這方便都沒(méi)有太多支持耗啦。