zorba-coders team mailing list archive
-
zorba-coders team
-
Mailing list archive
-
Message #12163
[Merge] lp:~zorba-coders/zorba/fix-fn-path into lp:zorba
Till Westmann has proposed merging lp:~zorba-coders/zorba/fix-fn-path into lp:zorba.
Requested reviews:
Ghislain Fourny (gislenius)
Markos Zaharioudakis (markos-za)
For more details, see:
https://code.launchpad.net/~zorba-coders/zorba/fix-fn-path/+merge/114739
fix position for elements and processing-instructions in fn:path
--
https://code.launchpad.net/~zorba-coders/zorba/fix-fn-path/+merge/114739
Your team Zorba Coders is subscribed to branch lp:zorba.
=== modified file 'src/runtime/nodes/nodes_impl.cpp'
--- src/runtime/nodes/nodes_impl.cpp 2012-07-12 17:29:55 +0000
+++ src/runtime/nodes/nodes_impl.cpp 2012-07-12 21:21:38 +0000
@@ -680,7 +680,7 @@
/*******************************************************************************
********************************************************************************/
-int getNodePosition(store::Item_t aNode)
+int getNodePosition(store::Item_t aNode, store::Item_t aNodeName)
{
int count = 1;
store::Iterator_t lIterator = aNode->getParent()->getChildren();
@@ -692,7 +692,7 @@
{
if(lItem->equals(aNode))
break;
- else
+ else if (aNodeName.isNull() || aNodeName->equals(lItem->getNodeName()))
count++;
}
}
@@ -703,101 +703,87 @@
bool FnPathIterator::nextImpl(store::Item_t& result, PlanState& planState) const
{
store::Item_t inNode;
+ store::Item_t swap;
store::Item_t nodeName;
- store::NsBindings nsBindings;
zstring path;
zstring temp;
zstring zNamespace;
zstring zLocalName;
zstring zPosition;
- bool rootIsDocument = false;
PlanIteratorState* state;
DEFAULT_STACK_INIT(PlanIteratorState, state, planState);
if (consumeNext(inNode, theChildren[0], planState))
{
- do
- {
+ while (inNode->getParent())
+ {
+ temp = path;
+ path = "/";
+
switch (inNode->getNodeKind())
{
- case store::StoreConsts::documentNode:
- temp = path;
- path = "/";
- path += temp;
- rootIsDocument = true;
- break;
-
case store::StoreConsts::elementNode:
nodeName = inNode->getNodeName();
zNamespace = nodeName->getNamespace();
zLocalName = nodeName->getLocalName();
- zPosition = ztd::to_string(getNodePosition(inNode));
- temp = path;
- path = "Q{"+zNamespace+"}"+zLocalName+"["+zPosition.c_str()+"]";
- path += temp;
+ zPosition = ztd::to_string(getNodePosition(inNode, nodeName));
+ path += "\""+zNamespace+"\":"+zLocalName+"["+zPosition+"]";
break;
-
case store::StoreConsts::attributeNode:
nodeName = inNode->getNodeName();
zNamespace =nodeName->getNamespace();
zLocalName = nodeName->getLocalName();
+ path += "@";
if(zNamespace != "")
{
- temp = path;
- path = "@Q{"+zNamespace+"}"+zLocalName;
- path += temp;
- }
- else
- {
- temp = path;
- path = "@"+zLocalName;
- path += temp;
- }
+ path += "\""+zNamespace+"\":";
+ }
+ path += zLocalName;
break;
-
case store::StoreConsts::textNode:
- zPosition = ztd::to_string(getNodePosition(inNode));
- temp = path;
- path = "text()["+zPosition+"]";
- path += temp;
+ zPosition = ztd::to_string(getNodePosition(inNode, NULL));
+ path += "text()["+zPosition+"]";
break;
-
case store::StoreConsts::commentNode:
- zPosition = ztd::to_string(getNodePosition(inNode));
- temp = path;
- path = "comment()["+zPosition+"]";
- path += temp;
+ zPosition = ztd::to_string(getNodePosition(inNode, NULL));
+ path += "comment()["+zPosition+"]";
break;
-
- case store::StoreConsts::piNode:
+ case store::StoreConsts::piNode:
nodeName = inNode->getNodeName();
zLocalName = nodeName->getLocalName();
- zPosition = ztd::to_string(getNodePosition(inNode));
- temp = path;
- path = "processing-instruction("+zLocalName+")["+zPosition+"]";
- path += temp;
+ zPosition = ztd::to_string(getNodePosition(inNode, nodeName));
+ path += "processing-instruction("+zLocalName+")["+zPosition+"]";
break;
-
default:
+ // this is either a documentNode which should always be a root
+ // node (and not end up here) or it is something very strange
ZORBA_ASSERT(false);
+ break;
}
-
- inNode = inNode->getParent();
-
- if (inNode && inNode->getNodeKind() != store::StoreConsts::documentNode)
+ path += temp;
+
+ swap = inNode->getParent();
+ inNode = swap;
+ }
+
+ // only the root node is left and there we've got some special
+ // cases in the spec
+ if (inNode->getNodeKind() == store::StoreConsts::documentNode)
+ {
+ if (path.empty())
{
- temp = path;
path = "/";
- path += temp;
}
-
- } while (inNode);
-
- if(rootIsDocument)
- STACK_PUSH(GENV_ITEMFACTORY->createString(result, path), state);
+ }
else
- throw XQUERY_EXCEPTION(err::FODC0001, ERROR_PARAMS("fn:path"), ERROR_LOC(loc));
+ {
+ temp = path;
+ path = "\"http://www.w3.org/2005/xpath-functions\":root()";
+ path += temp;
+ }
+
+ STACK_PUSH(GENV_ITEMFACTORY->createString(result, path), state);
}
STACK_END (state);
Follow ups