1
2
3
4
5
6
7 package org.xml.sax.helpers;
8
9 import java.io.IOException;
10
11 import org.xml.sax.XMLReader;
12 import org.xml.sax.XMLFilter;
13 import org.xml.sax.InputSource;
14 import org.xml.sax.Locator;
15 import org.xml.sax.Attributes;
16 import org.xml.sax.EntityResolver;
17 import org.xml.sax.DTDHandler;
18 import org.xml.sax.ContentHandler;
19 import org.xml.sax.ErrorHandler;
20 import org.xml.sax.SAXException;
21 import org.xml.sax.SAXParseException;
22 import org.xml.sax.SAXNotSupportedException;
23 import org.xml.sax.SAXNotRecognizedException;
24
25
26 /***
27 * Base class for deriving an XML filter.
28 *
29 * <blockquote>
30 * <em>This module, both source code and documentation, is in the
31 * Public Domain, and comes with <strong>NO WARRANTY</strong>.</em>
32 * See <a href='http://www.saxproject.org'>http://www.saxproject.org</a>
33 * for further information.
34 * </blockquote>
35 *
36 * <p>This class is designed to sit between an {@link org.xml.sax.XMLReader
37 * XMLReader} and the client application's event handlers. By default, it
38 * does nothing but pass requests up to the reader and events
39 * on to the handlers unmodified, but subclasses can override
40 * specific methods to modify the event stream or the configuration
41 * requests as they pass through.</p>
42 *
43 * @since SAX 2.0
44 * @author David Megginson
45 * @version 2.0.1 (sax2r2)
46 * @see org.xml.sax.XMLFilter
47 * @see org.xml.sax.XMLReader
48 * @see org.xml.sax.EntityResolver
49 * @see org.xml.sax.DTDHandler
50 * @see org.xml.sax.ContentHandler
51 * @see org.xml.sax.ErrorHandler
52 */
53 public class XMLFilterImpl
54 implements XMLFilter, EntityResolver, DTDHandler, ContentHandler, ErrorHandler
55 {
56
57
58
59
60
61
62
63 /***
64 * Construct an empty XML filter, with no parent.
65 *
66 * <p>This filter will have no parent: you must assign a parent
67 * before you start a parse or do any configuration with
68 * setFeature or setProperty, unless you use this as a pure event
69 * consumer rather than as an {@link XMLReader}.</p>
70 *
71 * @see org.xml.sax.XMLReader#setFeature
72 * @see org.xml.sax.XMLReader#setProperty
73 * @see #setParent
74 */
75 public XMLFilterImpl ()
76 {
77 super();
78 }
79
80
81 /***
82 * Construct an XML filter with the specified parent.
83 *
84 * @see #setParent
85 * @see #getParent
86 */
87 public XMLFilterImpl (XMLReader parent)
88 {
89 super();
90 setParent(parent);
91 }
92
93
94
95
96
97
98
99
100 /***
101 * Set the parent reader.
102 *
103 * <p>This is the {@link org.xml.sax.XMLReader XMLReader} from which
104 * this filter will obtain its events and to which it will pass its
105 * configuration requests. The parent may itself be another filter.</p>
106 *
107 * <p>If there is no parent reader set, any attempt to parse
108 * or to set or get a feature or property will fail.</p>
109 *
110 * @param parent The parent XML reader.
111 * @see #getParent
112 */
113 public void setParent (XMLReader parent)
114 {
115 this.parent = parent;
116 }
117
118
119 /***
120 * Get the parent reader.
121 *
122 * @return The parent XML reader, or null if none is set.
123 * @see #setParent
124 */
125 public XMLReader getParent ()
126 {
127 return parent;
128 }
129
130
131
132
133
134
135
136
137 /***
138 * Set the value of a feature.
139 *
140 * <p>This will always fail if the parent is null.</p>
141 *
142 * @param name The feature name.
143 * @param value The requested feature value.
144 * @exception org.xml.sax.SAXNotRecognizedException If the feature
145 * value can't be assigned or retrieved from the parent.
146 * @exception org.xml.sax.SAXNotSupportedException When the
147 * parent recognizes the feature name but
148 * cannot set the requested value.
149 */
150 public void setFeature (String name, boolean value)
151 throws SAXNotRecognizedException, SAXNotSupportedException
152 {
153 if (parent != null) {
154 parent.setFeature(name, value);
155 } else {
156 throw new SAXNotRecognizedException("Feature: " + name);
157 }
158 }
159
160
161 /***
162 * Look up the value of a feature.
163 *
164 * <p>This will always fail if the parent is null.</p>
165 *
166 * @param name The feature name.
167 * @return The current value of the feature.
168 * @exception org.xml.sax.SAXNotRecognizedException If the feature
169 * value can't be assigned or retrieved from the parent.
170 * @exception org.xml.sax.SAXNotSupportedException When the
171 * parent recognizes the feature name but
172 * cannot determine its value at this time.
173 */
174 public boolean getFeature (String name)
175 throws SAXNotRecognizedException, SAXNotSupportedException
176 {
177 if (parent != null) {
178 return parent.getFeature(name);
179 } else {
180 throw new SAXNotRecognizedException("Feature: " + name);
181 }
182 }
183
184
185 /***
186 * Set the value of a property.
187 *
188 * <p>This will always fail if the parent is null.</p>
189 *
190 * @param name The property name.
191 * @param value The requested property value.
192 * @exception org.xml.sax.SAXNotRecognizedException If the property
193 * value can't be assigned or retrieved from the parent.
194 * @exception org.xml.sax.SAXNotSupportedException When the
195 * parent recognizes the property name but
196 * cannot set the requested value.
197 */
198 public void setProperty (String name, Object value)
199 throws SAXNotRecognizedException, SAXNotSupportedException
200 {
201 if (parent != null) {
202 parent.setProperty(name, value);
203 } else {
204 throw new SAXNotRecognizedException("Property: " + name);
205 }
206 }
207
208
209 /***
210 * Look up the value of a property.
211 *
212 * @param name The property name.
213 * @return The current value of the property.
214 * @exception org.xml.sax.SAXNotRecognizedException If the property
215 * value can't be assigned or retrieved from the parent.
216 * @exception org.xml.sax.SAXNotSupportedException When the
217 * parent recognizes the property name but
218 * cannot determine its value at this time.
219 */
220 public Object getProperty (String name)
221 throws SAXNotRecognizedException, SAXNotSupportedException
222 {
223 if (parent != null) {
224 return parent.getProperty(name);
225 } else {
226 throw new SAXNotRecognizedException("Property: " + name);
227 }
228 }
229
230
231 /***
232 * Set the entity resolver.
233 *
234 * @param resolver The new entity resolver.
235 */
236 public void setEntityResolver (EntityResolver resolver)
237 {
238 entityResolver = resolver;
239 }
240
241
242 /***
243 * Get the current entity resolver.
244 *
245 * @return The current entity resolver, or null if none was set.
246 */
247 public EntityResolver getEntityResolver ()
248 {
249 return entityResolver;
250 }
251
252
253 /***
254 * Set the DTD event handler.
255 *
256 * @param resolver The new DTD handler.
257 */
258 public void setDTDHandler (DTDHandler handler)
259 {
260 dtdHandler = handler;
261 }
262
263
264 /***
265 * Get the current DTD event handler.
266 *
267 * @return The current DTD handler, or null if none was set.
268 */
269 public DTDHandler getDTDHandler ()
270 {
271 return dtdHandler;
272 }
273
274
275 /***
276 * Set the content event handler.
277 *
278 * @param resolver The new content handler.
279 */
280 public void setContentHandler (ContentHandler handler)
281 {
282 contentHandler = handler;
283 }
284
285
286 /***
287 * Get the content event handler.
288 *
289 * @return The current content handler, or null if none was set.
290 */
291 public ContentHandler getContentHandler ()
292 {
293 return contentHandler;
294 }
295
296
297 /***
298 * Set the error event handler.
299 *
300 * @param handle The new error handler.
301 */
302 public void setErrorHandler (ErrorHandler handler)
303 {
304 errorHandler = handler;
305 }
306
307
308 /***
309 * Get the current error event handler.
310 *
311 * @return The current error handler, or null if none was set.
312 */
313 public ErrorHandler getErrorHandler ()
314 {
315 return errorHandler;
316 }
317
318
319 /***
320 * Parse a document.
321 *
322 * @param input The input source for the document entity.
323 * @exception org.xml.sax.SAXException Any SAX exception, possibly
324 * wrapping another exception.
325 * @exception java.io.IOException An IO exception from the parser,
326 * possibly from a byte stream or character stream
327 * supplied by the application.
328 */
329 public void parse (InputSource input)
330 throws SAXException, IOException
331 {
332 setupParse();
333 parent.parse(input);
334 }
335
336
337 /***
338 * Parse a document.
339 *
340 * @param systemId The system identifier as a fully-qualified URI.
341 * @exception org.xml.sax.SAXException Any SAX exception, possibly
342 * wrapping another exception.
343 * @exception java.io.IOException An IO exception from the parser,
344 * possibly from a byte stream or character stream
345 * supplied by the application.
346 */
347 public void parse (String systemId)
348 throws SAXException, IOException
349 {
350 parse(new InputSource(systemId));
351 }
352
353
354
355
356
357
358
359
360 /***
361 * Filter an external entity resolution.
362 *
363 * @param publicId The entity's public identifier, or null.
364 * @param systemId The entity's system identifier.
365 * @return A new InputSource or null for the default.
366 * @exception org.xml.sax.SAXException The client may throw
367 * an exception during processing.
368 * @exception java.io.IOException The client may throw an
369 * I/O-related exception while obtaining the
370 * new InputSource.
371 */
372 public InputSource resolveEntity (String publicId, String systemId)
373 throws SAXException, IOException
374 {
375 if (entityResolver != null) {
376 return entityResolver.resolveEntity(publicId, systemId);
377 } else {
378 return null;
379 }
380 }
381
382
383
384
385
386
387
388
389 /***
390 * Filter a notation declaration event.
391 *
392 * @param name The notation name.
393 * @param publicId The notation's public identifier, or null.
394 * @param systemId The notation's system identifier, or null.
395 * @exception org.xml.sax.SAXException The client may throw
396 * an exception during processing.
397 */
398 public void notationDecl (String name, String publicId, String systemId)
399 throws SAXException
400 {
401 if (dtdHandler != null) {
402 dtdHandler.notationDecl(name, publicId, systemId);
403 }
404 }
405
406
407 /***
408 * Filter an unparsed entity declaration event.
409 *
410 * @param name The entity name.
411 * @param publicId The entity's public identifier, or null.
412 * @param systemId The entity's system identifier, or null.
413 * @param notationName The name of the associated notation.
414 * @exception org.xml.sax.SAXException The client may throw
415 * an exception during processing.
416 */
417 public void unparsedEntityDecl (String name, String publicId,
418 String systemId, String notationName)
419 throws SAXException
420 {
421 if (dtdHandler != null) {
422 dtdHandler.unparsedEntityDecl(name, publicId, systemId,
423 notationName);
424 }
425 }
426
427
428
429
430
431
432
433
434 /***
435 * Filter a new document locator event.
436 *
437 * @param locator The document locator.
438 */
439 public void setDocumentLocator (Locator locator)
440 {
441 this.locator = locator;
442 if (contentHandler != null) {
443 contentHandler.setDocumentLocator(locator);
444 }
445 }
446
447
448 /***
449 * Filter a start document event.
450 *
451 * @exception org.xml.sax.SAXException The client may throw
452 * an exception during processing.
453 */
454 public void startDocument ()
455 throws SAXException
456 {
457 if (contentHandler != null) {
458 contentHandler.startDocument();
459 }
460 }
461
462
463 /***
464 * Filter an end document event.
465 *
466 * @exception org.xml.sax.SAXException The client may throw
467 * an exception during processing.
468 */
469 public void endDocument ()
470 throws SAXException
471 {
472 if (contentHandler != null) {
473 contentHandler.endDocument();
474 }
475 }
476
477
478 /***
479 * Filter a start Namespace prefix mapping event.
480 *
481 * @param prefix The Namespace prefix.
482 * @param uri The Namespace URI.
483 * @exception org.xml.sax.SAXException The client may throw
484 * an exception during processing.
485 */
486 public void startPrefixMapping (String prefix, String uri)
487 throws SAXException
488 {
489 if (contentHandler != null) {
490 contentHandler.startPrefixMapping(prefix, uri);
491 }
492 }
493
494
495 /***
496 * Filter an end Namespace prefix mapping event.
497 *
498 * @param prefix The Namespace prefix.
499 * @exception org.xml.sax.SAXException The client may throw
500 * an exception during processing.
501 */
502 public void endPrefixMapping (String prefix)
503 throws SAXException
504 {
505 if (contentHandler != null) {
506 contentHandler.endPrefixMapping(prefix);
507 }
508 }
509
510
511 /***
512 * Filter a start element event.
513 *
514 * @param uri The element's Namespace URI, or the empty string.
515 * @param localName The element's local name, or the empty string.
516 * @param qName The element's qualified (prefixed) name, or the empty
517 * string.
518 * @param atts The element's attributes.
519 * @exception org.xml.sax.SAXException The client may throw
520 * an exception during processing.
521 */
522 public void startElement (String uri, String localName, String qName,
523 Attributes atts)
524 throws SAXException
525 {
526 if (contentHandler != null) {
527 contentHandler.startElement(uri, localName, qName, atts);
528 }
529 }
530
531
532 /***
533 * Filter an end element event.
534 *
535 * @param uri The element's Namespace URI, or the empty string.
536 * @param localName The element's local name, or the empty string.
537 * @param qName The element's qualified (prefixed) name, or the empty
538 * string.
539 * @exception org.xml.sax.SAXException The client may throw
540 * an exception during processing.
541 */
542 public void endElement (String uri, String localName, String qName)
543 throws SAXException
544 {
545 if (contentHandler != null) {
546 contentHandler.endElement(uri, localName, qName);
547 }
548 }
549
550
551 /***
552 * Filter a character data event.
553 *
554 * @param ch An array of characters.
555 * @param start The starting position in the array.
556 * @param length The number of characters to use from the array.
557 * @exception org.xml.sax.SAXException The client may throw
558 * an exception during processing.
559 */
560 public void characters (char ch[], int start, int length)
561 throws SAXException
562 {
563 if (contentHandler != null) {
564 contentHandler.characters(ch, start, length);
565 }
566 }
567
568
569 /***
570 * Filter an ignorable whitespace event.
571 *
572 * @param ch An array of characters.
573 * @param start The starting position in the array.
574 * @param length The number of characters to use from the array.
575 * @exception org.xml.sax.SAXException The client may throw
576 * an exception during processing.
577 */
578 public void ignorableWhitespace (char ch[], int start, int length)
579 throws SAXException
580 {
581 if (contentHandler != null) {
582 contentHandler.ignorableWhitespace(ch, start, length);
583 }
584 }
585
586
587 /***
588 * Filter a processing instruction event.
589 *
590 * @param target The processing instruction target.
591 * @param data The text following the target.
592 * @exception org.xml.sax.SAXException The client may throw
593 * an exception during processing.
594 */
595 public void processingInstruction (String target, String data)
596 throws SAXException
597 {
598 if (contentHandler != null) {
599 contentHandler.processingInstruction(target, data);
600 }
601 }
602
603
604 /***
605 * Filter a skipped entity event.
606 *
607 * @param name The name of the skipped entity.
608 * @exception org.xml.sax.SAXException The client may throw
609 * an exception during processing.
610 */
611 public void skippedEntity (String name)
612 throws SAXException
613 {
614 if (contentHandler != null) {
615 contentHandler.skippedEntity(name);
616 }
617 }
618
619
620
621
622
623
624
625
626 /***
627 * Filter a warning event.
628 *
629 * @param e The warning as an exception.
630 * @exception org.xml.sax.SAXException The client may throw
631 * an exception during processing.
632 */
633 public void warning (SAXParseException e)
634 throws SAXException
635 {
636 if (errorHandler != null) {
637 errorHandler.warning(e);
638 }
639 }
640
641
642 /***
643 * Filter an error event.
644 *
645 * @param e The error as an exception.
646 * @exception org.xml.sax.SAXException The client may throw
647 * an exception during processing.
648 */
649 public void error (SAXParseException e)
650 throws SAXException
651 {
652 if (errorHandler != null) {
653 errorHandler.error(e);
654 }
655 }
656
657
658 /***
659 * Filter a fatal error event.
660 *
661 * @param e The error as an exception.
662 * @exception org.xml.sax.SAXException The client may throw
663 * an exception during processing.
664 */
665 public void fatalError (SAXParseException e)
666 throws SAXException
667 {
668 if (errorHandler != null) {
669 errorHandler.fatalError(e);
670 }
671 }
672
673
674
675
676
677
678
679
680 /***
681 * Set up before a parse.
682 *
683 * <p>Before every parse, check whether the parent is
684 * non-null, and re-register the filter for all of the
685 * events.</p>
686 */
687 private void setupParse ()
688 {
689 if (parent == null) {
690 throw new NullPointerException("No parent for filter");
691 }
692 parent.setEntityResolver(this);
693 parent.setDTDHandler(this);
694 parent.setContentHandler(this);
695 parent.setErrorHandler(this);
696 }
697
698
699
700
701
702
703
704 private XMLReader parent = null;
705 private Locator locator = null;
706 private EntityResolver entityResolver = null;
707 private DTDHandler dtdHandler = null;
708 private ContentHandler contentHandler = null;
709 private ErrorHandler errorHandler = null;
710
711 }
712
713