ballerina-platform / ballerina-library

The Ballerina Library
https://ballerina.io/learn/api-docs/ballerina/
Apache License 2.0
136 stars 64 forks source link

Converting open Records back to XML #6833

Open DaAlbrecht opened 3 months ago

DaAlbrecht commented 3 months ago

Description:

Deserialization of a custom open Record back to XML fails.

Steps to reproduce:


import ballerina/data.xmldata;
import ballerina/io;

public type PayloadAnyType record {
    @xmldata:Attribute
    string 'version?;
    string 'type?;
};

public function main() returns error? {
    io:println("Hello, World!");

    xml xmlData = xml `
        <payloadAny version="token" type="token">
        <partnerGetRequest>
            <partnerGetRequest>
                <content>
                    <partner>21321321312321312312</partner>
                    <listOption>221312</listOption>
                </content>
            </partnerGetRequest>
            </partnerGetRequest>
        </payloadAny>
    `;

    PayloadAnyType data = check xmldata:parseAsType(xmlData);

    xml xmlItem = check xmldata:toXml(data);
    io:println("xmlItem: " + xmlItem);

}
Running executable

Hello, World!
error: {ballerina/lang.array}InherentTypeViolation {"message":"incompatible types: expected 'json', found 'map<anydata>'"}
        at ballerina.lang.map.0:entries(map.bal:97)
           ballerina.data.xmldata.0:getNamespacesMap(xml_api.bal:403)
           ballerina.data.xmldata.0:fromJson(xml_api.bal:186)
           ballerina.data.xmldata.0:toXml(xml_api.bal:138)
           didi.foo.0:main(main.bal:28)

Affected Versions:

❯ bal version
Ballerina 2201.9.2 (Swan Lake Update 9)
Language specification 2024R1
Update Tool 1.4.2
[[package]]
org = "ballerina"
name = "data.xmldata"
version = "0.1.4"

OS, DB, other environment details and versions:

Linux, MacOS

prakanth97 commented 3 months ago

As a workaround you can use

public type PayloadAnyType record {|
    @xmldata:Attribute
    string 'version?;
    string 'type?;
    json...;
|};

as expected type.

DaAlbrecht commented 3 months ago

As a workaround you can use


public type PayloadAnyType record {|

    @xmldata:Attribute

    string 'version?;

    string 'type?;

    json...;

|};

as expected type.

I want explicitly an open record sadly, so this does not work.

hasithaa commented 3 months ago

@DaAlbrecht It is an open record, but instead of open to anydata it is open to json. Do you have a requirement to use non-json values in the record?

Another option is

PayloadAnyType data = check xmldata:parseAsType(<map<json>>xmlData.toJson());
DaAlbrecht commented 2 months ago

As a workaround you can use


public type PayloadAnyType record {|

    @xmldata:Attribute

    string 'version?;

    string 'type?;

    json...;

|};

as expected type.

Sorry for the late reply, this does work as a workaround thank you!