xsddomparser.cpp
来自「IBM的解析xml的工具Xerces的源代码」· C++ 代码 · 共 530 行 · 第 1/2 页
CPP
530 行
/* * Copyright 2002,2004 The Apache Software Foundation. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. *//** * $Id: XSDDOMParser.cpp,v 1.14 2004/09/08 13:56:57 peiyongz Exp $ */// ---------------------------------------------------------------------------// Includes// ---------------------------------------------------------------------------#include <xercesc/validators/schema/XSDDOMParser.hpp>#include <xercesc/validators/schema/SchemaSymbols.hpp>#include <xercesc/internal/XMLScanner.hpp>#include <xercesc/internal/ElemStack.hpp>#include <xercesc/dom/DOMDocument.hpp>#include <xercesc/dom/impl/DOMElementImpl.hpp>#include <xercesc/dom/impl/DOMAttrImpl.hpp>#include <xercesc/dom/impl/DOMTextImpl.hpp>#include <xercesc/framework/XMLValidityCodes.hpp>XERCES_CPP_NAMESPACE_BEGIN// ---------------------------------------------------------------------------// XSDDOMParser: Constructors and Destructor// ---------------------------------------------------------------------------XSDDOMParser::XSDDOMParser( XMLValidator* const valToAdopt , MemoryManager* const manager , XMLGrammarPool* const gramPool): XercesDOMParser(valToAdopt, manager, gramPool) , fSawFatal(false) , fAnnotationDepth(-1) , fInnerAnnotationDepth(-1) , fDepth(-1) , fUserErrorReporter(0) , fUserEntityHandler(0) , fURIs(0) , fAnnotationBuf(1023, manager){ fURIs = new (manager) ValueVectorOf<unsigned int>(16, manager); fXSDErrorReporter.setErrorReporter(this); setValidationScheme(XercesDOMParser::Val_Never); setDoNamespaces(true);}XSDDOMParser::~XSDDOMParser(){ delete fURIs;}// ---------------------------------------------------------------------------// XSDDOMParser: Helper methods// ---------------------------------------------------------------------------DOMElement* XSDDOMParser::createElementNSNode(const XMLCh *namespaceURI, const XMLCh *qualifiedName){ ReaderMgr::LastExtEntityInfo lastInfo; ((ReaderMgr*) fScanner->getLocator())->getLastExtEntityInfo(lastInfo); return getDocument()->createElementNS(namespaceURI, qualifiedName, lastInfo.lineNumber, lastInfo.colNumber);}void XSDDOMParser::startAnnotation( const XMLElementDecl& elemDecl , const RefVectorOf<XMLAttr>& attrList , const unsigned int attrCount){ fAnnotationBuf.append(chOpenAngle); fAnnotationBuf.append(elemDecl.getFullName()); fAnnotationBuf.append(chSpace); // attributes are a bit of a pain. To get this right, we have to keep track // of the namespaces we've seen declared, then examine the namespace context // for other namespaces so that we can also include them. // optimized for simplicity and the case that not many // namespaces are declared on this annotation... fURIs->removeAllElements(); for (unsigned int i=0; i < attrCount; i++) { const XMLAttr* oneAttrib = attrList.elementAt(i); const XMLCh* attrValue = oneAttrib->getValue(); if (XMLString::equals(oneAttrib->getName(), XMLUni::fgXMLNSString)) fURIs->addElement(fScanner->getPrefixId(XMLUni::fgZeroLenString)); else if (!XMLString::compareNString(oneAttrib->getQName(), XMLUni::fgXMLNSColonString, 6)) fURIs->addElement(fScanner->getPrefixId(oneAttrib->getName())); fAnnotationBuf.append(oneAttrib->getQName()); fAnnotationBuf.append(chEqual); fAnnotationBuf.append(chDoubleQuote); fAnnotationBuf.append(attrValue); fAnnotationBuf.append(chDoubleQuote); fAnnotationBuf.append(chSpace); } // now we have to look through currently in-scope namespaces to see what // wasn't declared here ValueVectorOf<PrefMapElem*>* namespaceContext = fScanner->getNamespaceContext(); for (unsigned int j=0; j < namespaceContext->size(); j++) { unsigned int prefId = namespaceContext->elementAt(j)->fPrefId; if (!fURIs->containsElement(prefId)) { const XMLCh* prefix = fScanner->getPrefixForId(prefId); if (XMLString::equals(prefix, XMLUni::fgZeroLenString)) { fAnnotationBuf.append(XMLUni::fgXMLNSString); } else { fAnnotationBuf.append(XMLUni::fgXMLNSColonString); fAnnotationBuf.append(prefix); } fAnnotationBuf.append(chEqual); fAnnotationBuf.append(chDoubleQuote); fAnnotationBuf.append(fScanner->getURIText(namespaceContext->elementAt(j)->fURIId)); fAnnotationBuf.append(chDoubleQuote); fAnnotationBuf.append(chSpace); } } fAnnotationBuf.append(chCloseAngle); fAnnotationBuf.append(chLF);}void XSDDOMParser::startAnnotationElement( const XMLElementDecl& elemDecl , const RefVectorOf<XMLAttr>& attrList , const unsigned int attrCount){ fAnnotationBuf.append(chOpenAngle); fAnnotationBuf.append(elemDecl.getFullName()); //fAnnotationBuf.append(chSpace); for(unsigned int i=0; i < attrCount; i++) { const XMLAttr* oneAttr = attrList.elementAt(i); fAnnotationBuf.append(chSpace); fAnnotationBuf.append(oneAttr ->getQName()); fAnnotationBuf.append(chEqual); fAnnotationBuf.append(chDoubleQuote); fAnnotationBuf.append(oneAttr->getValue()); fAnnotationBuf.append(chDoubleQuote); } fAnnotationBuf.append(chCloseAngle);}void XSDDOMParser::endAnnotationElement( const XMLElementDecl& elemDecl , bool complete){ if (complete) { fAnnotationBuf.append(chLF); fAnnotationBuf.append(chOpenAngle); fAnnotationBuf.append(chForwardSlash); fAnnotationBuf.append(elemDecl.getFullName()); fAnnotationBuf.append(chCloseAngle); // note that this is always called after endElement on <annotation>'s // child and before endElement on annotation. // hence, we must make this the child of the current // parent's only child. DOMTextImpl *node = (DOMTextImpl *)fDocument->createTextNode(fAnnotationBuf.getRawBuffer()); fCurrentNode->appendChild(node); fAnnotationBuf.reset(); } else //capturing character calls { fAnnotationBuf.append(chOpenAngle); fAnnotationBuf.append(chForwardSlash); fAnnotationBuf.append(elemDecl.getFullName()); fAnnotationBuf.append(chCloseAngle); }}// ---------------------------------------------------------------------------// XSDDOMParser: Setter methods// ---------------------------------------------------------------------------void XSDDOMParser::setUserErrorReporter(XMLErrorReporter* const errorReporter){ fUserErrorReporter = errorReporter; fScanner->setErrorReporter(this);}void XSDDOMParser::setUserEntityHandler(XMLEntityHandler* const entityHandler){ fUserEntityHandler = entityHandler; fScanner->setEntityHandler(this);}// ---------------------------------------------------------------------------// XSDDOMParser: Implementation of the XMLDocumentHandler interface// ---------------------------------------------------------------------------void XSDDOMParser::startElement( const XMLElementDecl& elemDecl , const unsigned int urlId , const XMLCh* const elemPrefix , const RefVectorOf<XMLAttr>& attrList , const unsigned int attrCount , const bool isEmpty , const bool isRoot){ fDepth++; // while it is true that non-whitespace character data // may only occur in appInfo or documentation // elements, it's certainly legal for comments and PI's to // occur as children of annotation; we need // to account for these here. if (fAnnotationDepth == -1) { if (XMLString::equals(elemDecl.getBaseName(), SchemaSymbols::fgELT_ANNOTATION) && XMLString::equals(getURIText(urlId), SchemaSymbols::fgURI_SCHEMAFORSCHEMA)) { fAnnotationDepth = fDepth; startAnnotation(elemDecl, attrList, attrCount); } } else if (fDepth == fAnnotationDepth+1) { fInnerAnnotationDepth = fDepth; startAnnotationElement(elemDecl, attrList, attrCount); } else { startAnnotationElement(elemDecl, attrList, attrCount); // avoid falling through; don't call startElement in this case return; } DOMElement *elem; if (urlId != fScanner->getEmptyNamespaceId()) //TagName has a prefix { if (elemPrefix && *elemPrefix) { XMLBufBid elemQName(&fBufMgr); elemQName.set(elemPrefix); elemQName.append(chColon); elemQName.append(elemDecl.getBaseName()); elem = createElementNSNode( fScanner->getURIText(urlId), elemQName.getRawBuffer()); } else { elem = createElementNSNode(
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?