Public Member Functions | Protected Types | Protected Member Functions | Protected Attributes

xmlstorage::XMLReader Class Reference

XML reader class. More...

Inheritance diagram for xmlstorage::XMLReader:
Inheritance graph
[legend]
Collaboration diagram for xmlstorage::XMLReader:
Collaboration graph
[legend]

List of all members.

Public Member Functions

 this (XMLNode node, Stream i)
int get ()
 read one character from XML stream
bool parse ()
void read ()
char[] get_position ()
XMLFormat get_format ()
char[] get_endl ()
XMLErrorList get_errors ()
XMLErrorList get_warnings ()
void clear_errors ()
 version (XMLNODE_LOCATION)

Protected Types

enum  TAG { TAG_NONE, TAG_START, TAG_END }

Protected Member Functions

int eat_endl ()
void finish_read ()
void XmlDeclHandler (in char[]*ver, char[]*encoding, int standalone)
 store XML version and encoding into XML reader
void StartElementHandler (in char[] name, XMLNode.AttributeMap attributes)
 notifications about XML start tag
void EndElementHandler ()
 notifications about XML end tag
void DefaultHandler (in char[] s)

Protected Attributes

Stream _in
XMLPos _pos
char[] _content
TAG _last_tag
XMLErrorList _errors
XMLErrorList _warnings
XMLFormat _format
bool _endl_defined
bool _utf8

Detailed Description

XML reader class.

Definition at line 2092 of file xmlstorage.d.


Member Enumeration Documentation

enum xmlstorage::XMLReaderBase::TAG [protected, inherited]
Enumerator:
TAG_NONE 
TAG_START 
TAG_END 

Definition at line 1960 of file xmlstorage.d.


Constructor & Destructor Documentation

xmlstorage::XMLReader::this ( XMLNode  node,
Stream  i 
) [inline]

Definition at line 2095 of file xmlstorage.d.

    {
        super(node);
        _in = i;
    }

Member Function Documentation

void xmlstorage::XMLReaderBase::clear_errors (  ) [inline, inherited]

Definition at line 1938 of file xmlstorage.d.

Referenced by xmlstorage::XMLDoc::read().

    {
        _errors.clear();
        _warnings.clear();
    }

Here is the caller graph for this function:

void xmlstorage::XMLReaderBase::DefaultHandler ( in char[]  s ) [inline, protected, inherited]

Definition at line 2084 of file xmlstorage.d.

    {
        _content ~= s;
    }
int xmlstorage::XMLReaderBase::eat_endl (  ) [inline, protected, inherited]

Definition at line 1971 of file xmlstorage.d.

    {
        int c = get();

        if (c == '\r')
            c = get();

        if (c == '\n')
            c = get();

        return c;
    }
void xmlstorage::XMLReaderBase::EndElementHandler (  ) [inline, protected, inherited]

notifications about XML end tag

Definition at line 2049 of file xmlstorage.d.

    {
        int s = 0;
        int i = 0;
        int e = _content.length;

        if (_content.length>=9+3 &&
            _content[0..9]=="<![CDATA[" && _content[length-3..length]=="]]>") {
            s += 9;
            i = (e-=3);
        } else {
             // search for content end leaving only white space for _end_leading
            for(i=e; i>0; --i)
                if (!isspace(cast(dchar)_content[i-1]))
                    break;
        }

        if (i > s)
            if (_pos()._children.empty())   // no children in current node?
                _pos()._content ~= _content[s .. i];
            else if (_last_tag == TAG.TAG_START)
                _pos()._content ~= _content[s .. i];
            else
                _pos()._children.back()._trailing ~= _content[s .. i];

        if (i != e)
            _pos()._end_leading = _content[i .. e];

        _pos.back();

        _last_tag = TAG.TAG_END;
        _content.length = 0;
    }
void xmlstorage::XMLReaderBase::finish_read (  ) [inline, protected, inherited]

Definition at line 1986 of file xmlstorage.d.

    {
        if (_pos()._children.empty())
            _pos()._trailing ~= _content;
        else
            _pos()._children.back()._trailing ~= _content;

        _content.length = 0;
    }
int xmlstorage::XMLReader::get (  ) [inline, virtual]

read one character from XML stream

Implements xmlstorage::XMLReaderBase.

Definition at line 2102 of file xmlstorage.d.

    {
        int c = _in.getc();

        return !_in.eof()? c: EOF;
    }
char [] xmlstorage::XMLReaderBase::get_endl (  ) [inline, inherited]

Definition at line 1933 of file xmlstorage.d.

Referenced by xmlstorage::XMLDoc::read().

{return _endl_defined? _format._endl: "\n";}

Here is the caller graph for this function:

XMLErrorList xmlstorage::XMLReaderBase::get_errors (  ) [inline, inherited]

Definition at line 1935 of file xmlstorage.d.

Referenced by xmlstorage::XMLDoc::read().

{return _errors;}

Here is the caller graph for this function:

XMLFormat xmlstorage::XMLReaderBase::get_format (  ) [inline, inherited]

Definition at line 1932 of file xmlstorage.d.

Referenced by xmlstorage::XMLDoc::read().

{return _format;}

Here is the caller graph for this function:

char [] xmlstorage::XMLReaderBase::get_position (  ) [inline, inherited]

Definition at line 1923 of file xmlstorage.d.

    {
    /*@TODO display parser position in case of errors
        return format("%s(%d) [column %d] : %s", _systemId, _line, _column, _message);
    */
        return "";
    }
XMLErrorList xmlstorage::XMLReaderBase::get_warnings (  ) [inline, inherited]

Definition at line 1936 of file xmlstorage.d.

{return _warnings;}
bool xmlstorage::XMLReaderBase::parse (  ) [inline, inherited]

Definition at line 1728 of file xmlstorage.d.

References xmlstorage::StyleSheet::_charset, xmlstorage::StyleSheet::_media, xmlstorage::StyleSheet::_title, xmlstorage::Buffer::append(), xmlstorage::Buffer::get_attributes(), xmlstorage::Buffer::get_tag(), xmlstorage::Buffer::has_CDEnd(), xmlstorage::Buffer::reset(), and xmlstorage::Buffer::str().

    {
        Buffer buffer = new Buffer;
        int c = get();
        bool in_comment = false;

        while(c != EOF) {
            if (in_comment || c=='<') {
                buffer.append(c);

                 // read start or end tag
                for(;;) {
                    c = get();

                    if (c == EOF)
                        break;

                    buffer.append(c);

                    if (c == '>')
                        break;
                }

                char[] b = buffer.str();

                if (in_comment || (b.length>=4 && b[1..4]=="!--")) {
                     // XML comment
                    DefaultHandler(b);

                    if (b.length>=3 && b[length-3..length]=="-->")
                        in_comment = true;
                    else
                        in_comment = false;

                    c = get();
                } else if (b.length >= 2) {
                    if (b[1] == '/') {
                         // end tag

                        /*@TODO error handling
                        char[]& tag = buffer.get_tag();

                            if (tag != last_opened_tag) {
                                ERROR
                            }
                        */

                        EndElementHandler();

                        c = get();
                    } else if (b[1] == '?') {
                         // XML declaration
                        char[] tag = buffer.get_tag();

                        if (tag == "?xml") {
                            XMLNode.AttributeMap attributes;
                            buffer.get_attributes(attributes);

                            char[]* ver = "version" in attributes;
                            char[]* encoding = "encoding" in attributes;

                            int standalone;
                            char[]* found = "standalone" in attributes;
                            if (found)
                                standalone = !icmp(*found, "yes");
                            else
                                standalone = -1;

                            XmlDeclHandler(ver, encoding, standalone);

                            if (encoding && !icmp(*encoding, "utf-8"))
                                _utf8 = true;

                            c = eat_endl();
                        } else if (tag == "?xml-stylesheet") {
                            XMLNode.AttributeMap attributes;
                            buffer.get_attributes(attributes);

                            auto phref = "href" in attributes;
                            auto ptype = "type" in attributes;
                            auto palternate = "alternate" in attributes;

                            StyleSheet stylesheet = new StyleSheet(phref?*phref:"", ptype?*ptype:"", palternate?!icmp(*palternate,"yes"):false);

                            auto ptitle = "title" in attributes;
                            if (ptitle)
                                stylesheet._title = *ptitle;

                            auto pmedia = "media" in attributes;
                            if (pmedia)
                                stylesheet._media = *pmedia;

                            auto pcharset = "charset" in attributes;
                            if (pcharset)
                                stylesheet._charset = *pcharset;

                            _format._stylesheets.push_back(stylesheet);

                            c = eat_endl();
                        } else {
                            DefaultHandler(b);
                            c = get();
                        }
                    } else if (b[1] == '!') {
                        if (b.length>=10 && b[2..10]=="DOCTYPE ") {
                            _format._doctype.parse(b[10..length]);

                            c = eat_endl();
                        } else if (b.length>=9 && b[2..9]=="[CDATA[") {
                             // parse <![CDATA[ ... ]]> strings
                            while(!buffer.has_CDEnd()) {
                                c = get();

                                if (c == EOF)
                                    break;

                                buffer.append(c);
                            }

                            DefaultHandler(buffer.str());

                            c = get();
                        }
                    } else {
                         // start tag
                        char[] tag = buffer.get_tag();

                        if (tag.length) {
                            XMLNode.AttributeMap attributes;
                            buffer.get_attributes(attributes);

                            StartElementHandler(tag.dup, attributes);

                            if (b[length-2] == '/')
                                EndElementHandler();
                        }

                        c = get();
                    }
                } else // b.length < 2
                    c = get();
            } else {
                buffer.append(c);

                 // read white space
                for(;;) {
                     // check for the encoding of the first line end
                    if (!_endl_defined)
                        if (c == '\n') {
                            _format._endl = "\n";
                            _endl_defined = true;
                        } else if (c == '\r') {
                            _format._endl = "\r\n";
                            _endl_defined = true;
                        }

                    c = get();

                    if (c == EOF)
                        break;

                    if (c == '<')
                        break;

                    buffer.append(c);
                }

                DefaultHandler(buffer.str());
            }

            buffer.reset();
        }

        return true; //TODO return false on invalid XML
    }

Here is the call graph for this function:

void xmlstorage::XMLReaderBase::read (  ) [inline, inherited]

Definition at line 1907 of file xmlstorage.d.

References xmlstorage::XMLError::_message.

Referenced by xmlstorage::XMLDoc::read().

    {
        if (!parse()) {
            XMLError error;

            error._message = "XML parsing error";
            //error._line = ;
            //error._column = ;

            _errors.push_back(error);
        }

        finish_read();
    }

Here is the caller graph for this function:

void xmlstorage::XMLReaderBase::StartElementHandler ( in char[]  name,
XMLNode.AttributeMap  attributes 
) [inline, protected, inherited]

notifications about XML start tag

Definition at line 2009 of file xmlstorage.d.

References xmlstorage::XMLNode::_attributes, and xmlstorage::version().

    {
        int i = 0;

         // search for content end leaving only white space for leading
        for(i=_content.length; i>0; --i)
            if (!isspace(cast(dchar)_content[i-1]))
                break;

        if (i > 0)
            if (_pos()._children.empty()) { // no children in last node?
                if (_last_tag == TAG.TAG_START)
                    _pos()._content ~= _content[0 .. i];
                else if (_last_tag == TAG.TAG_END)
                    _pos()._trailing ~= _content[0 .. i];
                else // TAG_NONE at root node
                    i = 0;
            } else
                _pos()._children.back()._trailing ~= _content[0 .. i];

        char[] leading;

        if (i < _content.length)
            leading = _content[i .. length];

        XMLNode node = new XMLNode(name, leading);

        _pos.add_down(node);

      version(XMLNODE_LOCATION) {
        node._location = get_location();
      }

        node._attributes = attributes;

        _last_tag = TAG.TAG_START;
        _content.length = 0;
    }

Here is the call graph for this function:

xmlstorage::XMLReaderBase::version ( XMLNODE_LOCATION   ) [inline, inherited]

Definition at line 1944 of file xmlstorage.d.

                            {

    char[] _display_path;   // character pointer for fast reference in XMLLocation

    XMLLocation get_location()
    {
        return new XMLLocation; //@TODO XMLLocation for XS-native
    }

  }
void xmlstorage::XMLReaderBase::XmlDeclHandler ( in char *[]  ver,
char *[]  encoding,
int  standalone 
) [inline, protected, inherited]

store XML version and encoding into XML reader

Definition at line 1997 of file xmlstorage.d.

    {
        if (ver)
            _format._version = *ver;

        if (encoding)
            _format._encoding = *encoding;

        _format._standalone = standalone;
    }

Member Data Documentation

char [] xmlstorage::XMLReaderBase::_content [protected, inherited]

Definition at line 1958 of file xmlstorage.d.

bool xmlstorage::XMLReaderBase::_endl_defined [protected, inherited]

Definition at line 1967 of file xmlstorage.d.

Definition at line 1963 of file xmlstorage.d.

Definition at line 1966 of file xmlstorage.d.

Stream xmlstorage::XMLReader::_in [protected]

Definition at line 2110 of file xmlstorage.d.

TAG xmlstorage::XMLReaderBase::_last_tag [protected, inherited]

Definition at line 1960 of file xmlstorage.d.

XMLPos xmlstorage::XMLReaderBase::_pos [protected, inherited]

Definition at line 1956 of file xmlstorage.d.

bool xmlstorage::XMLReaderBase::_utf8 [protected, inherited]

Definition at line 1984 of file xmlstorage.d.

Definition at line 1964 of file xmlstorage.d.


The documentation for this class was generated from the following file: