W3C

XSL Transformations (XSLT) Specification
Version 1.0

W3C Working Draft 21 Apr 1999

This version:
http://www.w3.org/TR/1999/WD-xslt-19990421
http://www.w3.org/TR/1999/WD-xslt-19990421.xml
http://www.w3.org/TR/1999/WD-xslt-19990421.html
Latest version:
http://www.w3.org/TR/WD-xslt
Previous versions:
http://www.w3.org/TR/1998/WD-xsl-19981216
http://www.w3.org/TR/1998/WD-xsl-19980818
Editor:
James Clark <jjc@jclark.com>

Abstract

XSLT is a language for transforming XML documents into other XML documents.

XSLT is designed for use as part of XSL, which is a stylesheet language for XML. In addition to XSLT, XSL includes an XML vocabulary for specifying formatting. XSL specifies the styling of an XML document by using XSLT to describe how the document is transformed into another XML document that uses the formatting vocabulary.

XSLT is also designed to be used independently of XSL. However, XSLT is not intended as a completely general-purpose XML transformation language. Rather it is designed primarily for the kinds of transformation that are needed when XSLT is used as part of XSL.

Status of this document

This is a W3C Working Draft for review by W3C members and other interested parties. It is a draft document and may be updated, replaced, or obsoleted by other documents at any time. The material in this draft was previously part of the XSL Working Draft. The XSL Working Group will not allow early implementation to constrain its ability to make changes to this specification prior to final release. It is inappropriate to use W3C Working Drafts as reference material or to cite them as other than "work in progress". A list of current W3C working drafts can be found at http://www.w3.org/TR.

This draft is intended to be "feature complete". The Working Group plans to use future drafts to stabilize the current functionality; it does not intend to add any new functionality in version 1.0.

The XSL WG and the XML Linking WG have agreed to unify XSLT expressions and XPointers [XPointer]. A common core semantic model for querying has been agreed upon, and this draft follows this model (see [6.1 Location Paths]). However, further changes particularily in the syntax will probably be necessary.

This is part of the Style activity.

Comments may be sent to xsl-editors@w3.org; archives of the comments are available. Public discussion of XSL, including XSL Transformations, takes place on the XSL-List mailing list.

Table of contents

1. Introduction
2. Stylesheet Structure
3. Forwards-compatible Processing
4. Data Model
    4.1 Root Node
    4.2 Element Nodes
        4.2.1 Unique IDs
        4.2.2 Base URI
    4.3 Attribute Nodes
    4.4 Namespace Nodes
    4.5 Processing Instruction Nodes
    4.6 Comment Nodes
    4.7 Text Nodes
    4.8 Whitespace Stripping
5. Using the Result Tree
6. Expressions and Patterns
    6.1 Location Paths
        6.1.1 Axes
        6.1.2 Node Tests
        6.1.3 Predicates
        6.1.4 Abbreviated Syntax
    6.2 Expressions
        6.2.1 Basics
        6.2.2 Node-sets
        6.2.3 Booleans
        6.2.4 Numbers
        6.2.5 Strings
        6.2.6 Result Tree Fragments
        6.2.7 Extension Functions
        6.2.8 System Functions
        6.2.9 Lexical Structure
    6.3 Patterns
    6.4 Declarations
        6.4.1 Declaring Keys
        6.4.2 Declaring Extension Functions
        6.4.3 Declaring Locales
7. Template Rules
    7.1 Processing Model
    7.2 Defining Template Rules
    7.3 Applying Template Rules
    7.4 Conflict Resolution for Template Rules
    7.5 Built-in Template Rules
    7.6 Modes
8. Named Templates
9. Creating the Result Tree
    9.1 Creating Elements and Attributes
        9.1.1 Literal Result Elements
        9.1.2 Creating Elements with xsl:element
        9.1.3 Creating Attributes with xsl:attribute
        9.1.4 Named Attribute Sets
    9.2 Creating Text
    9.3 Creating Processing Instructions
    9.4 Creating Comments
    9.5 Copying
    9.6 Computing Generated Text
        9.6.1 Generating Text with xsl:value-of
        9.6.2 Attribute Value Templates
    9.7 Numbering
        9.7.1 Number to String Conversion Attributes
10. Repetition
11. Conditional Processing
    11.1 Conditional Processing with xsl:if
    11.2 Conditional Processing with xsl:choose
12. Sorting
13. Variables and Parameters
14. Messages
15. Combining Stylesheets
    15.1 Stylesheet Import
    15.2 Stylesheet Inclusion
    15.3 Embedding Stylesheets

Appendices

A. DTD Fragment for XSLT Stylesheets
B. References
    B.1 Normative References
    B.2 Other References
C. Examples
    A Formatting Objects Example
    B XHTML Example
D. Acknowledgements
E. Changes from Previous Public Working Draft

1. Introduction

A transformation expressed in XSLT describes rules for transforming a source tree into a result tree. The transformation is achieved by associating patterns with templates. A pattern is matched against elements in the source tree. A template is instantiated to create part of the result tree. The result tree is separate from the source tree. The structure of the result tree can be completely different from the structure of the source tree. In constructing the result tree, elements from the source tree can be filtered and reordered, and arbitrary structure can be added.

A transformation expressed in XSLT is called a stylesheet. This is because, in the case when XSLT is transforming into the XSL formatting vocabulary, the transformation functions as a stylesheet.

This document does not specify how an XSLT stylesheet is associated with an XML document. It is recommended that XSL processors support the mechanism described in [XML Stylesheet].

A stylesheet contains a set of template rules. A template rule has two parts: a pattern which is matched against nodes in the source tree and a template which can be instantiated to form part of the result tree. This allows a stylesheet to be applicable to a wide class of documents that have similar source tree structures.

A template is instantiated for a particular source element to create part of the result tree. A template can contain elements that specify literal result element structure. A template can also contain elements that are instructions for creating result tree fragments. When a template is instantiated, each instruction is executed and replaced by the result tree fragment that it creates. Instructions can select and process descendant source elements. Processing a descendant element creates a result tree fragment by finding the applicable template rule and instantiating its template. Note that elements are only processed when they have been selected by the execution of an instruction. The result tree is constructed by finding the template rule for the root node and instantiating its template.

In the process of finding the applicable template rule, more than one template rule may have a pattern that matches a given element. However, only one template rule will be applied. The method for deciding which template rule to apply is described in [7.4 Conflict Resolution for Template Rules].

XSLT uses XML namespaces [XML Names] to distinguish elements that are instructions to the XSLT processor from elements that specify literal result tree structure. Instruction elements all belong to the XSLT namespace. The examples in this document use a prefix of xsl: for elements in the XSLT namespace.

XSLT includes an expression language (see [6 Expressions and Patterns]) that is used for selecting elements for processing, for conditional processing and for generating text. The expression language is not a complete programming language. XSLT provides an extension mechanism to allow access from the expression language to a complete programming language such as ECMAScript or Java. XSLT does not require support for any programming language. Therefore XSLT stylesheets that must be portable across all XSLT implementations cannot depend on this extension mechanism.

2. Stylesheet Structure

A stylesheet is represented by an xsl:stylesheet element in an XML document. xsl:transform is allowed as a synonym for xsl:stylesheet.

XSLT processors must use the XML namespaces mechanism [XML Names] for both source documents and stylesheets. All XSLT defined elements, that is those specified in this document with a prefix of xsl:, will only be recognized by the XSLT processor if they belong to a namespace with the URI http://www.w3.org/XSL/Transform/1.0; XSLT defined elements are recognized only in the stylesheet not in the source document.

The xsl:stylesheet element may contain the following types of elements:

This example shows the structure of a stylesheet. Ellipses (...) indicate where attribute values or content have been omitted. Although this example shows one of each type of allowed element, stylesheets may contain zero or more of each of these elements.

<?xml version="1.0"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/XSL/Transform/1.0">
  <xsl:import href="..."/>

  <xsl:include href="..."/>

  <xsl:strip-space elements="..."/>
  
  <xsl:preserve-space elements="..."/>

  <xsl:key name="..." match="..." use="..."/>

  <xsl:functions ns="...">
  ...
  </xsl:functions>

  <xsl:locale name="...">
  ...
  </xsl:locale>

  <xsl:attribute-set name="...">
  ...
  </xsl:attribute-set>

  <xsl:variable name="...">...</xsl:variable>

  <xsl:param-variable name="...">...</xsl:param-variable>

  <xsl:template match="...">
    ...
  </xsl:template>

  <xsl:template name="...">
   ...
  </xsl:template>

</xsl:stylesheet>

The order in which the children of the xsl:stylesheet element occur is not significant except for xsl:import elements and for error recovery. Users are free to order the elements as they prefer, and stylesheet creation tools need not provide control over the order in which the elements occur.

3. Forwards-compatible Processing

An XSLT processor must treat any namespace whose URI starts with the http://www.w3.org/XSL/Transform/ in the same way as the XSLT 1.0 namespace (http://www.w3.org/XSL/Transform/1.0) except that it must recover from errors as follows:

Ed. Note: What happens with stylesheets that mix XSLT namespaces with different versions?

Thus any XSLT 1.0 processor must be able to process the following stylesheet without error:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/XSL/Transform/1.1">
  <xsl:template name="/">
    <xsl:choose>
      <xsl:when test="system-property('xsl:version') >= 1.1">
        <xsl:exciting-new-1.1-feature/>
      </xsl:when>
      <xsl:otherwise>
        <p>Sorry this stylesheet requires XSLT 1.1.</p>
      </xsl:otherwise>
    </xsl:choose>
  </xsl:template>
</xsl:stylesheet>

4. Data Model

XSLT operates on an XML document, whether a stylesheet or a source document, as a tree. Any two stylesheets or source documents that have the same tree will be processed the same by XSLT. The XML document resulting from the tree construction process is also a tree. This section describes how XSLT models an XML document as a tree. This model is conceptual only and does not mandate any particular implementation.

XML documents operated on by XSLT must conform to the XML namespaces specification [XML Names].

The tree contains nodes. There are seven kinds of node:

Neither processing instruction nodes nor comment nodes are included in the tree for the stylesheet.

For every type of node there is a way of determining a string value for a node of that type. For some types of node, the value is part of the node; for other types of node, the value is computed from the value of descendant nodes.

Issue (data-entity): Should XSLT provide support for external data entities and notations?

Issue (entity-ref): Should XSLT provide support for entity references?

Issue (dtd): Should XSLT provide support for DTDs in the data model?

4.1 Root Node

The root node is the root of the tree. It does not occur anywhere else in the tree. It has a single child which is the element node for the document element of the document.

The value of the root node is the value of the document element.

4.2 Element Nodes

There is an element node for every element in the document. An element has an expanded name consisting of a local name and a possibly null URI reference (see [XML Names]); the URI reference will be null if the element type name has no prefix and there is no default namespace in scope. A relative URI reference should be resolved into an absolute URI during namespace processing.

The children of an element node are the element nodes, comment nodes, processing instruction nodes and text nodes for its content. Entity references to both internal and external entities are expanded. Character references are resolved.

The descendants of an element node are the children of the element node and the descendants of the children that are element nodes.

The value of an element node is the string that results from concatenating all characters that are descendants of the element node in the order in which they occur in the document.

The set of all element nodes in a document can be ordered according to the order of the start-tags of the elements in the document; this is known as document order.

Ed. Note: Need a definition of document order that handles arbitrary node types, including attributes.

4.2.1 Unique IDs

An element object may have a unique identifier (ID). This is the value of the attribute which is declared in the DTD as type ID. No two elements in a document may have the same unique ID. If an XML processor reports two elements in a document as having the same unique ID (which is possible only if the document is invalid) then the second element must be treated as not having a unique ID.

NOTE: If a document does not have a DTD, then no element in the document will have a unique ID.

4.2.2 Base URI

An element node also has an associated URI called its base URI which is used for resolving attribute values that represent relative URIs into absolute URIs. If an element occurs in an external entity, the base URI of that element is the URI of the external entity. Otherwise the base URI is the base URI of the document.

4.3 Attribute Nodes

Each element node has an associated set of attribute nodes. A defaulted attribute is treated the same as a specified attribute. If an attribute was declared for the element type in the DTD, but the default was declared as #IMPLIED, and the attribute was not specified on the element, then the element's attribute set does not contain a node for the attribute.

An attribute node has an expanded name and has a string value. The expanded name consists of a local name and a possibly null URI (see [XML Names]); the URI will be null if the specified attribute name did not have a prefix. The value is the normalized value as specified by the XML Recommendation [XML]. An attribute whose normalized value is a zero-length string is not treated specially: it results in an attribute node whose value is a zero-length string.

There are no attribute nodes for attributes that declare namespaces (see [XML Names]).

Issue (external-dtd): Should we specify something about how we expect XSLT processors to process external DTDs and parameter entities? For example, what happens if an attribute default is declared in an external DTD?

4.4 Namespace Nodes

Each element has an associated set of namespace nodes, one for each namespace prefix that is in scope for the element and one for the default namespace if one is in scope for the element. This means that an element will have a namespace node:

A namespace node has a name which is a string giving the prefix. This is empty if the namespace node is for the default namespace. A namespace node also has a value which is the namespace URI. If the namespace declaration specifies a relative URI, then the resolved absolute URI is used as the value.

When writing an element node in the result tree out as XML, an XSLT processor must add sufficient namespace-declaring attributes to the start-tag to ensure that if a tree were recreated from the XML, then the set of namespace nodes on the element node in the recreated tree would be equal to or a superset of the set of namespace nodes of the element node in the result tree.

NOTE: The semantics of a document type may treat parts of attribute values or data content as namespace prefixes. The presence of namespace nodes ensures that the semantics can be preserved when the tree is written out as XML.

4.5 Processing Instruction Nodes

There is a processing instruction node for every processing instruction.

Ed. Note: What about processing instructions in the internal subset or elsewhere in the DTD?

A processing instruction has a name. This is a string equal to the processing instruction's target. It also has a value. This is a string equal to the part of the processing instruction following the target and any whitespace. It does not include the terminating ?>.

4.6 Comment Nodes

There is a comment node for every comment.

Ed. Note: What about comments in the internal subset or elsewhere in the DTD?

A comment has a value. This is a string equal to the text of the comment not including the opening <!-- or the closing -->.

4.7 Text Nodes

Character data is grouped into text nodes. As much character data as possible is grouped into each text node: a text node never has an immediately following or preceding sibling that is a text node. The value of a text node is the character data.

Each character within a CDATA section is treated as character data. Thus <![CDATA[<]]> in the source document will treated the same as &lt;. Both will result in a single < character in a text node in the tree.

NOTE: When a text node that contains a < character is written out as XML, the < character must be escaped by, for example, using &lt;, or including it in a CDATA section.

Characters inside comments or processing instructions are not character data. Line-endings in external entities are normalized to #xA as specified in the XML Recommendation [XML].

4.8 Whitespace Stripping

After the tree has been constructed, but before it is otherwise processed by XSLT, some text nodes may be stripped. The stripping process takes as input a set of element types for which whitespace must be preserved. The stripping process is applied to both stylesheets and source documents, but the set of whitespace-preserving element types is determined differently for stylesheets and for source documents.

A text node is preserved if any of the following apply:

Otherwise the text node is stripped.

The xml:space attributes are not stripped from the tree.

NOTE: This implies that if an xml:space attribute is specified on a literal result element, it will be included in the result.

For stylesheets, the set of whitespace-preserving element types consists of just xsl:text.

For source documents, the set of whitespace-preserving element types is determined using the stylesheet as follows:

Ed. Note: Clarify how these declarations interact with each other and with xsl:import.

5. Using the Result Tree

The xsl:stylesheet element has an optional result-ns attribute; the value must be a namespace prefix. If there is a namespace declared as the default namespace, then an empty string may be used as the value to specify that the default namespace is the result namespace.

The result-ns attribute is a hint to the XSLT processor that it should do something with the result tree other than simply output it as XML. XSLT processors are not required to pay attention to the hint and may simply output the result tree as XML. If the result-ns attribute is not specified, then the result tree must be output as XML. If the result-ns attribute is specified, all elements in the result tree must belong to the namespace identified by this prefix (the result namespace).

When an XSLT processor outputs the result tree as a sequence of bytes that represents the result tree in XML, it must do so in such a way that the sequence of bytes is a well-formed XML document conforming to the XML Namespaces Recommendation [XML Names] and that if a new tree was constructed from the sequence of bytes as specified in [4 Data Model], the new tree would be the same as the result tree, with the following possible exceptions:

A result namespace of http://www.w3.org/XSL/Format/1.0 indicates that the result tree should be interpreted according to the semantics defined in [XSL]. XSL requires that XSL processors respect this hint. The examples in this document use the fo: prefix for this namespace.

A result namespace of http://www.w3.org/TR/REC-html40 indicates that the result tree should be output as HTML that conforms to the HTML 4.0 Recommendation rather than as XML; for example,

<xsl:stylesheet
  xmlns:xsl="http://www.w3.org/XSL/Transform/1.0"
  xmlns="http://www.w3.org/TR/REC-html40"
  result-ns="">

<xsl:template match="/">
  <html>
   <xsl:apply-templates/>
  </html>
</xsl:template>

...

</xsl:stylesheet>

The xsl:stylesheet element can include an indent-result attribute with values yes or no. If the stylesheet specifies indent-result="yes", then the XSLT processor may add whitespace to the result tree (possibly based on whitespace stripped from either the source document or the stylesheet) in order to indent the result nicely; if indent-result="no", it must not add any whitespace to the result. When adding whitespace with indent-result="yes", the XSLT processor can use any algorithm provided that the result is the same as the result with indent-result="no" after whitespace is stripped from both using the process described with the set of whitespace-preserving element types consisting of just xsl:text.

6. Expressions and Patterns

Ed. Note: The XSL WG and the XML Linking WG have agreed to unify XSLT expressions and XPointers. A common core semantic model for querying has been agreed upon, and this draft follows this model. However, further changes particularily in the syntax will probably be necessary.

Expressions are used in XSLT for a variety of purposes including:

An expression is evaluated to yield an object which has one of the following types:

Expression evaluation occurs with respect to a context, which consists of:

The context node is always a member of the context node list. The variable bindings consist of a mapping from variable names to variable values. The value of a variable is an object which can have any of the types which are possible for the value of an expression.

The variable bindings, node key function, extension functions and namespace declarations used to evaluate a subexpression are always the same as those used to evaluate the containing expression. The context node and context node list used to evaluate a subexpression is sometimes different from the context node and context node list used to evaluate the containing expression. When the evaluation of a kind of expression is described, it will always be explicitly stated if the context node and node list change for the evaluation of subexpressions; if nothing is said about the context node and context node list, they remain unchanged for the evaluation of subexpressions of that kind of expression.

The node key function takes a pair of strings (a key name and a key value) and a document and returns a set of nodes (the nodes in the document that have a key with the specified name and value).

In XSLT, expressions occur in attribute values. The grammar specified in this section applies to the attribute value after XML 1.0 normalization. So, for example, if the grammar uses the character < this must not appear in the XML source for the stylesheet as < but must be quoted according to XML 1.0 rules by, for example, entering it as &lt;.

A top-level expression (an expression not occurring within an expression) gets its context as follows:

One important kind of expression is a location path. A location path selects a set of nodes relative to the context node. The result of evaluating an expression that is a location path is the node-set containing the nodes selected by the location path. Location paths can recursively contain expressions which are used to filter lists of nodes.

Certain contexts in XSLT make use of a pattern. A pattern specifies a set of conditions on a node. A node that satisfies the conditions matches the pattern; a node that does not satisfy the conditions does not match the pattern. The syntax for patterns is a subset of the syntax for expressions. In particular location paths that meet certain restrictions can be used as patterns. An expression that is also a pattern always evaluates to an object of type node-set. A node matches a pattern if the node is a member of the result of evaluating the pattern as an expression with respect to some possible context; the possible contexts are those whose context node is the node being matched or one of its ancestors.

In the following grammar, the nonterminals QName and NCName are defined in [XML Names], and S is defined in [XML].

Expressions (including patterns and location paths) are parsed by first dividing up the character string to be parsed into tokens and then parsing the resulting sequence of tokens. Whitespace can be freely used between tokens. The tokenization process is described in [6.2.9 Lexical Structure].

6.1 Location Paths

Every location path can be expressed using a straightforward but rather verbose syntax. There are also a number of syntactic abbreviations that allow common cases to be expressed concisely. This section will explain the semantics of location paths using the unabbreviated syntax. The abbreviated syntax will then be explained by showing how it expands into the unabbreviated syntax (see [6.1.4 Abbreviated Syntax]).

Here are some examples of location paths using the unabbreviated syntax:

There are two kinds of location path: relative location paths and absolute location paths.

A relative location path consists of a sequence of one or more location steps separated by /. The steps in a relative location path are composed together from left to right. Each step in turn selects a set of nodes relative to a context node. An initial sequence of steps is composed together with a following step as follows. The initial sequence of steps selects a set of nodes relative to a context node. Each node in that set is used as a context node for the following step. The sets of nodes identified by the second step are unioned together. The set of nodes identified by the composition of the steps is this union. For example, from-children(div)/from-children(para) selects the para element children of the div element children of the context node, or, in other words, the para element grandchildren that have div parents.

An absolute location path consists of / optionally followed by a relative location path. A / by itself selects the root node of the document containing the context node. If it is followed by a relative location path, then the location path selects the set of nodes that would be selected by the relative location path relative to the root node of the document containing the context node.

A location step consists of

The axis identifier selects an initial list of nodes relative to the context node. The initial list of nodes is filtered first by the node test; the result of filtering by the node test is then filtered by the first predicate; the result of that is then filtered by the next predicate and so on. The node test selects nodes from the initial list based on the node type and node name. Each predicate selects nodes that satisfy a condition specified by an arbitrary expression. The result of the location step is the set of nodes that are members of the list that results from filtering the initial list by the node test and all the predicates. Note that although a location step selects a set of nodes, an axis selects a list of nodes and the predicates operate on a list of nodes.

The axis identifier is followed by the node test and predicates in parentheses. For example, from-descendants(para) selects the descendants of the context node that are para elements: from-descendants specifies the axis, and para is a test that is true for elements with name para. Each predicate is specified as an expression in square brackets.

Location Paths
[1]    LocationPath    ::=    RelativeLocationPath
| AbsoluteLocationPath
[2]    AbsoluteLocationPath    ::=    '/' RelativeLocationPath?
| AbbreviatedAbsoluteLocationPath
[3]    RelativeLocationPath    ::=    Step
| RelativeLocationPath '/' Step
| AbbreviatedRelativeLocationPath
[4]    Step    ::=    AxisIdentifier '(' NodeTest Predicate* ')'
| AbbreviatedStep

6.1.1 Axes

An axis identifies a list of nodes based on the kind of tree relationship that the nodes have to the context node. For example, the children of the context node are one axis, the ancestors of the context node are another axis. Note that an axis identifies an ordered list, not a set. The order of nodes in an axis is in the direction away from the context node.

The following axes are defined:

In an axis identifier the name of the axis is preceded by from- to distinguish it from a function name.

Axes
[5]    AxisIdentifier    ::=    'from-ancestors'
| 'from-ancestors-or-self'
| 'from-attributes'
| 'from-children'
| 'from-descendants'
| 'from-descendants-or-self'
| 'from-following'
| 'from-following-siblings'
| 'from-parent'
| 'from-preceding'
| 'from-preceding-siblings'
| 'from-self'

6.1.2 Node Tests

A node test that is a QName tests whether the node is an element or attribute with the specified name. For example, from-attributes(href) selects the href attribute of the context node; if the context node has no href attribute, it will select an empty set of nodes.

A QName in the node test is expanded into a local name and a possibly null URI. This expansion is done using the namespace declarations from the expression context. This is the same way expansion is done for element type names in start and end-tags except that the default namespace declared with xmlns is not used: if the QName does not have a prefix, then the URI is null (this is the same way attribute names are expanded). The expanded names are then compared for equality. Two expanded names are equal if they have the same local part, and either both have no URI or both have the same URI.

A node test * is true for any element or attribute node. For example, from-children(*) will select all element children of the context node, and from-attributes(*) will select all attributes of the context node.

A node test can have the form NCName:*. In this case the prefix is expanded in the same way as with a QName using the context namespace declarations. The node test will be true for an element or attribute whose expanded name has the URI to which the prefix expands, whatever the local part of the name.

The node test text() is true for any text node. For example from-children(text()) will select the text node children of the context node. Similarly, the node test comment() is true for any comment node, and the node test pi() is true for any processing instruction. The pi() test may have an argument that is Literal; in this case it is true for any processing instruction that has a name equal to the value of the Literal.

A node test node() is true for any node.

[6]    NodeTest    ::=    WildcardName
| NodeType '(' ')'
| 'pi' '(' Literal ')'

6.1.3 Predicates

A predicate filters a list of nodes to produce a new list of nodes. For each node in the list to be filtered, the PredicateExpr is evaluated with that node as the context node and with the complete list of nodes to be filtered as the context node list; if PredicateExpr evaluates to true for that node, the node is included in the new list; otherwise it is not included.

A PredicateExpr is evaluated by evaluating the Expr and converting the result to a boolean. If the result is a number, the result will be converted to true if the number is equal to the position of the context node in the context node list and will be converted to false otherwise; if the result is not a number, then the result will be converted as if by a call to the boolean() function. Thus a location path para[3] is equivalent to para[position()=3].

Predicates
[7]    Predicate    ::=    '[' PredicateExpr ']'
[8]    PredicateExpr    ::=    Expr

6.1.4 Abbreviated Syntax

Here are some examples of location paths using abbreviated syntax:

The most important abbreviation is that when the axis is the children axis, the from-children and surrounding parentheses can be omitted. In effect the children axis is the default axis. For example, a location path div/para is short for from-children(div)/from-children(para).

There's also an abbreviation for the attributes axis. Instead of using from-attributes and parentheses around the node test, the node test can be preceded by @ to indicate the attributes axis. For example, a location path para[@type="warning"] is short for from-children(para[from-attributes(type)="warning"]) and so selects para children with a type attribute with value equal to warning.

// is short for /from-descendants-or-self(node())/. For example, //para is short for /from-descendants-or-self(node())/from-children(para) and so will select any para element in the document (even a para element that is a document element will be selected by //para since the document element node is a child of the root node); div//para is short for div/from-descendants-or-self(node())/from-children(para) and so will select all para descendants of div children.

A location step of . is short for from-self(node()). This is particularly useful in conjunction with //. For example, the location path .//para is short for

from-self(node())/from-descendants-or-self(node())/from-children(para)

and so will select all para descendant elements of the context node.

Similarly a location step of .. is short for from-parent(node()). For example, ../title is short for from-parent(node())/from-children(title) and so will select the title children of the parent of the context node.

Abbreviations
[9]    AbbreviatedAbsoluteLocationPath    ::=    '//' RelativeLocationPath
[10]    AbbreviatedRelativeLocationPath    ::=    RelativeLocationPath '//' Step
[11]    AbbreviatedStep    ::=    AbbreviatedNodeTestStep
| '.'
| '..'
[12]    AbbreviatedNodeTestStep    ::=    '@'? NodeTest Predicate*

6.2 Expressions

6.2.1 Basics

A VariableReference evaluates to the value to which the variable name is bound in the set of variable bindings in the context.

Parentheses may be used for grouping.

[13]    Expr    ::=    OrExpr
[14]    PrimaryExpr    ::=    VariableReference
| '(' Expr ')'
| Literal
| Number
| FunctionCall
[15]    FunctionCall    ::=    NodeSetFunctionCall
| BooleanFunctionCall
| StringFunctionCall
| NumberFunctionCall
| SystemFunctionCall
| ExtensionFunctionCall

6.2.2 Node-sets

A location path can be used as an expression. The expression returns the set of nodes selected by the path.

The | operator computes the union of its operands which must be node-sets.

Square brackets are used to filter expressions in the same way that they are used in location paths. It is an error if the expression to be filtered does not evaluate to a node-set. The context node list used for evaluating the expression in square brackets is the node-set to be filtered listed in document order.

The / operator and // operators combine an arbitrary expression and a relative location path. It is an error if the expression does not evaluate to a node-set. The / operator does composition in the same way as when / is used in a location path. As in location paths, // is short for /from-descendants-or-self(node())/.

There are no types of objects that can be converted to node-sets. It is an error if evaluating a NodeSetExpr yields an object that is not a node-set.

The last() function returns the number of nodes in the context node list. The position() function returns the position of the context node in the context node list. The first position is 1, and so the last position will be equal to last().

The count() function returns the number of nodes in the argument node-set.

The id() and idref() functions select elements by their unique ID (see [4.2.1 Unique IDs]). id() converts its argument to a string and returns a node-set containing the element in the same document as the context node with unique ID equal to that string, if there is such an element, and otherwise returns an empty node-set. idref() requires that its argument be a node-set; for each node in the node-set, the value is split into a whitespace-separated list of tokens; idref() returns a node-set containing the elements in the same document as the context node that have a unique ID equal to any of the tokens in the value of any of the nodes in the node-set. For example,

Ed. Note: No way to get an ID in another document. Can workaround with xsl:for-each. Maybe add optional second argument which gives document.

Issue (id-inverse): Should there be a way to get back from an element to the elements that reference it (eg by IDREF attributes)?

The key() and keyref() functions select a set of nodes using the node key function in the expression evaluation context. Both functions have a string as the first argument that specifies the name of the key and have an expression as the second argument. key() has a second argument that is a string and returns a node-set containing the nodes in the same document as the context node that have a value for the named key equal to this string. keyref() has a second argument that is a node-set and returns a node-set containing the nodes in the same document as the context node that have a value for the named key equal to the value of any of the nodes in the argument node-set. See [6.4.1 Declaring Keys] for how to declare a key.

The doc() and docref() functions allow access to XML documents other than the initial source document. They both rely on the ability to treat a string as a URI reference that is mapped to a node-set; this mapping always takes places relative to a node that can be used to resolve a relative URI into an absolute URI. If the URI reference does not contain a fragment identifier, then it will be mapped to a node-set containing the root node in a tree representing the XML document whose document entity is the resource identified by the URI. If the URI reference contains a fragment identifier, then it will first map the URI to a tree representing the XML document whose document entity is the resource identified by the URI and then use the fragment identifier to select a set of nodes in that tree; the semantics of the fragment identifier is dependant on media type of the result of retrieving the URI. doc() takes a string argument which it treats as a URI reference which is mapped to a node-set relative to the element in the stylesheet containing the expression. Note that a zero-length URI reference is a reference to the document relative to which the URI reference is being resolved; thus doc("") refers to the root node of the stylesheet; the tree representation of the stylesheet is exactly the same as if the XML document containing the stylesheet was the initial source document. docref() takes a node-set argument; for each node in the node-set, docref() treats the value of the node as a URI reference that is mapped to a node-set relative to that same node; docref() returns the union of the resulting node-sets.

Ed. Note: What if the fragment identifier identifies something that isn't a set of nodes (eg a span or a substring within a text node)? What are the allowed media types for the returned data? What is document order for node sets including nodes from multiple documents?

The local-part() function returns a string containing the local part of the name of the first node in the argument node-set. If the node-set is empty or the first node has no name, an empty string is returned. If the argument is omitted it defaults to the context node.

The namespace() function returns a string containing namespace of the name of the first node in the argument node-set. If the node-set is empty or the first node has no name or the name has no namespace, an empty string is returned. If the argument is omitted it defaults to the context node.

The qname() function returns a string containing a QName representing the name of the first node in the argument. The QName must represent the name with respect to the namespace declarations in effect on the node whose name is being represented. Typically this will be the form in which the name occurred in the XML source. This need not be the case if there are namespace declarations in effect on the node that associate multiple prefixes with the same namespace. However, an implementation may include information about the original prefix in its representation of nodes; in this case an implementation can ensure that the returned string is always the same as the QName used in the XML source. If the argument it omitted it defaults to the context node.

The generate-id() function returns a string that can be used as a unique identifier for the first node in the argument node-set. The unique identifier must consist of ASCII alphanumeric characters and must start with an alphabetic character. An implementation is free to generate an identifier in any convenient way provided that it always generates the same identifier for the same node and that different identifiers are always generated from different nodes. An implementation is under no obligation to generate the same identifiers each time a a document is transformed. If the argument node-set is empty, the empty string is returned. If the argument is omitted, it defaults to the context node.

[16]    NodeSetExpr    ::=    Expr
[17]    UnionExpr    ::=    PathExpr
| UnionExpr '|' PathExpr
[18]    PathExpr    ::=    LocationPath
| FilterExpr
| FilterExpr '/' RelativeLocationPath
| FilterExpr '//' RelativeLocationPath
[19]    FilterExpr    ::=    PrimaryExpr
| FilterExpr Predicate
[20]    NodeSetFunctionCall    ::=    'last' '(' ')'
| 'position' '(' ')'
| 'count' '(' NodeSetExpr ')'
| 'id' '(' StringExpr ')'
| 'idref' '(' NodeSetExpr ')'
| 'key' '(' StringExpr ',' StringExpr ')'
| 'keyref' '(' StringExpr ',' NodeSetExpr ')'
| 'doc' '(' StringExpr ')'
| 'docref' '(' NodeSetExpr ')'
| 'local-part' '(' NodeSetExpr? ')'
| 'namespace' '(' NodeSetExpr? ')'
| 'qname' '(' NodeSetExpr? ')'
| 'generate-id' '(' NodeSetExpr? ')'

6.2.3 Booleans

An object of type boolean can have two values, true and false.

The boolean() function converts its argument to a boolean as follows:

If the argument is omitted, it defaults to the context node.

A BooleanExpr is evaluated by converting the result of evaluating the Expr to a boolean as if by a call to the boolean() function.

An = expression is evaluated as follows. If at least one operand is a boolean, then each operand is converted to a boolean as if by applying the boolean() function and the operands are compared as booleans. Otherwise, if at least one operand is a number, then each operand is converted to a number as if by applying the number() function and the operands are compared as numbers; positive and negative zero compare equal. Otherwise both operands are converted to strings as if by applying the string() function and the operands are compared as strings; two strings are equal if they contain the same sequence of UCS characters.

A <, >, <= or >= expression is evaluated by first converting each operand to a number as if by a call to the number() function and then comparing the two numbers.

Issue (node-set-comparision): What should the semantics of comparison operators be when either or both of the operands are node-sets? Should there be an "any" or "all" semantic?

An or expression is evaluated by evaluating each operand and converting its value to a boolean. The result is true if either value is true and false otherwise.

An and expression is evaluated by evaluating each operand and converting its value to a boolean. The result is true if both values are true and false otherwise.

The not() function returns true if its argument is false, and false otherwise.

The true() function returns true.

The false() function returns false.

The lang() function returns true or false depending on whether the language of the context node as specified by xml:lang attributes is the same as or is a sublanguage of the language specified by the argument string. The language of the context node is determined by the value of the xml:lang attribute on the context node, or, if the context node has no xml:lang attribute, by the value of the xml:lang attribute on the nearest ancestor of the context node that has an xml:lang attribute. If there is no such attribute, then lang() returns false. If there is such an attribute, then lang() returns true if the attribute value is equal to the argument ignoring case, or if there is some suffix starting with - such that the attribute value is equal to the argument ignoring that suffix of the attribute value and ignoring case. For example, lang("en") would return true if the context node is any of these five elements:

<para xml:lang="en"/>
<div xml:lang="en"><para/></div>
<para xml:lang="EN"/>
<para xml:lang="en-us"/>
[21]    BooleanExpr    ::=    Expr
[22]    OrExpr    ::=    AndExpr
| OrExpr 'or' AndExpr
[23]    AndExpr    ::=    EqualityExpr
| AndExpr 'and' EqualityExpr
[24]    EqualityExpr    ::=    RelationalExpr
| EqualityExpr '=' RelationalExpr
[25]    RelationalExpr    ::=    AdditiveExpr
| RelationalExpr '<' AdditiveExpr
| RelationalExpr '>' AdditiveExpr
| RelationalExpr '<=' AdditiveExpr
| RelationalExpr '>=' AdditiveExpr
[26]    BooleanFunctionCall    ::=    'not' '(' BooleanExpr ')'
| 'true' '(' ')'
| 'false' '(' ')'
| 'boolean' '(' Expr? ')'
| 'lang' '(' StringExpr ')'

6.2.4 Numbers

A number represents a floating point number. A number can have any double-precision 64-bit format IEEE 754 value. These include a special "Not-a-Number" (NaN) value, positive and negative infinity, and positive and negative zero.

A NumberExpr is evaluated by converting the result of evaluating the Expr to a number as if by a call to the number() function.

The number() function converts its argument to a number as follows:

If the argument is omitted, it defaults to the context node.

The div operator performs floating point division according to IEEE 754.

The quo operator performs a floating point division and then truncates the result to an integer. For example,

The mod operator returns the remainder from the quo operation. For example,

NOTE: This is the same as the % operator in Java and ECMAScript.
NOTE: This is not the same as the IEEE remainder operation which returns the remainder from a rounding division.

The sum() function returns the sum of the values of the nodes in the argument node-set.

The floor() function returns the largest (closest to positive infinity) number that is not greater than the argument and that is an integer.

The ceiling() function returns the smallest (closest to negative infinity) number that is not less than the argument and that is an integer.

The round() function returns the number that is closest to the argument and that is an integer. If there are two such numbers, then the one that is even is returned.

Numeric Expressions
[27]    AdditiveExpr    ::=    MultiplicativeExpr
| AdditiveExpr '+' MultiplicativeExpr
| AdditiveExpr '-' MultiplicativeExpr
[28]    MultiplicativeExpr    ::=    UnaryExpr
| MultiplicativeExpr MultiplyOperator UnaryExpr
| MultiplicativeExpr 'div' UnaryExpr
| MultiplicativeExpr 'mod' UnaryExpr
| MultiplicativeExpr 'quo' UnaryExpr
[29]    UnaryExpr    ::=    UnionExpr
| '-' UnaryExpr
[30]    NumberExpr    ::=    Expr
[31]    NumberFunctionCall    ::=    'number' '(' Expr? ')'
| 'floor' '(' NumberExpr ')'
| 'ceiling' '(' NumberExpr ')'
| 'round' '(' NumberExpr ')'
| 'sum' '(' NodeSetExpr ')'

6.2.5 Strings

A string consists of a sequence of UCS characters.

A StringExpr is evaluated by converting the result of evaluating the Expr to a string as if by a call to the string() function.

The string() function converts an object to a string as follows:

If the argument is omitted, it defaults to the context node.

The concat() function returns the concatenation of its arguments.

The starts-with() function returns true if the first argument string starts with the second argument string, and otherwise returns false.

The contains() function returns true if the first argument string contains the second argument string, and otherwise returns false.

The substring-before() function returns the substring of the first argument string that precedes the first occurrence of the second argument string in the first argument string, or the empty string if the first argument string does not contain the second argument string. For example, substring-before("1999/04/01","/") returns 1999.

The substring-after() function returns the substring of the first argument string that follows the first occurrence of the second argument string in the first argument string, or the empty string if the first argument string does not contain the second argument string. For example, substring-after("1999/04/01","/") returns 04/01.

Ed. Note: Should the first argument of the above functions default to the value of the current node?

The normalize() function returns the argument string with white space normalized by stripping leading and trailing whitespace and replacing sequences of whitespace characters by a single space. Whitespace characters are the same allowed by the S production in XML. If the argument is omitted, it defaults to the context node converted to a string, in other words the value of the context node.

The translate() function returns the first argument string with occurrences of characters in the second argument string replaced by the corresponding characters from the third argument string. For example, translate("bar","abc","ABC") returns the string BAr.

The format-number() function converts its first argument to a string using the format pattern string specified by the second argument and the locale named by the third argument, or the default locale, if there is no third argument. The format pattern string is in the syntax specified by the JDK 1.1 DecimalFormat class. The format pattern string is in a localized notation: the locale determines what characters have a special meaning in the pattern (with the exception of the quote character, which is not localized). The format pattern must not contain the currency sign (#x00A4); support for this feature was added after the initial release of JDK 1.1. See [6.4.3 Declaring Locales] for how to declare a locale.

[32]    StringExpr    ::=    Expr
[33]    StringFunction    ::=    'string' '(' Expr? ')'
| 'starts-with' '(' StringExpr ',' StringExpr ')'
| 'contains' '(' StringExpr ',' StringExpr ')'
| 'substring-before '(' StringExpr ',' StringExpr ')'
| 'substring-after '(' StringExpr ',' StringExpr ')'
| 'normalize' '(' StringExpr? ')'
| 'translate' '(' StringExpr ',' StringExpr ',' StringExpr ')'
| 'concat' '(' StringExpr (',' StringExpr)+ ')'
| 'format-number' '(' NumberExpr ',' StringExpr (',' StringExpr)? ')'

Issue (regex): Should XSLT support regular expressions for matching against any or all of pcdata content, attribute values, attribute names, element type names?

Issue (equality-case): Do we need to be able to do comparisons in a case insensitive way?

Issue (equality-normalize): Do we need to normalize strings before comparison? Does the stylesheet need to specify what kinds of normalization are required (eg compatibility character normalization)?

Issue (resolve-expr): Do we need a resolve(NodeSetExpr) string expression that treats the characters as a relative URI and turns it into an absolute URI using the base URI of the addressed node?

6.2.6 Result Tree Fragments

Ed. Note: Add explanation of what a result tree fragment is.

The only operations that can be performed on a result tree fragment are to convert it to a string or a boolean. In particular, it is not permitted to use the /, //, and [] on result tree fragments.

Expressions can only return values of type result tree fragment by referencing variables of type result tree fragment or calling extension functions that return a result tree fragment.

6.2.7 Extension Functions

[34]    ExtensionFunctionCall    ::=    CName '(' ( Expr ( ',' Expr)*)? ')'

The CName is expanded to a name using the namespace declarations from the evaluation context. The XSLT processor attempts to locate an implementation of the extension function with the specified name that it can use. The implementation may be provided by an xsl:functions element (see [6.4.2 Declaring Extension Functions]) or the XSLT processor may be able to locate an implementation by other means not specified by XSLT. If the XSLT processor cannot locate such a function, then evaluating the expression is an error. Otherwise the implementation is called passing it the values of the expressions and the value returned by the function is the value of the expression. The function-available() function can be used to test whether an implementation of a particular function is available (see [6.2.8 System Functions]). A XSLT processor is allowed always to give an error when evaluating an ExtensionFunctionCall (with such an XSLT processor the function-available() function would always return false). Therefore if an XSLT stylesheet includes an ExtensionFunctionCall and does not use the function-available() function to test for and handle the possibility that an implementation of the function is not available, then it may not be portable across all XSLT implementations.

6.2.8 System Functions

[35]    SystemFunctionCall    ::=    'system-property' '(' StringExpr ')'
| 'function-available' '(' StringExpr ')'

For both these functions, the StringExpr must evaluate to a string that is a QName. The QName is expanded into a name using the namespace declarations in scope for the expression.

The system-property() function returns an object representing the value of the system property identified by the name. If the name has no namespace, then the system-property() function must return the string value of the operating system environment variable whose name is equal to the local part of the name. If there is no such system property, the empty string should be returned.

Implementations must provide the following system properties which are all in the XSLT namespace:

The function-available() function returns true if an implementation of the named extension function is available. For example:

<xsl:if test="function-available('jjc:currentDate')">
  <xsl:value-of select="jjc:currentDate()"/>
</xsl:if>

6.2.9 Lexical Structure

When tokenizing, the longest possible token is always returned.

For readability, whitespace may be used in patterns even though not explicitly allowed by the grammar: ExprWhitespace may be freely added within patterns before or after any ExprToken.

A NodeType, FunctionName, CName or AxisIdentifier token is recognized only when the following token is (. An OperatorName token or MultiplyOperator token is recognized as such only when there is a preceding token and the preceding token is not one of @, (, [, , or an Operator.

Expression Lexical Structure
[36]    ExprToken    ::=    '(' | ')' | '[' | ']' | '.' | '..' | '@' | ','
| WildcardName
| NodeType
| Operator
| FunctionName
| AxisIdentifier
| Literal
| Number
| CName
| VariableReference
[37]    Literal    ::=    '"' [^"]* '"'
| "'" [^']* "'"
[38]    Number    ::=    [0-9]+ ('.' [0-9]+)?
| '.' [0-9]+
[39]    Operator    ::=    OperatorName
| MultiplyOperator
| '/' | '//' | '|' | '+' | '-' | '=' | '<'| '<=' | '>' | '>='
[40]    OperatorName    ::=    'and' | 'or' | 'mod' | 'div' | 'quo'
[41]    MultiplyOperator    ::=    '*'
[42]    FunctionName    ::=    'boolean'
| 'ceiling'
| 'concat'
| 'contains'
| 'count'
| 'doc'
| 'docref'
| 'false'
| 'floor'
| 'format-number'
| 'function-available'
| 'generate-id'
| 'id'
| 'idref'
| 'key'
| 'keyref'
| 'lang'
| 'last'
| 'local-part'
| 'namespace'
| 'normalize'
| 'not'
| 'number'
| 'position'
| 'qname'
| 'round'
| 'starts-with'
| 'string'
| 'substring-after'
| 'substring-before'
| 'sum'
| 'system-property'
| 'translate'
| 'true'
[43]    CName    ::=    NCName ':' NCName
[44]    VariableReference    ::=    '$' NCName
[45]    WildcardName    ::=    '*'
| NCName ':' '*'
| QName
[46]    NodeType    ::=    'comment'
| 'text'
| 'pi'
| 'node'
[47]    ExprWhitespace    ::=    S

6.3 Patterns

This section explains what expressions are allowed as patterns and what the semantics of matching a pattern are.

Here are some examples of patterns:

A pattern must match the grammar for Pattern. A Pattern is set of location path patterns separated by |. A location path pattern is a location path none of the steps of which use either AxisIdentifiers or . or ... Location path patterns can also start with an id() or key() function call with a literal argument (see [6.2.2 Node-sets]). Predicates in a pattern can use arbitrary expressions just like predicates in a location path.

Patterns
[48]    Pattern    ::=    LocationPathPattern
| Pattern '|' LocationPathPattern
[49]    LocationPathPattern    ::=    '/' RelativePathPattern?
| IdKeyPattern (('/' | '//') RelativePathPattern)?
| '//'? RelativePathPattern
[50]    IdKeyPattern    ::=    'id' '(' Literal ')'
| 'key' '(' Literal ',' Literal ')'
[51]    RelativePathPattern    ::=    StepPattern
| RelativePathPattern '/' StepPattern
| RelativePathPattern '//' StepPattern
[52]    StepPattern    ::=    AbbreviatedNodeTestStep

A pattern is defined to match a node if and only if there is possible context such that when the pattern is evaluated as an expression with that context, the node is a member of the resulting node-set. When a node is being matched the possible contexts have a context node that is the node being matched or any ancestor of that node, and a context node list containing just the context node.

For example, p matches any p element, because for any p if the expression p is evaluated with the parent of the p element as context the resulting node-set will contain that p element as one of its members.

NOTE: This matches even a p element that is the document element, since the document root is the parent of the document element.

Although the semantics of patterns are specified indirectly in terms of expression evaluation, it is easy to understand the meaning of a pattern directly without thinking in terms of expression evaluation. In a pattern, | indicates alternatives; a pattern with one or more | separated alternatives matches if any one of the alternative matches. A pattern that consists of a sequence of StepPatterns separated by / or // is matched from right to left. The pattern only matches if the rightmost StepPattern matches and a suitable element matches the rest of the pattern; if the separator is / then only the parent is a suitable element; if the separator is //, then any ancestor is a suitable element. A StepPattern that's a NodeTest matches if the NodeTest is true for the node and the node is not an attribute node. A StepPattern that starts with @ matches if the node is an attribute node and the WildcardName matches the name of the attribute. When [] is present, then the first PredicateExpr in a StepPattern is evaluated with the element being matched as the context node and the siblings of the elements that match the NodeTest as the context node list, unless the node being matched is an attribute node, in which case the context node list is all the attributes that have the same parent as the attribute being matched and that match the WildcardName.

For example

appendix//ulist/item[position()=1]

matches a node if and only if all of the following are true:

Ed. Note: Need to revise above paragraph if we decide not to call the element to which an attribute is attached the parent of the attribute.

6.4 Declarations

6.4.1 Declaring Keys

The xsl:key element is used to declare keys. The name specifies the name of the key. The match attribute is a Pattern; a xsl:key element gives information about the keys of any node that match the pattern specified in the match attribute. The use attribute is a NodeSetExpr, which specifies the set of values for which the node has a key of the specified name. A node x has a key with name y and value z if and only if there is a xsl:key element such that:

Note that the NodeSetExpr may return a node-set with more than one node; all of the returned nodes serve as a key value. Note also that there may be more than one xsl:key element that matches a given node; all of the matching xsl:key elements are used.

Ed. Note: Add some examples.

6.4.2 Declaring Extension Functions

Implementations of the extension functions in a namespace can be provided using the xsl:functions element. The required ns attribute specifies the namespace for which an implementation is being provided. The value of the ns attribute is a namespace prefix which is expanded to a namespace URI using the namespace declarations in effect on the xsl:functions element.

The implementation may be provided in two ways. If the code attribute is present, then its value is a URI that identifies a resource containing an implementation of the functions in the namespace; in this case a type attribute giving the MIME media type of the data providing the implementation may also be provided, so as to allow the XSLT processor to avoid fetching resources of types that it is unable to make use of. If the code attribute is not present, then the content of the xsl:functions element contains the implementation of the functions; in this case the type attribute must be present.

Multiple alternative implementations may be provided for the same namespace. For example,

<xsl:stylesheet
 xmlns:xsl="http://www.w3.org/XSL/Transform/1.0"
 xmlns:jjc="http://www.jclark.com">

<xsl:template match="/">
  <xsl:value-of select="jjc:currentDate()"/>
</xsl:template>

<xsl:functions ns="jjc" type="text/javascript">

function currentDate() {
 return Date().toString()
}

<p>When multiple alternative implementations are provided, it is up to
the XSLT processor to determine which to use.</p>

</xsl:functions>

<xsl:functions ns="jjc" code="clsid:9A447990-E64D-11D2-8C29-00A0CC2428DA"/>

</xsl:stylesheet>

The xsl:functions element may also have an archive attribute that specifies a whitespace-separated list of URIs of resources relevant to the provided implementation.

An XSLT processor is not required to be able to make use of implementations provided by xsl:functions elements. The MIME media types that an XSLT processor is able to make use of and the way the XSLT processor interfaces with implementations is dependent on the particular XSLT processor. Therefore if an XSLT stylesheet includes an ExtensionFunctionCall of an extension function in a namespace for which an implementation is provided by an xsl:functions element, then it may not be portable across all XSLT implementations.

6.4.3 Declaring Locales

The xsl:locale element declares a locale which controls the interpretation of a format pattern used by the format-number() function. If there is a name attribute then the element declares a named locale, otherwise it declares the default locale.

The other attributes on xsl:locale correspond to the methods on the JDK 1.1 DecimalFormatSymbols class. For each get/set method pair there is an attribute defined for the xsl:locale element. The default values are given in the XSLT DTD (see [A DTD Fragment for XSLT Stylesheets]).

The following attributes specify characters that may appear in the result of formatting the number and also control the interpretation of characters in the format pattern:

The followi