sboag 99/12/13 00:22:55
Modified: . make.include
src makexpath4j
src/org/apache/xalan/xpath/xml XMLParserLiaisonDefault.java
src/org/apache/xalan/xslt ElemChoose.java ElemMessage.java
ElemTemplateElement.java NodeSorter.java
StylesheetHandler.java
Added: src/org/apache/xalan/xslt TemplateElementContext.java
Log:
Various other support for the previous commits.
Revision Changes Path
1.3 +1 -0 xml-xalan/make.include
Index: make.include
===================================================================
RCS file: /home/cvs/xml-xalan/make.include,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -r1.2 -r1.3
--- make.include 1999/11/09 00:00:12 1.2
+++ make.include 1999/12/13 08:22:53 1.3
@@ -35,6 +35,7 @@
JAVA = java
JAVAC = javac
JAVACFLAGS = -g -d $(CLASS_DIR)
+# JAVACFLAGS = -g:none -O -d $(CLASS_DIR)
JAR = jar
JARFLAGS = cf0
JAVADOC = javadoc
1.11 +5 -0 xml-xalan/src/makexpath4j
Index: makexpath4j
===================================================================
RCS file: /home/cvs/xml-xalan/src/makexpath4j,v
retrieving revision 1.10
retrieving revision 1.11
diff -u -r1.10 -r1.11
--- makexpath4j 1999/12/03 22:30:56 1.10
+++ makexpath4j 1999/12/13 08:22:54 1.11
@@ -129,7 +129,12 @@
$(XMLLIAISONDIR)$(PATHSEP)XSLResourceBundle.java \
$(XMLLIAISONDIR)$(PATHSEP)ProblemListener.java \
$(XMLLIAISONDIR)$(PATHSEP)StringToStringTable.java \
+ $(XMLLIAISONDIR)$(PATHSEP)StringToStringTableVector.java \
$(XMLLIAISONDIR)$(PATHSEP)StringKey.java \
+ $(XMLLIAISONDIR)$(PATHSEP)BoolStack.java \
+ $(XMLLIAISONDIR)$(PATHSEP)IntStack.java \
+ $(XMLLIAISONDIR)$(PATHSEP)IntVector.java \
+ $(XMLLIAISONDIR)$(PATHSEP)ElemDesc.java \
$(XMLLIAISONDIR)$(PATHSEP)StringVector.java \
$(XMLLIAISONDIR)$(PATHSEP)NodeVector.java \
$(XMLLIAISONDIR)$(PATHSEP)RawCharacterHandler.java \
1.12 +53 -2
xml-xalan/src/org/apache/xalan/xpath/xml/XMLParserLiaisonDefault.java
Index: XMLParserLiaisonDefault.java
===================================================================
RCS file:
/home/cvs/xml-xalan/src/org/apache/xalan/xpath/xml/XMLParserLiaisonDefault.java,v
retrieving revision 1.11
retrieving revision 1.12
diff -u -r1.11 -r1.12
--- XMLParserLiaisonDefault.java 1999/12/03 19:01:03 1.11
+++ XMLParserLiaisonDefault.java 1999/12/13 08:22:54 1.12
@@ -227,6 +227,57 @@
*/
protected ErrorHandler m_errorHandler = null;
+ /**
+ * Callback that may be executed when a node is found, if the
+ * XPath query can be done in document order.
+ * The callback will be set to null after the next LocationPath or
+ * Union is processed.
+ */
+ private NodeCallback m_callback = null;
+
+ /**
+ * Object that will be passed to the processLocatedNode method.
+ * The object will be set to null after the next LocationPath or
+ * Union is processed.
+ */
+ private Object m_callbackInfo = null;
+
+ /**
+ * Set a callback that may be called by XPath as nodes are located.
+ * The callback will only be called if the XLocator determines that
+ * the location path can process the nodes in document order.
+ * If the callback is called, the nodes will not be put into the
+ * node list, and the LocationPath will return an empty node list.
+ * The callback will be set to null after the next LocationPath or
+ * Union is processed.
+ * @param callback Interface that implements the processLocatedNode method.
+ * @param callbackInfo Object that will be passed to the
processLocatedNode method.
+ */
+ public void setCallback(NodeCallback callback, Object callbackInfo)
+ {
+ m_callback = callback;
+ m_callbackInfo = callbackInfo;
+ }
+
+ /**
+ * Get the callback that may be called by XPath as nodes are located.
+ * @return the current callback method.
+ */
+ public NodeCallback getCallback()
+ {
+ return m_callback;
+ }
+
+ /**
+ * Get the object that will be passed to the processLocatedNode method.
+ * @return object that will be passed to the processLocatedNode method.
+ */
+ public Object getCallbackInfo()
+ {
+ return m_callbackInfo;
+ }
+
+
//==========================================================
// SECTION: Parsing Support
//==========================================================
@@ -950,7 +1001,7 @@
Node attr = nnm.item(i);
String aname = attr.getNodeName();
boolean isPrefix = aname.startsWith("xmlns:");
- if (aname.equals("xmlns") || isPrefix)
+ if (isPrefix || aname.equals("xmlns"))
{
int index = aname.indexOf(':');
String p = isPrefix ? aname.substring(index+1) : "";
@@ -1397,7 +1448,7 @@
data = node.getNodeValue();
break;
case Node.PROCESSING_INSTRUCTION_NODE:
- warning(XPATHErrorResources.WARNING0013);
+ // warning(XPATHErrorResources.WARNING0013);
break;
default:
// ignore
1.2 +1 -0 xml-xalan/src/org/apache/xalan/xslt/ElemChoose.java
Index: ElemChoose.java
===================================================================
RCS file: /home/cvs/xml-xalan/src/org/apache/xalan/xslt/ElemChoose.java,v
retrieving revision 1.1
retrieving revision 1.2
diff -u -r1.1 -r1.2
--- ElemChoose.java 1999/11/08 20:56:19 1.1
+++ ElemChoose.java 1999/12/13 08:22:54 1.2
@@ -109,6 +109,7 @@
ElemWhen when = (ElemWhen)node;
// must be xsl:when
XPathSupport execContext = processor.getXMLProcessorLiaison();
+
XObject test = when.m_test.execute(execContext, sourceNode, this);
if(null != m_stylesheet.m_stylesheetRoot.m_traceListeners)
{
1.3 +6 -6 xml-xalan/src/org/apache/xalan/xslt/ElemMessage.java
Index: ElemMessage.java
===================================================================
RCS file: /home/cvs/xml-xalan/src/org/apache/xalan/xslt/ElemMessage.java,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -r1.2 -r1.3
--- ElemMessage.java 1999/11/10 22:00:47 1.2
+++ ElemMessage.java 1999/12/13 08:22:54 1.3
@@ -83,10 +83,10 @@
for(int i = 0; i < nAttrs; i++)
{
String aname = atts.getName(i);
- if(aname.equals(Constants.ATTRNAME_TERMINATE))
+ if(aname.equals(Constants.ATTRNAME_TERMINATE))
{
- m_terminate = atts.getValue(i);
- }
+ m_terminate = atts.getValue(i);
+ }
else if(!(isAttrOK(aname, atts, i) || processSpaceAttr(aname, atts,
i)))
{
processor.error(XSLTErrorResources.ERROR0002, new Object[] {name,
aname}); //name+" has an illegal attribute: "+aname);
@@ -108,8 +108,8 @@
String data = childrenToString(processor, sourceTree,
sourceNode, mode);
processor.message(this, sourceNode, data);
- if (m_terminate.equals(Constants.ATTRVAL_YES))
- throw new XSLProcessorException(data);
-
+ if (m_terminate.equals(Constants.ATTRVAL_YES))
+ throw new XSLProcessorException(data);
+
}
}
1.8 +108 -23
xml-xalan/src/org/apache/xalan/xslt/ElemTemplateElement.java
Index: ElemTemplateElement.java
===================================================================
RCS file:
/home/cvs/xml-xalan/src/org/apache/xalan/xslt/ElemTemplateElement.java,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -r1.7 -r1.8
--- ElemTemplateElement.java 1999/12/03 08:43:14 1.7
+++ ElemTemplateElement.java 1999/12/13 08:22:54 1.8
@@ -81,7 +81,7 @@
* @see Stylesheet
*/
public class ElemTemplateElement extends UnImplNode
- implements PrefixResolver, Serializable
+ implements PrefixResolver, Serializable, NodeCallback
{
/**
* The owning stylesheet.
@@ -385,7 +385,7 @@
{
String newValue = value; // make a copy of the value passed
boolean isPrefix = aname.startsWith("xmlns:");
- if (aname.equals("xmlns") || isPrefix)
+ if (isPrefix || aname.equals("xmlns"))
{
String p = isPrefix ? aname.substring(6) : "";
@@ -614,12 +614,14 @@
// Sort the nodes according to the xsl:sort method
int tok = xslInstruction.getXSLToken();
Vector keys = null;
+ NodeCallback callback = this;
if((Constants.ELEMNAME_APPLY_TEMPLATES == tok) ||
(Constants.ELEMNAME_FOREACH == tok))
{
ElemForEach foreach = (ElemForEach)xslInstruction;
if(null != foreach.m_sortElems)
{
+ callback = null; // can't use callbacks
int nChildren = foreach.m_sortElems.size();
keys = new Vector();
@@ -654,11 +656,26 @@
NodeList sourceNodes = null;
if(null != selectPattern)
{
- XPathSupport execContext = tcontext.getXMLProcessorLiaison();
- XObject result = selectPattern.execute(execContext, sourceNodeContext,
+ XPathSupport execContext = tcontext.getXMLProcessorLiaison();
+ if(null != callback)
+ execContext.setCallback(callback,
+ new TemplateElementContext(stylesheetTree,
+ xslInstruction,
+ template,
+ sourceNodeContext,
+ mode,
+ xslToken,
+ tcontext));
+
+ XObject result = selectPattern.execute(execContext, sourceNodeContext,
xslInstruction);
if(null != result)
+ {
sourceNodes = result.nodeset();
+
+ if(sourceNodes.getLength() == 0)
+ sourceNodes = null;
+ }
if(null != m_stylesheet.m_stylesheetRoot.m_traceListeners)
{
@@ -691,7 +708,7 @@
if(null != keys)
{
NodeSorter sorter = new
NodeSorter(tcontext.getXMLProcessorLiaison());
- sorter.sort((Vector)sourceNodes, keys, tcontext.getExecContext());
+ sorter.sort((NodeVector)sourceNodes, keys,
tcontext.getExecContext());
}
// NodeList children = sourceNodeContext.getChildNodes();
@@ -719,27 +736,58 @@
tcontext.getExecContext().setContextNodeList( savedContextNodeList );
}
}
- /*
- else
+ else if(null == selectPattern)
{
- NodeList children = sourceNodeContext.getChildNodes();
- NodeList savedContextNodeList =
m_stylesheet.m_processor.m_contextNodeList;
- m_stylesheet.m_processor.m_contextNodeList = children;
- if(m_stylesheet.m_processor.m_traceSelects)
- m_stylesheet.m_processor.traceSelect(xslInstruction, children);
- int nNodes = children.getLength();
- for(int i = 0; i < nNodes; i++)
- {
- Node childNode = children.item(i);
-
- transformChild(
- stylesheetTree, xslInstruction, template,
- sourceTree, sourceNodeContext, childNode,
- mode, xslToken);
+ if(tcontext.m_traceSelects)
+ tcontext.traceSelect(xslInstruction, sourceNodes);
+ Document ownerDoc = sourceNodeContext.getOwnerDocument();
+ if((Node.DOCUMENT_NODE != sourceNodeContext.getNodeType()) && (null ==
ownerDoc))
+ {
+ error(XSLTErrorResources.ERROR0018, null); //"Child node does not
have an owner document!");
+ }
+ NodeList savedContextNodeList =
tcontext.getExecContext().getContextNodeList();
+ MutableNodeList contextNodeList = new MutableNodeListImpl();
+ tcontext.getExecContext().setContextNodeList( contextNodeList );
+ /*
+ // This isn't much faster than the block below...
+ try
+ {
+ org.apache.xalan.xpath.dtm.DTMProxy contextp =
(org.apache.xalan.xpath.dtm.DTMProxy)sourceNodeContext;
+ org.apache.xalan.xpath.dtm.DTM dtm = contextp.getDTM();
+ int contextIndex = contextp.getDTMNodeNumber();
+ for(int child = dtm.getFirstChild(contextIndex);
+ child != -1; child = dtm.getNextSibling(child))
+ {
+ Node childNode = dtm.getNode(child);
+ contextNodeList.addNode(childNode);
+ transformChild(
+ stylesheetTree, xslInstruction, template,
+ ownerDoc,
+ sourceNodeContext, childNode,
+ mode, xslToken, tcontext);
+ }
}
- m_stylesheet.m_processor.m_contextNodeList = savedContextNodeList;
+ catch(ClassCastException cce)
+ */
+ {
+ for(Node childNode = sourceNodeContext.getFirstChild();
+ null != childNode; childNode = childNode.getNextSibling())
+ {
+ if(childNode.getNodeType() == Node.TEXT_NODE)
+ {
+ if(tcontext.shouldStripSourceNode(childNode))
+ continue;
+ }
+ contextNodeList.addNode(childNode);
+ transformChild(
+ stylesheetTree, xslInstruction, template,
+ ownerDoc,
+ sourceNodeContext, childNode,
+ mode, xslToken, tcontext);
+ }
+ }
+ tcontext.getExecContext().setContextNodeList( savedContextNodeList );
}
- */
}
/**
@@ -777,6 +825,43 @@
}
}
return isWhiteSpace;
+ }
+
+ /**
+ * Implementation of NodeCallback interface. Process the
+ * node as soon as it is located by the XLocator.
+ * @param execContext Execution context.
+ * @param sourceNode The source node that was located.
+ * @param callbackInfo Opaque info for the caller's benefit.
+ */
+ public void processLocatedNode(XPathSupport execContext,
+ Node sourceNode,
+ Object callbackInfo)
+ throws SAXException
+ {
+ TemplateElementContext templateContext =
(TemplateElementContext)callbackInfo;
+
+ try
+ {
+ transformChild(templateContext.m_stylesheetTree,
+ templateContext.m_xslInstruction, //
xsl:apply-templates or xsl:for-each
+ templateContext.m_template, // may be null
+ sourceNode.getOwnerDocument(),
+ templateContext.m_sourceNodeContext,
+ sourceNode,
+ templateContext.m_mode,
+ templateContext.m_xslToken,
+ templateContext.m_transformContext
+ );
+ }
+ catch(SAXException se)
+ {
+ throw se;
+ }
+ catch(Exception mue)
+ {
+ throw new XSLProcessorException(mue);
+ }
}
/**
1.4 +4 -4 xml-xalan/src/org/apache/xalan/xslt/NodeSorter.java
Index: NodeSorter.java
===================================================================
RCS file: /home/cvs/xml-xalan/src/org/apache/xalan/xslt/NodeSorter.java,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -r1.3 -r1.4
--- NodeSorter.java 1999/11/28 10:26:22 1.3
+++ NodeSorter.java 1999/12/13 08:22:54 1.4
@@ -61,6 +61,7 @@
import java.util.*;
import java.text.*;
import org.apache.xalan.xpath.XPathSupport;
+import org.apache.xalan.xpath.xml.NodeVector;
/**
* This class can sort vectors of DOM nodes according to a select pattern.
@@ -93,7 +94,7 @@
* @param v an vector of Nodes.
* @param keys a vector of NodeSortKeys.
*/
- public void sort(Vector v, Vector keys, XPathSupport support)
+ public void sort(NodeVector v, Vector keys, XPathSupport support)
throws org.xml.sax.SAXException,
java.net.MalformedURLException,
java.io.FileNotFoundException,
@@ -102,8 +103,7 @@
m_keys = keys;
// QuickSort2(v, 0, v.size() - 1 );
int n = v.size();
- Vector scratchVector = new Vector(n);
- scratchVector.setSize(n);
+ NodeVector scratchVector = new NodeVector(n);
mergesort(v, scratchVector, 0, n - 1, support);
}
@@ -178,7 +178,7 @@
* maintains the original document order of the input if
* the order isn't changed by the sort.
*/
- void mergesort(Vector a, Vector b, int l, int r, XPathSupport support)
+ void mergesort(NodeVector a, NodeVector b, int l, int r, XPathSupport
support)
throws org.xml.sax.SAXException,
java.net.MalformedURLException,
java.io.FileNotFoundException,
1.9 +66 -57
xml-xalan/src/org/apache/xalan/xslt/StylesheetHandler.java
Index: StylesheetHandler.java
===================================================================
RCS file:
/home/cvs/xml-xalan/src/org/apache/xalan/xslt/StylesheetHandler.java,v
retrieving revision 1.8
retrieving revision 1.9
diff -u -r1.8 -r1.9
--- StylesheetHandler.java 1999/12/03 08:43:14 1.8
+++ StylesheetHandler.java 1999/12/13 08:22:54 1.9
@@ -303,6 +303,69 @@
int index = name.indexOf(':');
return (index < 0) ? name : name.substring(index+1);
}
+
+ /**
+ * Process xsl:strip-space and xsl:preserve-space.
+ */
+ private void processStripAndPreserve(String name, AttributeList atts,
+ int xslToken, int lineNumber, int
columnNumber)
+ throws SAXException
+ {
+ ElemTemplateElement nsNode = new ElemEmpty(m_processor,
+ m_stylesheet,
+ name, atts, lineNumber,
columnNumber);
+
+ int nAttrs = atts.getLength();
+ boolean foundIt = false;
+ for(int i = 0; i < nAttrs; i++)
+ {
+ String aname = atts.getName(i);
+ if(aname.equals(Constants.ATTRNAME_ELEMENTS))
+ {
+ foundIt = true;
+ StringTokenizer tokenizer = new StringTokenizer(atts.getValue(i), "
\t\n\r");
+ while(tokenizer.hasMoreTokens())
+ {
+ // Use only the root, at least for right now.
+ String wildcardName = tokenizer.nextToken();
+
+ /**
+ * Creating a match pattern is too much overhead, but it's a
reasonably
+ * easy and safe way to do this right now. TODO: Validate the
pattern
+ * to make sure it's a WildcardName.
+ */
+ XPath matchPat = m_stylesheet.createMatchPattern(wildcardName,
nsNode);
+
+ if(Constants.ELEMNAME_PRESERVESPACE == xslToken)
+ {
+ if(null ==
m_stylesheet.m_stylesheetRoot.m_whitespacePreservingElements)
+ {
+ m_stylesheet.m_stylesheetRoot.m_whitespacePreservingElements
+ = new Vector();
+ }
+
m_stylesheet.m_stylesheetRoot.m_whitespacePreservingElements.addElement(matchPat);
+ }
+ else
+ {
+ if(null ==
m_stylesheet.m_stylesheetRoot.m_whitespaceStrippingElements)
+ {
+ m_stylesheet.m_stylesheetRoot.m_whitespaceStrippingElements
+ = new Vector();
+ }
+
m_stylesheet.m_stylesheetRoot.m_whitespaceStrippingElements.addElement(matchPat);
+ }
+ }
+ }
+ else if(!isAttrOK(aname, atts, i))
+ {
+ m_stylesheet.error(XSLTErrorResources.ERROR0002, new Object[] {name,
aname}); //name+" has an illegal attribute: "+aname);
+ }
+ }
+ if(!foundIt)
+ {
+ throw new
SAXException(XSLMessages.createMessage(XSLTErrorResources.ERROR0033, new
Object[]{name, Constants.ATTRNAME_ELEMENTS})); //"(StylesheetHandler) "+name+"
requires a "+Constants.ATTRNAME_ELEMENTS+" attribute!");
+ }
+ }
/**
* Receive notification of the beginning of an element.
@@ -414,62 +477,8 @@
case Constants.ELEMNAME_PRESERVESPACE:
case Constants.ELEMNAME_STRIPSPACE:
- {
- ElemTemplateElement nsNode = new ElemEmpty(m_processor,
- m_stylesheet,
- name, atts,
lineNumber, columnNumber);
-
- int nAttrs = atts.getLength();
- boolean foundIt = false;
- for(int i = 0; i < nAttrs; i++)
- {
- String aname = atts.getName(i);
- if(aname.equals(Constants.ATTRNAME_ELEMENTS))
- {
- foundIt = true;
- StringTokenizer tokenizer = new
StringTokenizer(atts.getValue(i), " \t\n\r");
- while(tokenizer.hasMoreTokens())
- {
- // Use only the root, at least for right now.
- String wildcardName = tokenizer.nextToken();
-
- /**
- * Creating a match pattern is too much overhead, but it's
a reasonably
- * easy and safe way to do this right now. TODO: Validate
the pattern
- * to make sure it's a WildcardName.
- */
- XPath matchPat =
m_stylesheet.createMatchPattern(wildcardName, nsNode);
-
- if(Constants.ELEMNAME_PRESERVESPACE == xslToken)
- {
- if(null ==
m_stylesheet.m_stylesheetRoot.m_whitespacePreservingElements)
- {
-
m_stylesheet.m_stylesheetRoot.m_whitespacePreservingElements
- = new Vector();
- }
-
m_stylesheet.m_stylesheetRoot.m_whitespacePreservingElements.addElement(matchPat);
- }
- else
- {
- if(null ==
m_stylesheet.m_stylesheetRoot.m_whitespaceStrippingElements)
- {
-
m_stylesheet.m_stylesheetRoot.m_whitespaceStrippingElements
- = new Vector();
- }
-
m_stylesheet.m_stylesheetRoot.m_whitespaceStrippingElements.addElement(matchPat);
- }
- }
- }
- else if(!isAttrOK(aname, atts, i))
- {
- m_stylesheet.error(XSLTErrorResources.ERROR0002, new
Object[] {name, aname}); //name+" has an illegal attribute: "+aname);
- }
- }
- if(!foundIt)
- {
- throw new
SAXException(XSLMessages.createMessage(XSLTErrorResources.ERROR0033, new
Object[]{name, Constants.ATTRNAME_ELEMENTS})); //"(StylesheetHandler) "+name+"
requires a "+Constants.ATTRNAME_ELEMENTS+" attribute!");
- }
- }
+ processStripAndPreserve(name, atts, xslToken,
+ lineNumber, columnNumber);
break;
case Constants.ELEMNAME_KEY:
@@ -1129,7 +1138,7 @@
if(name.equals("HTML"))
{
m_stylesheet.m_stylesheetRoot.m_indentResult = true;
- m_stylesheet.m_stylesheetRoot.m_outputmethod = "html";
+ m_stylesheet.m_stylesheetRoot.setOutputMethod("html");
}
return elem;
}
1.1
xml-xalan/src/org/apache/xalan/xslt/TemplateElementContext.java
Index: TemplateElementContext.java
===================================================================
package org.apache.xalan.xslt;
import org.w3c.dom.Node;
import org.apache.xalan.xpath.xml.QName;
/**
* Object to hold information needed to call transformChild. An instance
* of this object is passed to XPath, and then passed back to the
* processLocatedNode method.
*/
public class TemplateElementContext
{
/**
* Construct an instance of TemplateElementContext.
*/
TemplateElementContext(Stylesheet stylesheetTree,
ElemTemplateElement xslInstruction,
ElemTemplateElement template,
Node sourceNodeContext,
QName mode,
int xslToken,
XSLTEngineImpl transformContext)
{
m_stylesheetTree = stylesheetTree;
m_xslInstruction = xslInstruction;
m_template = template;
m_sourceNodeContext = sourceNodeContext;
m_mode = mode;
m_xslToken = xslToken;
m_transformContext = transformContext;
}
Stylesheet m_stylesheetTree;
ElemTemplateElement m_xslInstruction; // xsl:apply-templates or xsl:for-each
ElemTemplateElement m_template; // may be null
Node m_sourceNodeContext;
QName m_mode;
int m_xslToken;
XSLTEngineImpl m_transformContext;
}