1
2
3
4
5
6
7
8
9
10
11
12
13
14
15 package dojox.cometd.demo;
16
17
18 import javax.servlet.ServletContext;
19 import javax.servlet.ServletContextAttributeEvent;
20 import javax.servlet.ServletContextAttributeListener;
21
22 import org.mortbay.cometd.BayeuxService;
23 import org.mortbay.log.Log;
24 import org.mortbay.thread.QueuedThreadPool;
25
26 import dojox.cometd.Bayeux;
27 import dojox.cometd.Client;
28 import dojox.cometd.Listener;
29 import dojox.cometd.Message;
30 import dojox.cometd.MessageListener;
31 import dojox.cometd.RemoveListener;
32
33 import java.util.Map;
34 import java.util.Set;
35 import java.util.concurrent.ConcurrentHashMap;
36 import java.util.concurrent.ConcurrentMap;
37 import java.util.concurrent.CopyOnWriteArraySet;
38
39 public class BayeuxStartupListener implements ServletContextAttributeListener
40 {
41 public void initialize(Bayeux bayeux)
42 {
43 synchronized(bayeux)
44 {
45 if (!bayeux.hasChannel("/service/echo"))
46 {
47 new EchoRPC(bayeux);
48
49
50
51
52 }
53 }
54 }
55
56 public void attributeAdded(ServletContextAttributeEvent scab)
57 {
58 if (scab.getName().equals(Bayeux.DOJOX_COMETD_BAYEUX))
59 {
60 Bayeux bayeux=(Bayeux)scab.getValue();
61 initialize(bayeux);
62 }
63 }
64
65 public void attributeRemoved(ServletContextAttributeEvent scab)
66 {
67
68 }
69
70 public void attributeReplaced(ServletContextAttributeEvent scab)
71 {
72
73 }
74
75
76 public static class EchoRPC extends BayeuxService
77 {
78 public EchoRPC(Bayeux bayeux)
79 {
80 super(bayeux,"echo");
81 subscribe("/service/echo","doEcho");
82 }
83
84 public Object doEcho(Client client, Object data)
85 {
86 Log.info("ECHO from "+client+" "+data);
87 return data;
88 }
89 }
90
91 public static class Monitor extends BayeuxService
92 {
93 public Monitor(Bayeux bayeux)
94 {
95 super(bayeux,"monitor");
96 subscribe("/meta/subscribe","monitorSubscribe");
97 subscribe("/meta/subscribe","monitorUnsubscribe");
98 subscribe("/meta/*","monitorMeta");
99
100 }
101
102 public void monitorSubscribe(Client client, Message message)
103 {
104 Log.info("Subscribe from "+client+" for "+message.get(Bayeux.SUBSCRIPTION_FIELD));
105 }
106
107 public void monitorUnsubscribe(Client client, Message message)
108 {
109 Log.info("Unsubscribe from "+client+" for "+message.get(Bayeux.SUBSCRIPTION_FIELD));
110 }
111
112 public void monitorMeta(Client client, Message message)
113 {
114 if (Log.isDebugEnabled())
115 Log.debug(message.toString());
116 }
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132 }
133
134 public static class ChatService extends BayeuxService
135 {
136 ConcurrentMap<String,Set<String>> _members = new ConcurrentHashMap<String,Set<String>>();
137
138 public ChatService(Bayeux bayeux)
139 {
140 super(bayeux,"chat");
141 subscribe("/chat/**","trackMembers");
142 }
143
144 public void trackMembers(Client joiner,String channel,Map<String,Object> data,String id)
145 {
146 if (Boolean.TRUE.equals(data.get("join")))
147 {
148 Set<String> m = _members.get(channel);
149 if (m==null)
150 {
151 Set<String> new_list=new CopyOnWriteArraySet<String>();
152 m=_members.putIfAbsent(channel,new_list);
153 if (m==null)
154 m=new_list;
155 }
156
157 final Set<String> members=m;
158 final String username=(String)data.get("user");
159
160 members.add(username);
161 joiner.addListener(new RemoveListener(){
162 public void removed(String clientId, boolean timeout)
163 {
164 members.remove(username);
165 }
166 });
167
168 send(joiner,channel,members,id);
169 }
170 }
171 }
172 }