Automatic DDS data to JSON for web integration service

6 posts / 0 new
Last post
Offline
Last seen: 5 years 4 months ago
Joined: 03/25/2015
Posts: 33
Automatic DDS data to JSON for web integration service

Hello,

I am currently experimenting on usage of RTI web integration service between the publisher and subscriber that are C++ based.

I noticed that the data POST/GET is in either JSON/XML format.. What are the options available in the automatic data conversion/serialization to JSON/XML format?

The last option could be writing the converters for each and every type.

Thanks.

Uday

Organization:
manuelBaena's picture
Offline
Last seen: 3 years 6 days ago
Joined: 06/27/2017
Posts: 8

Hello Uday,

You can convert the data to XML or JSON using the API DDS_DynamicDataFormatter_to_xml or DDS_DynamicDataFormatter_to_json. Please, be aware that both DDS_DynamicDataFormatter_to_json() and DDS_DynamicDataFormatter_to_xml() are internal, and they are not included in the public Connext DDS API. You can use them but taking into account that their specification could change in the future.

To use this mechanism and convert a sample to XML/JSON format, you can serialize the sample to CDR buffer, instantiate a DynamicData sample, and finally, translate the DynamicData sample to XML or JSON.

In the following code snippets you can see all the steps that you can follow to perform this task:

1. Define the parameters that you will need to perform the conversion (DynamicData, CDR and JSON).

// 1.1 DynamicData
 DDS_DynamicData *dynData = NULL;
 struct DDS_DynamicDataTypeProperty_t props;
 struct DDS_TypeCode * type_code = NULL;
 DDSDynamicDataTypeSupport *type_support = NULL;
 
 // 1.2 CDR
 unsigned int cdrbufferlength = HelloWorldPlugin_get_serialized_sample_max_size(
 NULL, RTI_TRUE, RTI_CDR_ENCAPSULATION_ID_CDR_NATIVE, 0);
 char *cdrbuffer = new char[cdrbufferlength];
 
 // 1.3 JSON
 unsigned int jsonbufferlength = 100; // estimated size
 char *jsonbuffer = new char[jsonbufferlength];
 
 // 1.4 XML
 unsigned int xmlbufferlength = 100; // estimated size
 char *xmlbuffer = new char[xmlbufferlength];

2. Initialize the TypeCode.

type_code = HelloWorld_get_typecode();
if (type_code == NULL) {
    printf("get_typecode error\n");
    publisher_shutdown(participant);
    return -1;
}

3. Initialize the type support:

type_support = new DDSDynamicDataTypeSupport(type_code, props);
if (type_support == NULL) {
    printf("constructor DynamicDataTypeSupport error\n");
    publisher_shutdown(participant);
    return -1;
}

 

4. Initialize the dynamic data:

dynData = type_support->create_data();
if (dynData == NULL) {
    printf("create_dynamic_data error\n");
    publisher_shutdown(participant);
    return -1;
}

 

For each sample that you want to convert, you would need to perform the following tasks:

5. Serialize the sample to the CDR buffer:

if (!HelloWorldPlugin_serialize_to_cdr_buffer(
 cdrbuffer,
 &cdrbufferlength,
 instance)){
    printf("serializing typed sample to cdr buffer error\n");
}
 


6. Instantiate the dynamic data with the cdr buffer:

retcode = DDS_DynamicData_from_cdr_buffer(
 dynData,
 cdrbuffer,
 cdrbufferlength);
if (retcode != DDS_RETCODE_OK) {
    printf("DDS_DynamicData_from_cdr_buffer error %d\n", retcode);
    publisher_shutdown(participant);
    return -1;
}


7. Translate the dynamic data to JSON or XML:

// XML translation:
retcode = DDS_DynamicDataFormatter_to_xml(dynData, xmlBuffer, &xmlBufferLength, 0);
if (retcode != DDS_RETCODE_OK) {
    printf("Error converting from Dynamic Data to XML");
    publisher_shutdown(participant);
    return -1;
}
printf("XML Data:\n%s\n\n", xmlBuffer);
 
// JSON translation:
retcode = DDS_DynamicDataFormatter_to_json(dynData, jsonbuffer, &jsonBufferLength, 0);
if (retcode != DDS_RETCODE_OK) {
    printf("Error converting from Dynamic Data to JSON");
    publisher_shutdown(participant);
    return -1;
}
printf("JSON Data:\n%s\n", jsonbuffer);


Hope this fits your request.

Regards,
Manuel

Offline
Last seen: 5 years 4 months ago
Joined: 03/25/2015
Posts: 33

Hi Manuel,

I accidentally got into this page, when I noticed that there was a response. I coninuosly monitored this thread for few weeks after which I left. I probably got an email which I didn't notice. Sorry for that.

In any case, thanks a lot for the detailed response. Will consider looking into it. For now, a python-way approach is being looked into in parallel.

Thanks.

Uday

Offline
Last seen: 7 years 3 weeks ago
Joined: 11/01/2017
Posts: 1

Hi All,

Not sure if this is the right place for my question. If not, please let me know where I can post the question.
 

I was working with RTI Web Integration Service 5.2.3 EAR  and we had to send any enumeration in the data via a http post operation as the ordinal value of the enumeration (int value). As I understand, with the latest version of RTI Web Integration service, it defaults to using the string representation of the enum instead.

This means we have to make quite a lot of changes in our code base. I wonder if there is a setting when starting the web integration service to have it continue to use the ordinal value instead of defaulting to the string value.

I tried to search for any documentation regarding this but was not successful.

 

Any help and/or recommendation shall be greatly appreciated.

Thank you,

Tri

Offline
Last seen: 7 years 2 weeks ago
Joined: 09/17/2015
Posts: 53

Somehow my reply to this topic got lost. Anyways, you can modify the Apache Velocity template of the rtiddsgen to create your own serialization function using any JSON/XML or whatever library you'd like to use. It is pretty simple to do so.

Fernando Garcia's picture
Offline
Last seen: 4 months 1 week ago
Joined: 05/18/2011
Posts: 200

Hi Tri,

This means we have to make quite a lot of changes in our code base. I wonder if there is a setting when starting the web integration service to have it continue to use the ordinal value instead of defaulting to the string value.

In the write operation you can provide both the integer representation and the string representation of the Enumeration value; the parser takes care of transforming what you pass to the right format.

However, as you mentioned, the default representation for the READ operation has changed from 5.2.3 (Early Access Release) to 5.3.0 (General Access Release). Now, enumeration values are by default represented as strings as opposed to integers. Fortunately, there is a query parameter called  enumAsIntegers that you can use to change this behavior (see Reference Documentation here); you will have to append it to your GET request as follows:

GET http://<hostname>[:port]/dds/rest1/../data_readers/YourDataReader?enumsAsIntegers=true HTTP/1.1

Please, let me know if this would work for you and whether you have run into any other issues when upgrading.

Thanks,
Fernando.