Search code examples
xquery

XQuery: create array of maps


I don't understand how to dynamically create an array of maps in Xquery which in the end should be serialised as JSON:

I can create a simple/static array of maps like this

let $array := [map{"id": "4711"}, map{"id": "4712"}]

I can add another map like this:

let $array := array:append($array, map {"id": "4713"})

using the following

return 
 serialize($array, 
        <output:serialization-parameters>
            <output:method>json</output:method>
        </output:serialization-parameters>)

results in [{"id":"4711"},{"id":"4712"},{"id":"4713"}] which is perfect JSON for me.

But I have an arbitrary number of maps to add to this array based on a sequence, like this:

let $mylist := ("4714", "4715")

What I'd like to have as result is this:

[{"id":"4711"},{"id":"4712"},{"id":"4713"},{"id":"4714"},{"id":"475"}]

I'm trying to achieve this by:

let $array := array:append($array, 
    for $n in $mylist
    return map {"id": $n}
)  

But this returns as result:

[{"id":"4711"},{"id":"4712"},{"id":"4713"},[{"id":"4714"},{"id":"4715"}]]

So, obviously the for loop creates another array and appends that to the existing one. How do I avoid that?


Solution

  • I think the following should do it:

    let $mylist := ("4714", "4715")
    return array{ $mylist ! map{'id': .} }
    

    It's a bit unfortunate in my view that array{} is special-purpose syntax rather than just being a function.

    You can also do it with

    array:join( $mylist ! [map{'id': .}] )