Need a special offer?Find out if your project fits.
+

Don't like getData raw data format

Answered
Oleg asked on November 23, 2020

I have table where first field is date and all over fields are values.
 
getData gives me
 
data:[
{r0: '31-03-22', v0: 123, v1: 412, v2: 332},
{r0: '31-03-22', v0: 123, v1: 412, v2: 332},
{r0: '31-03-22', v0: 123, v1: 412, v2: 332}
];
and meta object {r0Name: Campaign, v0Name: someName ...}
 
Why for my visx chart i need to spend my time for adopting this data. The problem is that i want prepareData func return [
"Campaign": '31-03-22',
'someName': 123,
...
];
 
The problem is Meta object. I need to iterate and get field names with right order. But it's big thing because Object methods can't guarantee order of fields and I can't just use something like this:
const fields = [];
for(const item in rawData.meta) {
if(item.includes('Name')) fields.push(rawData.meta[item]);
}
 
because i'm getting 'Campaign' on the last position of array.
 
So know I need to use regex for 'v0Name' 'v1Name' and some sort of sorting when i iterate through my fieldNames in Meta object.
 
I don't understand how I can easy format this data. getData method needs to be modified. I want call getData and get all my data with normal field names as keys. Thanks

4 answers

Public
Oleg November 24, 2020

Maybe i can help someone.

export const drawChart = (rawData) => {
constdata=rawData.data.map(item=> {
letrowItem= {};
for (const [key, value] ofObject.entries(item)) {
for (const [key2, value2] ofObject.entries(rawData.meta)) {
if(key2===`${key}Name`) {
rowItem= {
...rowItem,
[value2 as string]: value,
}
}
}
}
returnrowItem;
})
}

Public
Oleg November 24, 2020

It's bad answer. because I can't guarantee order. Please help me

Public
Vera Didenko Vera Didenko Flexmonster November 25, 2020

Hello, Oleg,
 
Thank you for reaching out to us.
 
For such cases, we kindly recommend writing a custom data parser that returns the getData() output in the desired format.
 
We have several ready-to-use connectors for the following charting libraries: HighchartsFusionChartsGoogle Charts, and amCharts.
These connectors use the getData() API call and process the output to correspond to the specific charting library's supported data format.
The connectors' source code is open, and you are welcome to check out how the data processing was handled there.
 
According to your description, it seems the amCharts connector's implementation is close to your case. The connector transforms the output of getData() from, for example: 

data: [

   {v0: 6221870}
{r0: "blue", v0: 1046834}
{r0: "green", v0: 1103515}
{r0: "purple", v0: 29947}
{r0: "red", v0: 2179775}
{r0: "white", v0: 1806444}
{r0: "yellow", v0: 55355}

],

meta: {

cAmount: 0,
caption: "",
formats: [{…}],
r0Name: "Color",
rAmount: 1,
v0Name: "Sum of Price",
vAmount: 1,

}

to the following format: 

data: [

{Color: "blue", Sum of Price: 1046834}
{Color: "green", Sum of Price: 1103515}
{Color: "purple", Sum of Price: 29947}
{Color: "red", Sum of Price: 2179775}
{Color: "white", Sum of Price: 1806444}
{Color: "yellow", Sum of Price: 55355}

]

 
Here is a code snippet of how the amCharts connector handles the data processing: 

// "data" is the output of the getData() API call

function prepareSeries(data) {
var records = [];
var basedOnRows = false;
var basedOnColumns = false;

for (var i = 0; i < data.data.length; i++) {

// 1) Getting the needed headers:
if (i == 0) {

var headerRow = {};

if (data.meta["rAmount"] > 0) {

headerRow["r0Name"] = data.meta["r0Name"];
basedOnRows = true;

} else if (data.meta["cAmount"] > 0) {

headerRow["c0Name"] = data.meta["c0Name"];
basedOnColumns = true;
}

for (var j = 0; j < data.meta["vAmount"]; j++) {
headerRow["v" + j + "Name"] = data.meta["v" + j + "Name"];
}
}


var record = data.data[i];
var recordIsNotAFact = false;
var _record = {};

// 2) Mapping row header to data:
if (basedOnRows) {
if (record["r0"] == undefined || record["r1"] != undefined || record["c0"] != undefined || record["v0"] == undefined) continue;
_record[headerRow["r0Name"]] = record["r0"];
}

// 3) Mapping column header to data:
if (basedOnColumns) {
if (record["c0"] == undefined || record["c1"] != undefined || record["r0"] != undefined || record["v0"] == undefined) continue;
_record[headerRow["c0Name"]] = record["c0"];
}

// 4) Mapping value headers to data:
for (var j = 0; j < data.meta["vAmount"]; j++) {
if (record["v" + j] == undefined) {
recordIsNotAFact = true;
continue;
}
_record[headerRow["v" + j + "Name"]] = !isNaN(record["v" + j]) ? record["v" + j] : 0;
}

if (recordIsNotAFact) continue;
records.push(_record);
}


return records;

}

 
 
We hope this helps. Please feel free to reach out if further questions arise.
 
Kind regards, 
Vera

Public
Oleg November 26, 2020

Than you Vera!

Please login or Register to Submit Answer