1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178
|
<html><head><meta http-equiv="Content-Type" content="text/html; charset=utf-8"><title>5.
How xmlformat Works
</title><meta name="generator" content="DocBook XSL Stylesheets V1.69.1"><link rel="start" href="index.html" title="
The xmlformat XML Document Formatter
"><link rel="up" href="index.html" title="
The xmlformat XML Document Formatter
"><link rel="prev" href="using-config-files.html" title="4.
Using Configuration Files
"><link rel="next" href="prerequisites.html" title="6.
Prerequisites
"></head><body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF"><div class="navheader"><table width="100%" summary="Navigation header"><tr><th colspan="3" align="center">5.
How <span><strong class="command">xmlformat</strong></span> Works
</th></tr><tr><td width="20%" align="left"><a accesskey="p" href="using-config-files.html">Prev</a> </td><th width="60%" align="center"> </th><td width="20%" align="right"> <a accesskey="n" href="prerequisites.html">Next</a></td></tr></table><hr></div><div class="sect1" lang="en"><div class="titlepage"><div><div><h2 class="title" style="clear: both"><a name="how-xmlformat-works"></a>5.
How <span><strong class="command">xmlformat</strong></span> Works
</h2></div></div></div><p>
Briefly, <span><strong class="command">xmlformat</strong></span> processes an XML document using
the following steps:
</p><div class="orderedlist"><ol type="1"><li><p>
Read the document into memory as a single string.
</p></li><li><p>
Parse the document into a list of tokens.
</p></li><li><p>
Convert the list of tokens into nodes in a tree structure, tagging each
node according to the token type.
</p></li><li><p>
Discard extraneous whitespace nodes and normalize text nodes. (The
meaning of "normalize" is described in <a href="doc-processing-model.html#text-handling" title="3.3.
Text Handling
">Section 3.3, “
Text Handling
”</a>.)
</p></li><li><p>
Process the tree to produce a single string representing the reformatted
document.
</p></li><li><p>
Print the string.
</p></li></ol></div><p>
<span><strong class="command">xmlformat</strong></span> is not an XSLT processor. In essence, all
it does is add or delete whitespace to control line breaking,
indentation, and text normalization.
</p><p>
<span><strong class="command">xmlformat</strong></span> uses the REX parser developed by Robert D.
Cameron (see <a href="references.html" title="7.
References
">Section 7, “
References
”</a>). REX performs a parse based
on a regular expression that operates on a string representing the XML
document. The parse produces a list of tokens. REX does a pure lexical
scan that performs no alteration of the text except to tokenize it. In
particular:
</p><div class="itemizedlist"><ul type="disc"><li><p>
REX doesn't normalize any whitespace, including line endings. This is
true for text elements, and for whitespace within tags (including
between attributes and within attribute values). Any normalization or
reformatting to be done is performed in later stages of
<span><strong class="command">xmlformat</strong></span> operation.
</p></li><li><p>
REX leaves entity references untouched. It doesn't try to resolve them.
This means it doesn't complain about undefined entities, which to my
mind is an advantage. (A pretty printer shouldn't have to read a DTD or
a schema.)
</p></li><li><p>
If the XML is malformed, errors can be detected easily: REX produces
error tokens that begin with "<" but do not end with ">".
</p></li></ul></div><p>
<span><strong class="command">xmlformat</strong></span> expects its input documents to be legal
XML. It does not consider fixing broken documents to be its job, so if
<span><strong class="command">xmlformat</strong></span> finds error tokens in the result produced
by REX, it lists them and exits.
</p><p>
Assuming the document contains no error tokens,
<span><strong class="command">xmlformat</strong></span> uses the token list to construct a tree
structure. It categorizes each token based on its initial characters:
</p><div class="informaltable"><table border="1"><colgroup><col><col></colgroup><thead><tr><th>Initial Characters</th><th>Token Type</th></tr></thead><tbody><tr><td><code class="literal"><!--</code></td><td>comment</td></tr><tr><td><code class="literal"><?</code></td><td>processing instruction (this includes the <code class="literal"><?xml?></code> instruction)</td></tr><tr><td><code class="literal"><!DOCTYPE</code></td><td><code class="literal">DOCTYPE</code> declaration</td></tr><tr><td><code class="literal"><![</code></td><td><code class="literal">CDATA</code> section</td></tr><tr><td><code class="literal"></</code></td><td>element closing tag</td></tr><tr><td><code class="literal"><</code></td><td>element opening tag</td></tr></tbody></table></div><p>
Anything token not beginning with one of the sequences shown in the
preceding table is a text token.
</p><p>
The token categorization determineas the node types of nodes in the
document tree. Each node has a label that identifies the node type:
</p><div class="informaltable"><table border="1"><colgroup><col><col></colgroup><thead><tr><th>Label</th><th>Node Type</th></tr></thead><tbody><tr><td><code class="literal">comment</code></td><td>comment node</td></tr><tr><td><code class="literal">pi</code></td><td>processing instruction node</td></tr><tr><td><code class="literal">DOCTYPE</code></td><td><code class="literal">DOCTYPE</code> declaration node</td></tr><tr><td><code class="literal">CDATA</code></td><td><code class="literal">CDATA</code> section node</td></tr><tr><td><code class="literal">elt</code></td><td>element node</td></tr><tr><td><code class="literal">text</code></td><td>text node</td></tr></tbody></table></div><p>
If the document is not well-formed, tree construction will fail. In this
case, <span><strong class="command">xmlformat</strong></span> displays one or more error messages
and exits. For example, this document is invalid:
</p><pre class="screen">
<p>This is a <strong>malformed document.</p>
</pre><p>
Running that document through <span><strong class="command">xmlformat</strong></span> produces the
following result:
</p><pre class="screen">
MISMATCH open (strong), close (p); malformed document?
Non-empty tag stack; malformed document?
Non-empty children stack; malformed document?
Cannot continue.
</pre><p>
That is admittedly cryptic, but remember that it's not
<span><strong class="command">xmlformat</strong></span>'s job to repair (or even diagnose) bad XML.
If a document is not well-formed, you may find Tidy a useful tool for
fixing it up.
</p><p>
Tokens of each type except element tokens correspond to single distinct
nodes in the document. Elements are more complex. They may consist of
multiple tokens, and may contain children:
</p><div class="itemizedlist"><ul type="disc"><li><p>
An element with a combined opening/closing tag (such as
<code class="literal"><abc/></code>) consists of a single token.
</p></li><li><p>
An element with separate opening and closing tags (such as
<code class="literal"><abc>...</abc></code>) consists of at least the
two tags, plus any children that appear between the tags.
</p></li></ul></div><p>
Element opening tag tokens include any attributes that are present,
because <span><strong class="command">xmlformat</strong></span> performs no tag reformatting. Tags
are preserved intact in the output, including any whitespace between
attributes or within attribute values.
</p><p>
In addition to the type value that labels a node as a given node type,
each node has content:
</p><div class="itemizedlist"><ul type="disc"><li><p>
For all node types except elements, the content is the text of the token
from which the node was created.
</p></li><li><p>
For element nodes, the content is the list of child nodes that appear
within the element. An empty element has an empty child node list. In
addition to the content, element nodes contain other information:
</p><div class="itemizedlist"><ul type="circle"><li><p>
The literal text of the opening and closing tags. If an element is
written in single-tag form (<code class="literal"><abc/></code>), the
closing tag is empty.
</p></li><li><p>
The element name that is present in the opening tag. (This is maintained
separately from the opening tag so that a pattern match need not be done
on the opening tag each time it's necessary to determine the element
name.)
</p></li></ul></div></li></ul></div><p>
After constructing the node tree, <span><strong class="command">xmlformat</strong></span> performs
two operations on it:
</p><div class="itemizedlist"><ul type="disc"><li><p>
The tree is "canonized" to normalize text nodes and to discard
extraneous whitespace nodes. A whitespace node is a text node consisting
of nothing but whitespace characters (space, tab, carriage return,
linefeed (newline)). Decisions about which whitespace nodes are
extraneous are based on the configuration options supplied to
<span><strong class="command">xmlformat</strong></span>.
</p></li><li><p>
The canonized tree is used to produce formatted output.
<span><strong class="command">xmlformat</strong></span> performs line-wrapping of element content,
and adds indentation and line breaks. Decisions about how to apply these
operations are based on the configuration options.
</p></li></ul></div><p>
Here's an example input document, representing a single-row table:
</p><pre class="screen">
<table>
<row>
<cell>1</cell><cell>2</cell>
<cell>3</cell>
</row></table>
</pre><p>
After reading this in and constructing the tree, the canonized output
looks like this:
</p><pre class="screen">
<table><row><cell>1</cell><cell>2</cell><cell>3</cell></row></table>
</pre><p>
The output after applying the default formatting options looks like
this:
</p><pre class="screen">
<table>
<row>
<cell>1</cell>
<cell>2</cell>
<cell>3</cell>
</row>
</table>
</pre></div><div class="navfooter"><hr><table width="100%" summary="Navigation footer"><tr><td width="40%" align="left"><a accesskey="p" href="using-config-files.html">Prev</a> </td><td width="20%" align="center"> </td><td width="40%" align="right"> <a accesskey="n" href="prerequisites.html">Next</a></td></tr><tr><td width="40%" align="left" valign="top">4.
Using Configuration Files
</td><td width="20%" align="center"><a accesskey="h" href="index.html">Home</a></td><td width="40%" align="right" valign="top"> 6.
Prerequisites
</td></tr></table></div></body></html>
|