Click here to Skip to main content
11,632,778 members (83,354 online)
Click here to Skip to main content
Articles » Languages » XML » General » Downloads
Add your own
alternative version

C++ Wrappers for the Expat XML Parser

, 17 Feb 2002 593.9K 4.1K 75
The included class definitions provide complete and easy to use C++ wrappers for the Expat C API
expatimpl_src.zip
#ifndef DSSI_EXPATIMPL_H
#define DSSI_EXPATIMPL_H

//-----------------------------------------------------------------------------
// 
// @doc
//
// @module	ExpatImpl.h - Expat class container |
//
// This module contains the definition of the expat class container.
//
// Copyright (c) 1994-2002 - Descartes Systems Sciences, Inc.
//
// @end
//
// $History: ExpatImpl.h $
//      
//      *****************  Version 1  *****************
//      User: Tim Smith    Date: 1/29/02    Time: 1:57p
//      Created in $/Omni_V2/_ToolLib
//      1. String.h now replaced with StringCode.h.
//      2. StringRsrc.h modified to use new string class.
//      3. Added tons of new classes from the wedge work.
//      
//-----------------------------------------------------------------------------

//-----------------------------------------------------------------------------
//
// Required include files
//
//-----------------------------------------------------------------------------

#include <assert.h>
#include "expat.h"

//-----------------------------------------------------------------------------
//
// Forward definitions
//
//-----------------------------------------------------------------------------

//-----------------------------------------------------------------------------
//
// Template class definition
//
//-----------------------------------------------------------------------------

template <class _T>
class CExpatImpl
{

// @access Constructors and destructors
public:
	
	// @cmember General constructor

	CExpatImpl ()
	{
		m_p = NULL;
	}

	// @cmember Destructor

	~CExpatImpl ()
	{
		Destroy ();
	}

// @access Parser creation and deletion methods
public:

	// @cmember Create a parser

	bool Create (const XML_Char *pszEncoding = NULL, 
		const XML_Char *pszSep = NULL)
	{

		//
		// Destroy the old parser
		//

		Destroy ();

		//
		// If the encoding or seperator are empty, then NULL
		//

		if (pszEncoding != NULL && pszEncoding [0] == 0)
			pszEncoding = NULL;
		if (pszSep != NULL && pszSep [0] == 0)
			pszSep = NULL;

		//
		// Create the new one
		//

		m_p = XML_ParserCreate_MM (pszEncoding, NULL, pszSep);
		if (m_p == NULL)
			return false;

		//
		// Invoke the post create routine
		//

		_T *pThis = static_cast <_T *> (this);
		pThis ->OnPostCreate ();

		//
		// Set the user data used in callbacks
		//

		XML_SetUserData (m_p, (void *) this);
		return true;
	}

	// @cmember Destroy the parser

	void Destroy ()
	{
		if (m_p != NULL)
			XML_ParserFree (m_p);
		m_p = NULL;
	}

// @access Parser parse methods
public:

	// @cmember Parse a block of data

	bool Parse (const char *pszBuffer, int nLength = -1, bool fIsFinal = true)
	{

		//
		// Validate
		//

		assert (m_p != NULL);

		//
		// Get the length if not specified
		//

		if (nLength < 0)
			nLength = strlen (pszBuffer);

		//
		// Invoke the parser
		//

		return XML_Parse (m_p, pszBuffer, nLength, fIsFinal) != 0;
	}

	// @cmember Parse a block of data

#ifdef WCHAR
	bool Parse (const WCHAR *pszBuffer, int nLength = -1, bool fIsFinal = true)
	{

		//
		// Validate
		//

		assert (m_p != NULL);

		//
		// Get the length if not specified
		//

		if (nLength < 0)
			nLength = wcslen (pszBuffer) * 2;

		//
		// Invoke the parser
		//

		return XML_Parse (m_p, pszBuffer, nLength, fIsFinal) != 0;
	}
#endif

	// @cmember Parse internal buffer

	bool ParseBuffer (int nLength, bool fIsFinal = true)
	{
		assert (m_p != NULL);
		return XML_ParseBuffer (m_p, nLength, fIsFinal) != 0;
	}

	// @cmember Get the internal buffer

	void *GetBuffer (int nLength)
	{
		assert (m_p != NULL);
		return XML_GetBuffer (m_p, nLength);
	}

// @access Parser callback enable/disable methods
public:

	// @cmember Enable/Disable the start element handler

	void EnableStartElementHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetStartElementHandler (m_p, fEnable ? StartElementHandler : NULL);
	}

	// @cmember Enable/Disable the end element handler

	void EnableEndElementHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetEndElementHandler (m_p, fEnable ? EndElementHandler : NULL);
	}

	// @cmember Enable/Disable the element handlers

	void EnableElementHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		EnableStartElementHandler (fEnable);
		EnableEndElementHandler (fEnable);
	}

	// @cmember Enable/Disable the character data handler

	void EnableCharacterDataHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetCharacterDataHandler (m_p,
			fEnable ? CharacterDataHandler : NULL);
	}

	// @cmember Enable/Disable the processing instruction handler

	void EnableProcessingInstructionHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetProcessingInstructionHandler (m_p, 
			fEnable ? ProcessingInstructionHandler : NULL);
	}

	// @cmember Enable/Disable the comment handler

	void EnableCommentHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetCommentHandler (m_p, fEnable ? CommentHandler : NULL);
	}

	// @cmember Enable/Disable the start CDATA section handler

	void EnableStartCdataSectionHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetStartCdataSectionHandler (m_p, 
			fEnable ? StartCdataSectionHandler : NULL);
	}

	// @cmember Enable/Disable the end CDATA section handler

	void EnableEndCdataSectionHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetEndCdataSectionHandler (m_p, 
			fEnable ? EndCdataSectionHandler : NULL);
	}

	// @cmember Enable/Disable the CDATA section handlers

	void EnableCdataSectionHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		EnableStartCdataSectionHandler (fEnable);
		EnableEndCdataSectionHandler (fEnable);
	}

	// @cmember Enable/Disable default handler
	
	void EnableDefaultHandler (bool fEnable = true, bool fExpand = true)
	{
		assert (m_p != NULL);
		if (fExpand)
		{
			XML_SetDefaultHandlerExpand (m_p, 
				fEnable ? DefaultHandler : NULL);
		}
		else
			XML_SetDefaultHandler (m_p, fEnable ? DefaultHandler : NULL);
	}
	
	// @cmember Enable/Disable external entity ref handler
	
	void EnableExternalEntityRefHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetExternalEntityRefHandler (m_p, 
			fEnable ? ExternalEntityRefHandler : NULL);
	}
	
	// @cmember Enable/Disable unknown encoding handler
	
	void EnableUnknownEncodingHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetUnknownEncodingHandler (m_p, 
			fEnable ? UnknownEncodingHandler : NULL);
	}
	
	// @cmember Enable/Disable start namespace handler
	
	void EnableStartNamespaceDeclHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetStartNamespaceDeclHandler (m_p, 
			fEnable ? StartNamespaceDeclHandler : NULL);
	}
	
	// @cmember Enable/Disable end namespace handler
	
	void EnableEndNamespaceDeclHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetEndNamespaceDeclHandler (m_p, 
			fEnable ? EndNamespaceDeclHandler : NULL);
	}

	// @cmember Enable/Disable namespace handlers

	void EnableNamespaceDeclHandler (bool fEnable = true)
	{
		EnableStartNamespaceDeclHandler (fEnable);
		EnableEndNamespaceDeclHandler (fEnable);
	}
	
	// @cmember Enable/Disable the XML declaration handler

	void EnableXmlDeclHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetXmlDeclHandler (m_p, fEnable ? XmlDeclHandler : NULL);
	}

	// @cmember Enable/Disable the start DOCTYPE declaration handler

	void EnableStartDoctypeDeclHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetStartDoctypeDeclHandler (m_p, 
			fEnable ? StartDoctypeDeclHandler : NULL);
	}

	// @cmember Enable/Disable the end DOCTYPE declaration handler

	void EnableEndDoctypeDeclHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		XML_SetEndDoctypeDeclHandler (m_p, 
			fEnable ? EndDoctypeDeclHandler : NULL);
	}

	// @cmember Enable/Disable the DOCTYPE declaration handler

	void EnableDoctypeDeclHandler (bool fEnable = true)
	{
		assert (m_p != NULL);
		EnableStartDoctypeDeclHandler (fEnable);
		EnableEndDoctypeDeclHandler (fEnable);
	}

// @access Parser error reporting methods
public:

	// @cmember Get last error

	enum XML_Error GetErrorCode () 
	{
		assert (m_p != NULL);
		return XML_GetErrorCode (m_p);
	}

	// @cmember Get the current byte index

	long GetCurrentByteIndex () 
	{
		assert (m_p != NULL);
		return XML_GetCurrentByteIndex (m_p);
	}

	// @cmember Get the current line number

	int GetCurrentLineNumber () 
	{
		assert (m_p != NULL);
		return XML_GetCurrentLineNumber (m_p);
	}

	// @cmember Get the current column number

	int GetCurrentColumnNumber () 
	{
		assert (m_p != NULL);
		return XML_GetCurrentColumnNumber (m_p);
	}

	// @cmember Get the current byte count

	int GetCurrentByteCount () 
	{
		assert (m_p != NULL);
		return XML_GetCurrentByteCount (m_p);
	}

	// @cmember Get the input context

	const char *GetInputContext (int *pnOffset, int *pnSize)
	{
		assert (m_p != NULL);
		return XML_GetInputContext (m_p, pnOffset, pnSize);
	}

	// @cmember Get last error string

	const XML_LChar *GetErrorString () 
	{
		return XML_ErrorString (GetErrorCode ());
	}

// @access Parser other methods
public:

	// @cmember Return the version string

	static const XML_LChar *GetExpatVersion ()
	{
		return XML_ExpatVersion ();
	}

	// @cmember Get the version information

	static void GetExpatVersion (int *pnMajor, int *pnMinor, int *pnMicro)
	{
		XML_expat_version v = XML_ExpatVersionInfo ();
		if (pnMajor)
			*pnMajor = v .major;
		if (pnMinor)
			*pnMinor = v .minor;
		if (pnMicro)
			*pnMicro = v .micro;
	}

	// @cmember Get last error string

	static const XML_LChar *GetErrorString (enum XML_Error nError) 
	{
		return XML_ErrorString (nError);
	}

// @access Public handler methods
public:

	// @cmember Start element handler

	void OnStartElement (const XML_Char *pszName, const XML_Char **papszAttrs)
	{
		return;
	}

	// @cmember End element handler

	void OnEndElement (const XML_Char *pszName)
	{
		return;
	}

	// @cmember Character data handler

	void OnCharacterData (const XML_Char *pszData, int nLength)
	{
		return;
	}

	// @cmember Processing instruction handler

	void OnProcessingInstruction (const XML_Char *pszTarget, 
		const XML_Char *pszData)
	{
		return;
	}

	// @cmember Comment handler

	void OnComment (const XML_Char *pszData)
	{
		return;
	}

	// @cmember Start CDATA section handler

	void OnStartCdataSection ()
	{
		return;
	}

	// @cmember End CDATA section handler

	void OnEndCdataSection ()
	{
		return;
	}

	// @cmember Default handler
	
	void OnDefault (const XML_Char *pszData, int nLength)
	{
		return;
	}
	
	// @cmember External entity ref handler
	
	bool OnExternalEntityRef (const XML_Char *pszContext,
		const XML_Char *pszBase, const XML_Char *pszSystemID,
		const XML_Char *pszPublicID)
	{
		return false;
	}
	
	// @cmember Unknown encoding handler
	
	bool OnUnknownEncoding (const XML_Char *pszName, XML_Encoding *pInfo)
	{
		return false;
	}
	
	// @cmember Start namespace declaration handler
	
	void OnStartNamespaceDecl (const XML_Char *pszPrefix, 
		const XML_Char *pszURI)
	{
		return;
	}
	
	// @cmember End namespace declaration handler
	
	void OnEndNamespaceDecl (const XML_Char *pszPrefix)
	{
		return;
	}
	
	// @cmember XML declaration handler

	void OnXmlDecl (const XML_Char *pszVersion, const XML_Char *pszEncoding,
		bool fStandalone)
	{
		return;
	}

	// @cmember Start DOCTYPE declaration handler

	void OnStartDoctypeDecl (const XML_Char *pszDoctypeName, 
		const XML_Char *pszSysID, const XML_Char *pszPubID,
		bool fHasInternalSubset)
	{
		return;
	}

	// @cmember End DOCTYPE declaration handler

	void OnEndDoctypeDecl ()
	{
		return;
	}

// @access Protected methods
protected:

	// @cmember Handle any post creation

	void OnPostCreate ()
	{
	}

// @access Protected static methods
protected:

	// @cmember Start element handler wrapper

	static void __cdecl StartElementHandler (void *pUserData,
		const XML_Char *pszName, const XML_Char **papszAttrs)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnStartElement (pszName, papszAttrs);
	}

	// @cmember End element handler wrapper

	static void __cdecl EndElementHandler (void *pUserData,
		const XML_Char *pszName)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnEndElement (pszName);
	}

	// @cmember Character data handler wrapper

	static void __cdecl CharacterDataHandler (void *pUserData,
		const XML_Char *pszData, int nLength)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnCharacterData (pszData, nLength);
	}

	// @cmember Processing instruction handler wrapper

	static void __cdecl ProcessingInstructionHandler (void *pUserData,
		const XML_Char *pszTarget, const XML_Char *pszData)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnProcessingInstruction (pszTarget, pszData);
	}

	// @cmember Comment handler wrapper

	static void __cdecl CommentHandler (void *pUserData,
		const XML_Char *pszData)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnComment (pszData);
	}

	// @cmember Start CDATA section wrapper

	static void __cdecl StartCdataSectionHandler (void *pUserData)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnStartCdataSection ();
	}

	// @cmember End CDATA section wrapper

	static void __cdecl EndCdataSectionHandler (void *pUserData)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnEndCdataSection ();
	}

	// @cmember Default wrapper
	
	static void __cdecl DefaultHandler (void *pUserData, 
		const XML_Char *pszData, int nLength)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnDefault (pszData, nLength);
	}
	
	// @cmember External entity ref wrapper
	
	static int __cdecl ExternalEntityRefHandler (void *pUserData, 
		const XML_Char *pszContext, const XML_Char *pszBase, 
		const XML_Char *pszSystemID, const XML_Char *pszPublicID)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		return pThis ->OnExternalEntityRef (pszContext, 
			pszBase, pszSystemID, pszPublicID) ? 1 : 0;
	}
	
	// @cmember Unknown encoding wrapper
	
	static int __cdecl UnknownEncodingHandler (void *pUserData, 
		const XML_Char *pszName, XML_Encoding *pInfo)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		return pThis ->OnUnknownEncoding (pszName, pInfo) ? 1 : 0;
	}
	
	// @cmember Start namespace decl wrapper
	
	static void __cdecl StartNamespaceDeclHandler (void *pUserData, 
		const XML_Char *pszPrefix, const XML_Char *pszURI)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnStartNamespaceDecl (pszPrefix, pszURI);
	}
	
	// @cmember End namespace decl wrapper
	
	static void __cdecl EndNamespaceDeclHandler (void *pUserData, 
		const XML_Char *pszPrefix)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnEndNamespaceDecl (pszPrefix);
	}
	
	// @cmember XML declaration wrapper

	static void __cdecl XmlDeclHandler (void *pUserData,
		const XML_Char *pszVersion, const XML_Char *pszEncoding,
		int nStandalone)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnXmlDecl (pszVersion, pszEncoding, nStandalone != 0);
	}

	// @cmember Start Doctype declaration wrapper

	static void __cdecl StartDoctypeDeclHandler (void *pUserData,
		const XML_Char *pszDoctypeName, const XML_Char *pszSysID, 
		const XML_Char *pszPubID, int nHasInternalSubset)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnStartDoctypeDecl (pszDoctypeName, pszSysID, 
			pszPubID, nHasInternalSubset != 0);
	}

	// @cmember End Doctype declaration wrapper

	static void __cdecl EndDoctypeDeclHandler (void *pUserData)
	{
		_T *pThis = static_cast <_T *> ((CExpatImpl <_T> *) pUserData);
		pThis ->OnEndDoctypeDecl ();
	}

// @access Protected members
protected:

	XML_Parser		m_p;
};

//-----------------------------------------------------------------------------
//
// Virtual method class definition
//
//-----------------------------------------------------------------------------

class CExpat : public CExpatImpl <CExpat>
{
// @access Constructors and destructors
public:
	
	CExpat ()
	{
	}

// @access Public handler methods
public:

	// @cmember Start element handler

	virtual void OnStartElement (const XML_Char *pszName, 
		const XML_Char **papszAttrs)
	{
		return;
	}

	// @cmember End element handler

	virtual void OnEndElement (const XML_Char *pszName)
	{
		return;
	}

	// @cmember Character data handler

	virtual void OnCharacterData (const XML_Char *pszData, int nLength)
	{
		return;
	}

	// @cmember Processing instruction handler

	virtual void OnProcessingInstruction (const XML_Char *pszTarget, 
		const XML_Char *pszData)
	{
		return;
	}

	// @cmember Comment handler

	virtual void OnComment (const XML_Char *pszData)
	{
		return;
	}

	// @cmember Start CDATA section handler

	virtual void OnStartCdataSection ()
	{
		return;
	}

	// @cmember End CDATA section handler

	virtual void OnEndCdataSection ()
	{
		return;
	}

	// @cmember Default handler
	
	virtual void OnDefault (const XML_Char *pszData, int nLength)
	{
		return;
	}
	
	// @cmember External entity ref handler
	
	virtual bool OnExternalEntityRef (const XML_Char *pszContext,
		const XML_Char *pszBase, const XML_Char *pszSystemID,
		const XML_Char *pszPublicID)
	{
		return false;
	}
	
	// @cmember Unknown encoding handler
	
	virtual bool OnUnknownEncoding (const XML_Char *pszName, XML_Encoding *pInfo)
	{
		return false;
	}
	
	// @cmember Start namespace declaration handler
	
	virtual void OnStartNamespaceDecl (const XML_Char *pszPrefix, 
		const XML_Char *pszURI)
	{
		return;
	}
	
	// @cmember End namespace declaration handler
	
	virtual void OnEndNamespaceDecl (const XML_Char *pszPrefix)
	{
		return;
	}
	
	// @cmember XML declaration handler

	virtual void OnXmlDecl (const XML_Char *pszVersion, 
		const XML_Char *pszEncoding, bool fStandalone)
	{
		return;
	}

	// @cmember Start DOCTYPE declaration handler

	virtual void OnStartDoctypeDecl (const XML_Char *pszDoctypeName, 
		const XML_Char *pszSysID, const XML_Char *pszPubID,
		bool fHasInternalSubset)
	{
		return;
	}

	// @cmember End DOCTYPE declaration handler

	virtual void OnEndDoctypeDecl ()
	{
		return;
	}
};

#endif // DSSI_EXPATIMPL_H

By viewing downloads associated with this article you agree to the Terms of Service and the article's licence.

If a file you wish to view isn't highlighted, and is a text file (not binary), please let us know and we'll add colourisation support for it.

License

This article has no explicit license attached to it but may contain usage terms in the article text or the download files themselves. If in doubt please contact the author via the discussion board below.

A list of licenses authors might use can be found here

Share

About the Author

Tim Smith
Web Developer
Canada Canada
Currently I am working in the tools department at BioWare Corp..

You may also be interested in...

| Advertise | Privacy | Terms of Use | Mobile
Web04 | 2.8.150728.1 | Last Updated 18 Feb 2002
Article Copyright 2002 by Tim Smith
Everything else Copyright © CodeProject, 1999-2015
Layout: fixed | fluid