1
2
3
4
5
6
7
8
9
10
11
12
13
14
15 package org.mortbay.cometd;
16
17 import java.io.IOException;
18 import java.io.Reader;
19 import java.util.HashSet;
20 import java.util.List;
21 import java.util.Map;
22
23 import org.cometd.Bayeux;
24 import org.cometd.Message;
25 import org.mortbay.util.ArrayQueue;
26 import org.mortbay.util.StringMap;
27 import org.mortbay.util.ajax.JSON;
28
29
30 public class MessagePool
31 {
32 final private ArrayQueue<MessageImpl> _messagePool;
33 final private ArrayQueue<JSON.ReaderSource> _readerPool;
34
35
36 public MessagePool()
37 {
38 this(50);
39 }
40
41
42 public MessagePool(int capacity)
43 {
44 _messagePool=new ArrayQueue<MessageImpl>(capacity);
45 _readerPool=new ArrayQueue<JSON.ReaderSource>(capacity);
46 }
47
48
49
50
51
52 public JSON getJSON()
53 {
54 return _json;
55 }
56
57
58
59
60
61 public void setJSON(JSON json)
62 {
63 _json=json;
64 }
65
66
67
68
69
70 public JSON getMsgJSON()
71 {
72 return _msgJSON;
73 }
74
75
76
77
78
79 public void setMsgJSON(JSON msgJSON)
80 {
81 _msgJSON=msgJSON;
82 }
83
84
85
86
87
88 public JSON getBatchJSON()
89 {
90 return _batchJSON;
91 }
92
93
94
95
96
97 public void setBatchJSON(JSON batchJSON)
98 {
99 _batchJSON=batchJSON;
100 }
101
102
103
104 public MessageImpl newMessage()
105 {
106 MessageImpl message=_messagePool.poll();
107 if (message==null)
108 message=new MessageImpl(this);
109 message.incRef();
110 return message;
111 }
112
113
114 public MessageImpl newMessage(Message associated)
115 {
116 MessageImpl message=_messagePool.poll();
117 if (message==null)
118 message=new MessageImpl(this);
119 message.incRef();
120 if (associated!=null)
121 message.setAssociated(associated);
122 return message;
123 }
124
125
126 public void recycleMessage(MessageImpl message)
127 {
128 message.clear();
129 _messagePool.offer(message);
130 }
131
132
133 public Message[] parse(Reader reader) throws IOException
134 {
135 JSON.ReaderSource source =_readerPool.poll();
136 if (source==null)
137 source=new JSON.ReaderSource(reader);
138 else
139 source.setReader(reader);
140
141 Object batch=_batchJSON.parse(source);
142 _readerPool.offer(source);
143
144 if (batch==null)
145 return new Message[0];
146 if (batch.getClass().isArray())
147 return (Message[])batch;
148 return new Message[]{(Message)batch};
149 }
150
151
152 public Message[] parse(String s) throws IOException
153 {
154 Object batch=_batchJSON.parse(new JSON.StringSource(s));
155 if (batch==null)
156 return new Message[0];
157 if (batch.getClass().isArray())
158 return (Message[])batch;
159 return new Message[]{(Message)batch};
160 }
161
162
163 public void parseTo(String fodder, List<Message> messages)
164 {
165 Object batch=_batchJSON.parse(new JSON.StringSource(fodder));
166 if (batch==null)
167 return;
168 if (batch.getClass().isArray())
169 {
170 Message[] msgs=(Message[])batch;
171 for (int m=0;m<msgs.length;m++)
172 messages.add(msgs[m]);
173 }
174 else
175 messages.add((Message)batch);
176 }
177
178
179
180 private StringMap _fieldStrings = new StringMap();
181 private StringMap _valueStrings = new StringMap();
182 {
183 _fieldStrings.put(Bayeux.ADVICE_FIELD,Bayeux.ADVICE_FIELD);
184 _fieldStrings.put(Bayeux.CHANNEL_FIELD,Bayeux.CHANNEL_FIELD);
185 _fieldStrings.put(Bayeux.CLIENT_FIELD,Bayeux.CLIENT_FIELD);
186 _fieldStrings.put("connectionType","connectionType");
187 _fieldStrings.put(Bayeux.DATA_FIELD,Bayeux.DATA_FIELD);
188 _fieldStrings.put(Bayeux.ERROR_FIELD,Bayeux.ERROR_FIELD);
189 _fieldStrings.put(Bayeux.EXT_FIELD,Bayeux.EXT_FIELD);
190 _fieldStrings.put(Bayeux.ID_FIELD,Bayeux.ID_FIELD);
191 _fieldStrings.put(Bayeux.SUBSCRIPTION_FIELD,Bayeux.SUBSCRIPTION_FIELD);
192 _fieldStrings.put(Bayeux.SUCCESSFUL_FIELD,Bayeux.SUCCESSFUL_FIELD);
193 _fieldStrings.put(Bayeux.TIMESTAMP_FIELD,Bayeux.TIMESTAMP_FIELD);
194 _fieldStrings.put(Bayeux.TRANSPORT_FIELD,Bayeux.TRANSPORT_FIELD);
195
196 _valueStrings.put(Bayeux.META_CLIENT,Bayeux.META_CLIENT);
197 _valueStrings.put(Bayeux.META_CONNECT,Bayeux.META_CONNECT);
198 _valueStrings.put(Bayeux.META_DISCONNECT,Bayeux.META_DISCONNECT);
199 _valueStrings.put(Bayeux.META_HANDSHAKE,Bayeux.META_HANDSHAKE);
200 _valueStrings.put(Bayeux.META_SUBSCRIBE,Bayeux.META_SUBSCRIBE);
201 _valueStrings.put(Bayeux.META_UNSUBSCRIBE,Bayeux.META_UNSUBSCRIBE);
202 }
203
204
205
206
207 private JSON _json = new JSON()
208 {
209 @Override
210 protected String toString(char[] buffer, int offset, int length)
211 {
212 Map.Entry entry = _valueStrings.getEntry(buffer,offset,length);
213 if (entry!=null)
214 return (String)entry.getValue();
215 String s= new String(buffer,offset,length);
216 return s;
217 }
218 };
219
220
221
222 private JSON _msgJSON = new JSON()
223 {
224 @Override
225 protected Map newMap()
226 {
227 return newMessage();
228 }
229
230 @Override
231 protected String toString(char[] buffer, int offset, int length)
232 {
233 Map.Entry entry = _fieldStrings.getEntry(buffer,offset,length);
234 if (entry!=null)
235 return (String)entry.getValue();
236 String s= new String(buffer,offset,length);
237 return s;
238 }
239
240 @Override
241 protected JSON contextFor(String field)
242 {
243 return _json;
244 }
245 };
246
247
248
249 private JSON _batchJSON = new JSON()
250 {
251 @Override
252 protected Map newMap()
253 {
254 return newMessage();
255 }
256
257 @Override
258 protected Object[] newArray(int size)
259 {
260 return new Message[size];
261 }
262
263 @Override
264 protected JSON contextFor(String field)
265 {
266 return _json;
267 }
268
269 @Override
270 protected JSON contextForArray()
271 {
272 return _msgJSON;
273 }
274 };
275
276 }