1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24 package net.sf.stax;
25
26 import java.util.Map;
27 import java.util.HashMap;
28
29 import org.xml.sax.Attributes;
30 import org.xml.sax.SAXException;
31
32 /***
33 * On-element dispatch.
34 *
35 * <p>Select from one of the concrete subclasses <b>ByNsURI</b>,
36 * <b>ByLocalName</b>, or <b>ByQName</b>.</p>
37 *
38 * @see DispatchOnElement.ByNsURI
39 * @see DispatchOnElement.ByLocalName
40 * @see DispatchOnElement.ByQName
41 *
42 * @author Thomas Down
43 * @author Matthew Pocock
44 * @author Michael Heuer
45 * @version $Revision: 1.2 $ $Date: 2006/01/02 20:37:34 $
46 */
47 public abstract class DispatchOnElement
48 extends StAXContentHandlerBase
49 {
50 /*** Return value. */
51 private Object retVal;
52
53 /*** Map of names to handlers. */
54 private Map nameToHandler;
55
56 /*** Default handler. */
57 private StAXContentHandler defaultHandler;
58
59
60 /***
61 * Create a new on-element dispatch.
62 */
63 protected DispatchOnElement()
64 {
65 nameToHandler = new HashMap();
66 }
67
68
69 /***
70 * Choose a handler for the specified namespace URI, local
71 * name, and qualified XML name.
72 *
73 * @param nsURI namespace URI
74 * @param localName local name (without prefix)
75 * @param qName qualified XML name (with prefix)
76 * @return a handler for the specified namespare URI, local
77 * name, and qualified XML name
78 * @throws SAXException any SAX exception, possibly wrapping another exception
79 */
80 protected abstract StAXContentHandler chooseHandler(final String nsURI,
81 final String localName,
82 final String qName)
83 throws SAXException;
84
85 /*** @see StAXContentHandlerBase */
86 public final void startElement(final String nsURI,
87 final String localName,
88 final String qName,
89 final Attributes attrs,
90 final StAXDelegationContext dctx)
91 throws SAXException
92 {
93 StAXContentHandler handler = chooseHandler(nsURI, localName, qName);
94
95 if (handler == null)
96 {
97 handler = defaultHandler;
98 }
99 if (handler == null)
100 {
101 throw new SAXException(this + " Can't find handler for " + nsURI + " " + localName
102 + " " + qName + " among " + nameToHandler.keySet());
103 }
104 else
105 {
106 dctx.delegate(handler);
107 }
108 }
109
110 /*** @see StAXContentHandlerBase */
111 public final void endElement(final String nsURI,
112 final String localName,
113 final String qName,
114 final Object retVal,
115 final StAXContext ctx)
116 throws SAXException
117 {
118 this.retVal = retVal;
119 }
120
121 /*** @see StAXContentHandlerBase */
122 public final Object endTree(final StAXContext ctx)
123 {
124 return retVal;
125 }
126
127 /***
128 * Add the specified named handler.
129 *
130 * @param name name
131 * @param handler handler
132 */
133 public final void setHandler(final String name, final StAXContentHandler handler)
134 {
135 nameToHandler.put(name, handler);
136 }
137
138 /***
139 * Set the default handler for this on-element dispatch
140 * to <code>handler</code>.
141 *
142 * @param handler default handler
143 */
144 public final void setDefaultHandler(final StAXContentHandler handler)
145 {
146 this.defaultHandler = handler;
147 }
148
149 /***
150 * Return the default handler for this on-element dispatch.
151 *
152 * @return the default handler for this on-element dispatch
153 */
154 public final StAXContentHandler getDefaultHandler()
155 {
156 return defaultHandler;
157 }
158
159 /***
160 * Return the handler associated with the specified name.
161 *
162 * @param name name
163 * @return the handler associated with the specified name
164 */
165 public final StAXContentHandler getHandler(final String name)
166 {
167 return (StAXContentHandler) nameToHandler.get(name);
168 }
169
170
171 /***
172 * On-element dispatch that chooses handlers by namespace URI.
173 *
174 * <p>This class replaces
175 * <pre>
176 * class FooHandler
177 * extends StAXContentHandlerBase
178 * {
179 * public void startElement(..., StAXDelegationContext dctx)
180 * {
181 * if ("urn:net.sf.stax:bar".equals(nsURI))
182 * {
183 * dctx.delegate(barHandler);
184 * }
185 * else if ("urn:net.sf.stax:baz".equals(nsURI))
186 * {
187 * dctx.delegate.(bazHandler);
188 * }
189 * }
190 * }
191 * </pre>
192 * with
193 * <pre>
194 * DispatchOnElement dispatch = new DispatchOnElement.ByNsURI();
195 * dispatch.setHandler("urn:net.sf.stax:bar", barHandler);
196 * dispatch.setHandler("urn:net.sf.stax:baz", bazHandler);
197 * </pre></p>
198 */
199 public static final class ByNsURI
200 extends DispatchOnElement
201 {
202
203 /*** @see DispatchOnElement */
204 protected StAXContentHandler chooseHandler(final String nsURI,
205 final String localName,
206 final String qName)
207 throws SAXException
208 {
209 return getHandler(nsURI);
210 }
211 }
212
213 /***
214 * On-element dispatch that chooses handlers by local name.
215 *
216 * <p>This class replaces
217 * <pre>
218 * class FooHandler
219 * extends StAXContentHandlerBase
220 * {
221 * public void startElement(..., StAXDelegationContext dctx)
222 * {
223 * if ("bar".equals(localName))
224 * {
225 * dctx.delegate(barHandler);
226 * }
227 * else if ("baz".equals(localName))
228 * {
229 * dctx.delegate.(bazHandler);
230 * }
231 * }
232 * }
233 * </pre>
234 * with
235 * <pre>
236 * DispatchOnElement dispatch = new DispatchOnElement.ByLocalName();
237 * dispatch.setHandler("bar", barHandler);
238 * dispatch.setHandler("baz", bazHandler);
239 * </pre></p>
240 */
241 public static final class ByLocalName
242 extends DispatchOnElement
243 {
244
245 /*** @see DispatchOnElement */
246 protected StAXContentHandler chooseHandler(final String nsURI,
247 final String localName,
248 final String qName)
249 throws SAXException
250 {
251 return getHandler(localName);
252 }
253 }
254
255 /***
256 * On-element dispatch that chooses handlers by qualified XML name.
257 *
258 * <p>This class replaces
259 * <pre>
260 * class FooHandler
261 * extends StAXContentHandlerBase
262 * {
263 * public void startElement(..., StAXDelegationContext dctx)
264 * {
265 * if ("bar".equals(qName))
266 * {
267 * dctx.delegate(barHandler);
268 * }
269 * else if ("baz".equals(qName))
270 * {
271 * dctx.delegate.(bazHandler);
272 * }
273 * }
274 * }
275 * </pre>
276 * with
277 * <pre>
278 * DispatchOnElement dispatch = new DispatchOnElement.ByQName();
279 * dispatch.setHandler("bar", barHandler);
280 * dispatch.setHandler("baz", bazHandler);
281 * </pre></p>
282 */
283 public static final class ByQName
284 extends DispatchOnElement
285 {
286
287 /*** @see DispatchOnElement */
288 protected StAXContentHandler chooseHandler(final String nsURI,
289 final String localName,
290 final String qName)
291 throws SAXException
292 {
293 return getHandler(qName);
294 }
295 }
296 }