001: /*
002: * Copyright 2006 the original author or authors.
003: *
004: * Licensed under the Apache License, Version 2.0 (the "License");
005: * you may not use this file except in compliance with the License.
006: * You may obtain a copy of the License at
007: *
008: * http://www.apache.org/licenses/LICENSE-2.0
009: *
010: * Unless required by applicable law or agreed to in writing, software
011: * distributed under the License is distributed on an "AS IS" BASIS,
012: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013: * See the License for the specific language governing permissions and
014: * limitations under the License.
015: */
016:
017: package org.springframework.xml.stream;
018:
019: import javax.xml.namespace.QName;
020: import javax.xml.stream.XMLStreamException;
021:
022: import org.springframework.xml.namespace.QNameUtils;
023: import org.springframework.xml.namespace.SimpleNamespaceContext;
024: import org.xml.sax.Attributes;
025: import org.xml.sax.ContentHandler;
026: import org.xml.sax.SAXException;
027:
028: /**
029: * Abstract base class for SAX <code>ContentHandler</code> implementations that use StAX as a basis. All methods
030: * delegate to internal template methods, capable of throwing a <code>XMLStreamException</code>. Additionally, an
031: * namespace context is used to keep track of declared namespaces.
032: *
033: * @author Arjen Poutsma
034: * @since 1.0.0
035: */
036: public abstract class AbstractStaxContentHandler implements
037: ContentHandler {
038:
039: private SimpleNamespaceContext namespaceContext = new SimpleNamespaceContext();
040:
041: /**
042: * @throws SAXException
043: */
044: public final void startDocument() throws SAXException {
045: namespaceContext.clear();
046: try {
047: startDocumentInternal();
048: } catch (XMLStreamException ex) {
049: throw new SAXException("Could not handle startDocument: "
050: + ex.getMessage(), ex);
051: }
052: }
053:
054: protected abstract void startDocumentInternal()
055: throws XMLStreamException;
056:
057: public final void endDocument() throws SAXException {
058: namespaceContext.clear();
059: try {
060: endDocumentInternal();
061: } catch (XMLStreamException ex) {
062: throw new SAXException("Could not handle startDocument: "
063: + ex.getMessage(), ex);
064: }
065: }
066:
067: protected abstract void endDocumentInternal()
068: throws XMLStreamException;
069:
070: /**
071: * Binds the given prefix to the given namespaces.
072: *
073: * @see SimpleNamespaceContext#bindNamespaceUri(String,String)
074: */
075: public final void startPrefixMapping(String prefix, String uri) {
076: namespaceContext.bindNamespaceUri(prefix, uri);
077: }
078:
079: /**
080: * Removes the binding for the given prefix.
081: *
082: * @see SimpleNamespaceContext#removeBinding(String)
083: */
084: public final void endPrefixMapping(String prefix) {
085: namespaceContext.removeBinding(prefix);
086: }
087:
088: public final void startElement(String uri, String localName,
089: String qName, Attributes atts) throws SAXException {
090: try {
091: startElementInternal(QNameUtils.toQName(uri, qName), atts,
092: namespaceContext);
093: } catch (XMLStreamException ex) {
094: throw new SAXException("Could not handle startElement: "
095: + ex.getMessage(), ex);
096: }
097: }
098:
099: protected abstract void startElementInternal(QName name,
100: Attributes atts, SimpleNamespaceContext namespaceContext)
101: throws XMLStreamException;
102:
103: public final void endElement(String uri, String localName,
104: String qName) throws SAXException {
105: try {
106: endElementInternal(QNameUtils.toQName(uri, qName),
107: namespaceContext);
108: } catch (XMLStreamException ex) {
109: throw new SAXException("Could not handle endElement: "
110: + ex.getMessage(), ex);
111: }
112: }
113:
114: protected abstract void endElementInternal(QName name,
115: SimpleNamespaceContext namespaceContext)
116: throws XMLStreamException;
117:
118: public final void characters(char ch[], int start, int length)
119: throws SAXException {
120: try {
121: charactersInternal(ch, start, length);
122: } catch (XMLStreamException ex) {
123: throw new SAXException("Could not handle characters: "
124: + ex.getMessage(), ex);
125: }
126: }
127:
128: protected abstract void charactersInternal(char[] ch, int start,
129: int length) throws XMLStreamException;
130:
131: public final void ignorableWhitespace(char[] ch, int start,
132: int length) throws SAXException {
133: try {
134: ignorableWhitespaceInternal(ch, start, length);
135: } catch (XMLStreamException ex) {
136: throw new SAXException(
137: "Could not handle ignorableWhitespace:"
138: + ex.getMessage(), ex);
139: }
140: }
141:
142: protected abstract void ignorableWhitespaceInternal(char[] ch,
143: int start, int length) throws XMLStreamException;
144:
145: public final void processingInstruction(String target, String data)
146: throws SAXException {
147: try {
148: processingInstructionInternal(target, data);
149: } catch (XMLStreamException ex) {
150: throw new SAXException(
151: "Could not handle processingInstruction: "
152: + ex.getMessage(), ex);
153: }
154: }
155:
156: protected abstract void processingInstructionInternal(
157: String target, String data) throws XMLStreamException;
158:
159: public final void skippedEntity(String name) throws SAXException {
160: try {
161: skippedEntityInternal(name);
162: } catch (XMLStreamException ex) {
163: throw new SAXException("Could not handle skippedEntity: "
164: + ex.getMessage(), ex);
165: }
166: }
167:
168: protected abstract void skippedEntityInternal(String name)
169: throws XMLStreamException;
170: }
|