Search code examples
xquerymarklogic

Error trying to insert array node object XDMP-CHILDDUPNAME?


I've read all the documentation around using XQuery to manipulate JSON documents and adding nodes and adding elements to arrays using xdmp:insert-xxx but I'm trying to create a new object with an array of values to an existing array and can't seem to figure it out.

I would like to add the following object to the root node of my json document.

{
 "A" : [ "B", "C" ]
}

When I try,

xdmp:node-insert-child( $doc/object-node(), object-node{ "ConfiscatedItems" : array-node{ "calculator", "welding iron" } }/ConfiscatedItems )

I receive the XDMP-CHILDDUPNAME Object nodes cannot have two children with the same name

My end object is to say if I had a document like;

{
   "f": "g",
   "h": 1,
   "q": [ 1, 2 ]
}

I would like it to look like;

{
   "f": "g",
   "h": 1,
   "q": [ 1, 2 ],
   "A": [ "B", "C" ]
}

I can do this in two steps by create a new text node called 'A' and the using xdmp:node-replace() with the array, but I want to do this in one step, not two. This is mainly because I'm creating generic code that uses xdmp:value() to execute tasks meaning I have limits around transactions and can't do this in two steps in the same transaction. Can someone assist?


Solution

  • When you have the XPath /ConfiscatedItems that is addressing the named property with an array-node, it will return a sequence of the array items. Those items will have the same name and will result in the (confusing if you don't understand what is happening) error message XDMP-CHILDDUPNAME.

    It can be helpful to use xdmp:describe() to get a better idea of what is being selected for JSON nodes.

    You want to return the array-node, not the items in the array. So, change your XPath from:

    /ConfiscatedItems
    

    to:

    /array-node("ConfiscatedItems")
    

    Or, to match the example JSON you posted /array-node("A")