You may want to insert external program files into your DocBook documents to use as examples. That way you don't have to type them into your document and maintain them there. It would also be nice if you didn't have to escape the special XML characters such as <
and &
which are used in programming languages.
This can be done in two ways: with an XSLT extension in Saxon or Xalan, or with XInclude for xsltproc.
The stylesheets come with an XSLT extension function to insert text from a file and escape the XML markup characters. Such extension functions are available for Saxon and Xalan, but not currently for xsltproc. To enable this extension, you have to set two parameters, either in your customization layer or on the command line. The parameters are use.extensions=1
and textinsert.extension=1
. Both must be set for it to work. You must also make
sure the appropriate DocBook extensions file is included in your Java
CLASSPATH. See the Saxon or Xalan section in
the section “Installing an XSLT processor” for more on setting the
CLASSPATH.
Once the parameters and CLASSPATH are properly set, then you can use markup like this to insert an external text file:
<example><title>My program listing</title>
<programlisting><textobject><textdata
fileref="mycode.c" /></textobject></programlisting>
</example>
You can also use entityref
instead of fileref
so that you are referencing a system entity instead of a file pathname. Using a system entity provides one level of indirection, enabling you to change the declaration of the system entity in the DTD without having to edit the reference to it in the document. The system entity declaration must indicate the NDATA type as linespecific
(which is declared in the DTD), so the processor knows it is a text file. The following is an example of declaring a system entity and then referencing it.
<!DOCTYPE book SYSTEM "docbook.dtd" [ <!ENTITY code3 SYSTEM "codesamples/mycode.c" NDATA linespecific> ]> <book> ... <example><title>My program listing</title> <programlisting><textobject><textdata entityref="code3" /></textobject></programlisting> </example>
If for some reason the entity reference does not resolve, then your programlisting
will be blank.
If your DTD is earlier than version 4.2, then you can't put a textobject
directly inside a programlisting
. You have to use an imageobject
element inside a inlinemediaobject
element. And you must add a format="linespecific"
attribute to its imagedata
element, as in the following example.
For DocBook 4.1.2 DTD and earlier:
<programlisting><inlinemediaobject><imageobject><imagedata
fileref="mycode.c"
format="linespecific"/></imageobject></inlinemediaobject>
<programlisting>
Notice that the elements inside these programlisting
examples have no space or line breaks between elements, only between attributes. That's because spaces and line breaks between elements are always preserved inside programlisting
, so this style avoids introducing extraneous spaces in the output. You can break a line between attributes within an element's start tag.
If your output does not have the included text, then you need to check for these problems:
If instead of the code text you get an xlink
element in your output, then the two extension parameters described above have not been properly set.
If the two parameters are properly set, and you get a message about "No insertfile extension available.", then either you need to use Saxon or Xalan, or the CLASSPATH does not include the Saxon or Xalan extension file.
If you get a message "Cannot read file:...", then the textinsert extension is working, but the pathname is not resolving, or the file is unreadable by the process.
If you are using an XInclude-enabled processor such as xsltproc, then you can use an XInclude element instead of a textobject
element. The following is an example that accomplishes the same as the previous example:
<example><title>My program listing</title>
<programlisting><xi:include href="mycode.c" parse="text"
xmlns:xi="http://www.w3.org/2001/XInclude"/></programlisting>
</example>
The parse="text"
attribute ensures that any characters that might be misinterpreted as XML are properly escaped when the text is included. But using parse="text"
also means you cannot select part of the external file with XPointer syntax, because the file is not treated as XML (even if it happens to be XML).
Since the xi:include
element is not part of the standard DocBook DTD, you will get validation errors when you try to validate a document with such a programlisting
. However, you can add xi:include
to the DTD, as described in the section “DTD customizations for XIncludes”, to avoid such errors.
DocBook XSL: The Complete Guide - 3rd Edition | PDF version available | Copyright © 2002-2005 Sagehill Enterprises |