Bug #3432
closedError running fn:transform() when TimingTraceListener is set
100%
Description
When running the attached stylesheet test-XPDY0002-error.xsl I get the following error:
Error in xsl:if/@test on line 18 column 31 of test-fn-transform.xsl:
XPDY0002: Finding root of tree: the context item is absent
But ONLY if TimingTraceListener is set.
The stylesheet uses a package, which in turn uses fn:transform to run a stylesheet test-fn-transform.xsl
test-fn-transform.xsl has a root-level variable set using an XPath from the document root.
Among the set of files attached are a batch file and an Ant build file.
Removing -TP:test-xslt-trace-profile.html from the batch file also removes the error
Removing
and from the Ant XSLT task also removes the error.
I'm using Saxon HE 9.8.0.4
Files
Updated by Michael Kay about 7 years ago
- Status changed from New to In Progress
The fn:transform() code is not setting the global context item before invoking Controller.applyTemplates(). It should do so: simple bug, easy to fix.
This leaves the question, why does it work when tracing is not enabled?
Well, Controller.globalContextItem is being set to the initial source doc in Controller.transformDocument() at #2286. This seems incorrect. But how come it doesn't happen when tracing is enabled? Well, this is because, with tracing enabled, global variables are evaluated eagerly (so that the trace output is intelligible). In fact, they are initialized before Controller.transformDocument (incorrectly) sets the global context item.
The primary fix here is to ensure that fn:transform calls Controller.setGlobalContextItem() if the source-node option is present. This is straightforward (though it suggests the need for a couple of extra test cases).
The secondary problem, of preventing globalContextItem being set on the applyTemplates() path, is trickier, because the same code is used in a wide variety of situations and there is a serious risk of causing regression to other workloads. Nevertheless, it's clearly wrong, and it could cause worse problems than simply a failure to throw XPDY0002: it could cause the global context item to have the wrong value. So I shall try and correct this one too.
Updated by Michael Kay about 7 years ago
Noted in passing that the fn:transform() code does not seem to do anything useful with the value of the global-context-item option when this is supplied in place of source-node.
Updated by Michael Kay about 7 years ago
My first attempt to remove the setting of globalContextItem from Controller.transformDocument() results in two s9api unit tests failing: XsltTransformer.testContextNotRoot and XsltTransformer.testContextNotRootNamedTemplate. These tests are handling the obscure rule (defined in the XSLT 1.0 spec, but translated here to 3.0 terminology) that when the initial match selection is a non-root node, the global context item is the root node of the corresponding document.
(XSLT 2.0 ยง9.5: For a global variable or the default value of a stylesheet parameter, the expression or sequence constructor specifying the variable value is evaluated with a singleton focus based on the root node of the tree containing the initial context node. )
After some delicate rearrangement of code I have now got all the JAXP and s9api unit tests to pass, but there's still a slight risk some user workloads could be affected because this rule wasn't being applied on all paths.
Updated by Michael Kay about 7 years ago
- Tracker changed from Support to Bug
- Category set to XPath conformance
- Status changed from In Progress to Resolved
- Assignee set to Michael Kay
- Priority changed from Low to Normal
- Fix Committed on Branch 9.8 added
Fix committed:
-
fn:transform now correctly sets the global context item taking into account the two options source-node and global-context-item
-
Controller.transformDocument() no longer sets the global context item to the supplied source node; instead, callers of this function that require this behaviour do it themselves.
Updated by O'Neil Delpratt about 7 years ago
- Status changed from Resolved to Closed
- % Done changed from 0 to 100
- Fixed in Maintenance Release 9.8.0.5 added
Bug fix applied in the Saxon 9.8.0.5 maintenance release.
Please register to edit this issue