@datarailsshared/dr_renderer 1.4.57 → 1.4.59
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json
CHANGED
@@ -1983,14 +1983,10 @@ let getHighchartsRenderer = function ($, document, Highcharts, default_colors, h
|
|
1983
1983
|
};
|
1984
1984
|
|
1985
1985
|
highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart = function (pivotData, chartOptions, additionOptions, opts) {
|
1986
|
-
|
1987
1986
|
var pie_drill_down_series = [],
|
1988
1987
|
row_n_keys = pivotData.getRowKeys(),
|
1989
1988
|
col_n_keys = pivotData.getColKeys();
|
1990
1989
|
|
1991
|
-
var num_cols = col_n_keys.length;
|
1992
|
-
var num_rows = row_n_keys.length;
|
1993
|
-
|
1994
1990
|
const othersName = highchartsRenderer.getOthersName(opts);
|
1995
1991
|
|
1996
1992
|
lodash.forEach(col_n_keys, function (col_n_value) {
|
@@ -2009,19 +2005,17 @@ let getHighchartsRenderer = function ($, document, Highcharts, default_colors, h
|
|
2009
2005
|
col_ob.name = highchartsRenderer.getFormattedColKey(col_ob.initialName, pivotData);
|
2010
2006
|
col_ob.data = [];
|
2011
2007
|
lodash.forEach(row_n_keys, function (row_n_value) {
|
2012
|
-
|
2008
|
+
// always takes the first key during drilldown,
|
2009
|
+
// we are only supporting one level drilldown but pivot table could have multiple nested row keys
|
2010
|
+
const rowKey = [row_n_value[0]];
|
2011
|
+
var agg = pivotData.getAggregator(rowKey, col_n_value);
|
2013
2012
|
var val = agg.value();
|
2014
|
-
if (val != null &&
|
2013
|
+
if (val != null && rowKey[0]) {
|
2015
2014
|
if ($.isNumeric(val)) {
|
2016
2015
|
val = parseFloat(val);
|
2017
|
-
// if (val > -1 && val < 1) {
|
2018
|
-
// val = parseFloat(val.toPrecision(4));
|
2019
|
-
// } else {
|
2020
|
-
// val = parseFloat(val.toFixed(2));
|
2021
|
-
// }
|
2022
2016
|
}
|
2023
2017
|
|
2024
|
-
const row_initial_name =
|
2018
|
+
const row_initial_name = rowKey[0] === highchartsRenderer.DR_OTHERS_KEY ? othersName : rowKey;
|
2025
2019
|
const row_name = highchartsRenderer.getFormattedRowKey(row_initial_name, pivotData);
|
2026
2020
|
col_ob.data.push({
|
2027
2021
|
name: row_name,
|
@@ -2031,6 +2025,10 @@ let getHighchartsRenderer = function ($, document, Highcharts, default_colors, h
|
|
2031
2025
|
}
|
2032
2026
|
});
|
2033
2027
|
if (col_ob.data.length) {
|
2028
|
+
// filtering out when there are multiple data series
|
2029
|
+
col_ob.data = lodash.uniqBy(col_ob.data, item =>
|
2030
|
+
Array.isArray(item.name) ? item.name.join(highchartsRenderer.delimer) : item.name
|
2031
|
+
);
|
2034
2032
|
pie_drill_down_series.push(col_ob);
|
2035
2033
|
}
|
2036
2034
|
}
|
@@ -3195,95 +3193,6 @@ let getHighchartsRenderer = function ($, document, Highcharts, default_colors, h
|
|
3195
3193
|
return highchartsRenderer.ptCreateElementAndDraw(chartOptions, opts);
|
3196
3194
|
};
|
3197
3195
|
|
3198
|
-
highchartsRenderer.ptRenderColumnWithDrilldown = function (pivotData, opts, drilldownFunc) {
|
3199
|
-
var chartOptions = {};
|
3200
|
-
var additionOptions = opts.chartOptions ? opts.chartOptions : highchartsRenderer.getDefaultValueForChart('column-chart-drilldown');
|
3201
|
-
|
3202
|
-
|
3203
|
-
chartOptions.chart = {
|
3204
|
-
type: 'column',
|
3205
|
-
events: {
|
3206
|
-
'drilldown': function (e) {
|
3207
|
-
highchartsRenderer.modifyEventPointForDrilldown(e);
|
3208
|
-
if (drilldownFunc)
|
3209
|
-
drilldownFunc(e, this, "drilldown");
|
3210
|
-
|
3211
|
-
},
|
3212
|
-
'drillup': function (e) {
|
3213
|
-
if (drilldownFunc)
|
3214
|
-
drilldownFunc(e, this, "drillup");
|
3215
|
-
|
3216
|
-
}
|
3217
|
-
|
3218
|
-
}
|
3219
|
-
};
|
3220
|
-
if (disableAnimation) {
|
3221
|
-
chartOptions.chart.animation = false;
|
3222
|
-
}
|
3223
|
-
highchartsRenderer.setTitleAndSubTitle(chartOptions, opts, additionOptions);
|
3224
|
-
|
3225
|
-
chartOptions.yAxis = {
|
3226
|
-
min: null,
|
3227
|
-
max: null,
|
3228
|
-
title: {
|
3229
|
-
text: additionOptions && additionOptions.axisY ? additionOptions.axisY.name : ''
|
3230
|
-
},
|
3231
|
-
labels: {
|
3232
|
-
formatter: highchartsRenderer.defaultValueLabelsFormatter(pivotData, opts)
|
3233
|
-
}
|
3234
|
-
};
|
3235
|
-
if (additionOptions) {
|
3236
|
-
highchartsRenderer.setYAxisMinMax(chartOptions.yAxis, additionOptions.axisY);
|
3237
|
-
}
|
3238
|
-
|
3239
|
-
chartOptions.legend = {enabled: false};
|
3240
|
-
|
3241
|
-
chartOptions.plotOptions = {
|
3242
|
-
series: {
|
3243
|
-
animation: !disableAnimation,
|
3244
|
-
borderWidth: 0,
|
3245
|
-
cropThreshold: 1000,
|
3246
|
-
dataLabels: {
|
3247
|
-
allowOverlap: additionOptions && additionOptions.label ? additionOptions.label.overlap : false,
|
3248
|
-
enabled: additionOptions && additionOptions.label ? additionOptions.label.show : true,
|
3249
|
-
formatter: highchartsRenderer.defaultDataLabelFormatter(pivotData, opts),
|
3250
|
-
style: highchartsRenderer.getDataLabelsStyle(additionOptions)
|
3251
|
-
}
|
3252
|
-
},
|
3253
|
-
column: {
|
3254
|
-
borderRadius: 1,
|
3255
|
-
}
|
3256
|
-
};
|
3257
|
-
|
3258
|
-
chartOptions.tooltip = {
|
3259
|
-
formatter: function () {
|
3260
|
-
var y = parseFloat(this.y);
|
3261
|
-
var agg = pivotData.getAggregator([], []);
|
3262
|
-
if (agg) {
|
3263
|
-
return '<b>' + this.point.name + '</b>: ' + agg.format(y, true);
|
3264
|
-
} else {
|
3265
|
-
return '<b>' + this.point.name + '</b>: ' + y.toLocaleString();
|
3266
|
-
}
|
3267
|
-
},
|
3268
|
-
};
|
3269
|
-
|
3270
|
-
chartOptions.xAxis = {
|
3271
|
-
type: 'category',
|
3272
|
-
};
|
3273
|
-
chartOptions = highchartsRenderer.prepareAxisX(chartOptions, additionOptions, pivotData.getColKeys());
|
3274
|
-
chartOptions.series = highchartsRenderer.ptCreateSeriesToDrillDownChart(pivotData, chartOptions, additionOptions, opts);
|
3275
|
-
//if (drilldownFunc)
|
3276
|
-
// chartOptions.drilldown = {}
|
3277
|
-
//else
|
3278
|
-
chartOptions.drilldown = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(pivotData, chartOptions, additionOptions, opts);
|
3279
|
-
|
3280
|
-
highchartsRenderer.handleGridLines(additionOptions, chartOptions)
|
3281
|
-
|
3282
|
-
helpers.disableLegendInteractionIfRequired(chartOptions, additionOptions);
|
3283
|
-
|
3284
|
-
return highchartsRenderer.ptCreateElementAndDraw(chartOptions, opts);
|
3285
|
-
};
|
3286
|
-
|
3287
3196
|
highchartsRenderer.ptRenderBar = function (pivotData, opts) {
|
3288
3197
|
var chartOptions = {};
|
3289
3198
|
var rowAttrs = pivotData.rowAttrs;
|
@@ -0,0 +1,491 @@
|
|
1
|
+
import * as JQuery from "jquery";
|
2
|
+
import * as lodash from 'lodash';
|
3
|
+
import moment from 'moment/min/moment.min';
|
4
|
+
import initPivotTable from "../src/pivottable";
|
5
|
+
import initDRPivotTable from "../src/dr_pivottable";
|
6
|
+
|
7
|
+
const getHighchartsRenderer = require('../src/highcharts_renderer');
|
8
|
+
const DataFormatter = require('../src/dataformatter');
|
9
|
+
|
10
|
+
global.$ = JQuery;
|
11
|
+
global.lodash = lodash;
|
12
|
+
|
13
|
+
const Highcharts = {
|
14
|
+
Color: jest.fn(),
|
15
|
+
chart: jest.fn(),
|
16
|
+
setOptions: jest.fn(),
|
17
|
+
wrap: jest.fn(),
|
18
|
+
Tooltip: {
|
19
|
+
prototype: {
|
20
|
+
hide: jest.fn()
|
21
|
+
}
|
22
|
+
},
|
23
|
+
Point: {
|
24
|
+
prototype: {
|
25
|
+
setState: jest.fn()
|
26
|
+
}
|
27
|
+
},
|
28
|
+
Series: {
|
29
|
+
prototype: {
|
30
|
+
setState: jest.fn()
|
31
|
+
}
|
32
|
+
},
|
33
|
+
defaultOptions: {
|
34
|
+
global: {
|
35
|
+
useUTC: false
|
36
|
+
}
|
37
|
+
},
|
38
|
+
merge: jest.fn((target, source) => Object.assign({}, target, source))
|
39
|
+
};
|
40
|
+
|
41
|
+
const _document = {
|
42
|
+
createElement: jest.fn(() => ({
|
43
|
+
style: {},
|
44
|
+
setAttribute: jest.fn(),
|
45
|
+
appendChild: jest.fn()
|
46
|
+
})),
|
47
|
+
body: {
|
48
|
+
appendChild: jest.fn()
|
49
|
+
}
|
50
|
+
};
|
51
|
+
|
52
|
+
function createMockAggregator(value) {
|
53
|
+
return {
|
54
|
+
value: () => value
|
55
|
+
};
|
56
|
+
}
|
57
|
+
|
58
|
+
|
59
|
+
let highchartsRenderer = {};
|
60
|
+
|
61
|
+
describe('ptCreateDrillDownSeriesToDrilldownChart', () => {
|
62
|
+
let mockPivotData;
|
63
|
+
let mockChartOptions;
|
64
|
+
let mockAdditionOptions;
|
65
|
+
let mockOpts;
|
66
|
+
|
67
|
+
beforeAll(() => {
|
68
|
+
const _window = {
|
69
|
+
DataFormatter: DataFormatter
|
70
|
+
};
|
71
|
+
|
72
|
+
initPivotTable(JQuery, _window, _document);
|
73
|
+
initDRPivotTable(JQuery, _window, _document);
|
74
|
+
|
75
|
+
const DEFAULT_USER_COLORS = ['#7cb5ec', '#434348', '#90ed7d', '#f7a35c', '#8085e9', '#f15c80', '#e4d354', '#2b908f', '#f45b5b', '#91e8e1'];
|
76
|
+
highchartsRenderer = getHighchartsRenderer(JQuery, _document, Highcharts, lodash.cloneDeep(DEFAULT_USER_COLORS), highchartsRenderer, DataFormatter, lodash, moment, false);
|
77
|
+
});
|
78
|
+
|
79
|
+
beforeEach(() => {
|
80
|
+
const createMockAggregator = (value) => ({
|
81
|
+
value: () => value
|
82
|
+
});
|
83
|
+
|
84
|
+
mockPivotData = {
|
85
|
+
getRowKeys: jest.fn(() => [
|
86
|
+
['CITY SERVICE DEPTS'],
|
87
|
+
['MID-SOUTH'],
|
88
|
+
['NORTH TX'],
|
89
|
+
['SOUTH TX'],
|
90
|
+
['VIRGINIA'],
|
91
|
+
['CAROLINA']
|
92
|
+
]),
|
93
|
+
getColKeys: jest.fn(() => [
|
94
|
+
['003-NATIONAL ACCOUNTS'],
|
95
|
+
['015-MEMPHIS'],
|
96
|
+
['016-WICHITA FALLS'],
|
97
|
+
['017-AMARILLO'],
|
98
|
+
['019-AUSTIN'],
|
99
|
+
['020-NORFOLK'],
|
100
|
+
['023-NEWPORT NEWS'],
|
101
|
+
['035-CHARLOTTE CITY SERVICE']
|
102
|
+
]),
|
103
|
+
getAggregator: jest.fn((rowKey, colKey) => {
|
104
|
+
const rowStr = Array.isArray(rowKey) ? rowKey[0] : rowKey;
|
105
|
+
const colStr = Array.isArray(colKey) ? colKey[0] : colKey;
|
106
|
+
|
107
|
+
const dataMap = {
|
108
|
+
'CITY SERVICE DEPTS,003-NATIONAL ACCOUNTS': 305550.96,
|
109
|
+
'MID-SOUTH,015-MEMPHIS': 78827.94,
|
110
|
+
'NORTH TX,016-WICHITA FALLS': 28926.52,
|
111
|
+
'NORTH TX,017-AMARILLO': 92653.77,
|
112
|
+
'SOUTH TX,019-AUSTIN': 103645.51,
|
113
|
+
'VIRGINIA,020-NORFOLK': 0,
|
114
|
+
'VIRGINIA,023-NEWPORT NEWS': 19997.5,
|
115
|
+
'CAROLINA,035-CHARLOTTE CITY SERVICE': 124248.97
|
116
|
+
};
|
117
|
+
|
118
|
+
const key = `${rowStr},${colStr}`;
|
119
|
+
const value = dataMap[key] || null;
|
120
|
+
|
121
|
+
return createMockAggregator(value);
|
122
|
+
}),
|
123
|
+
colFormats: [
|
124
|
+
{
|
125
|
+
type: "Text",
|
126
|
+
name: "Br number & Name",
|
127
|
+
format: null,
|
128
|
+
val_not_convert: []
|
129
|
+
}
|
130
|
+
],
|
131
|
+
rowFormats: [
|
132
|
+
{
|
133
|
+
type: "Text",
|
134
|
+
name: "Area",
|
135
|
+
format: null,
|
136
|
+
val_not_convert: []
|
137
|
+
}
|
138
|
+
]
|
139
|
+
};
|
140
|
+
|
141
|
+
mockChartOptions = {
|
142
|
+
chart: {
|
143
|
+
type: 'pie'
|
144
|
+
}
|
145
|
+
};
|
146
|
+
|
147
|
+
mockAdditionOptions = {
|
148
|
+
dataLabels: {
|
149
|
+
color: '#151a41'
|
150
|
+
}
|
151
|
+
};
|
152
|
+
|
153
|
+
mockOpts = {
|
154
|
+
total_value_options: {
|
155
|
+
filter_options: {
|
156
|
+
filteredOutFieldName: 'Others'
|
157
|
+
}
|
158
|
+
}
|
159
|
+
};
|
160
|
+
|
161
|
+
jest.spyOn(highchartsRenderer, 'getFormattedColKey').mockImplementation((name) => name);
|
162
|
+
jest.spyOn(highchartsRenderer, 'getFormattedRowKey').mockImplementation((name) => Array.isArray(name) ? name : [name]);
|
163
|
+
jest.spyOn(highchartsRenderer, 'moveSeriesToSecondYAxisIfNeeded').mockImplementation(() => {});
|
164
|
+
jest.spyOn(highchartsRenderer, 'getDataLabelsStylesForDrillDown').mockReturnValue({
|
165
|
+
activeDataLabelStyle: {
|
166
|
+
color: '#151a41'
|
167
|
+
}
|
168
|
+
});
|
169
|
+
});
|
170
|
+
|
171
|
+
afterEach(() => {
|
172
|
+
jest.restoreAllMocks();
|
173
|
+
});
|
174
|
+
|
175
|
+
describe('with valid pivot data', () => {
|
176
|
+
it('should create drill-down series correctly', () => {
|
177
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
178
|
+
mockPivotData,
|
179
|
+
mockChartOptions,
|
180
|
+
mockAdditionOptions,
|
181
|
+
mockOpts
|
182
|
+
);
|
183
|
+
|
184
|
+
// Verify the structure of the result
|
185
|
+
expect(result).toHaveProperty('activeDataLabelStyle');
|
186
|
+
expect(result).toHaveProperty('series');
|
187
|
+
expect(result.activeDataLabelStyle).toEqual({
|
188
|
+
color: '#151a41'
|
189
|
+
});
|
190
|
+
|
191
|
+
// Verify series structure
|
192
|
+
expect(Array.isArray(result.series)).toBe(true);
|
193
|
+
expect(result.series.length).toBe(7);
|
194
|
+
|
195
|
+
// Check first series (003-NATIONAL ACCOUNTS)
|
196
|
+
const firstSeries = result.series[0];
|
197
|
+
expect(firstSeries).toMatchObject({
|
198
|
+
id: '003-NATIONAL ACCOUNTS',
|
199
|
+
initialName: '003-NATIONAL ACCOUNTS',
|
200
|
+
name: '003-NATIONAL ACCOUNTS',
|
201
|
+
data: expect.any(Array)
|
202
|
+
});
|
203
|
+
|
204
|
+
// Verify data points in first series
|
205
|
+
expect(firstSeries.data).toHaveLength(1);
|
206
|
+
expect(firstSeries.data[0]).toMatchObject({
|
207
|
+
name: ['CITY SERVICE DEPTS'],
|
208
|
+
initialName: ['CITY SERVICE DEPTS'],
|
209
|
+
y: 305550.96
|
210
|
+
});
|
211
|
+
});
|
212
|
+
|
213
|
+
it('should handle numeric column IDs correctly', () => {
|
214
|
+
// Test with numeric column keys
|
215
|
+
mockPivotData.getColKeys.mockReturnValue([
|
216
|
+
[123],
|
217
|
+
[456]
|
218
|
+
]);
|
219
|
+
|
220
|
+
mockPivotData.getAggregator.mockImplementation(() => createMockAggregator(100));
|
221
|
+
|
222
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
223
|
+
mockPivotData,
|
224
|
+
mockChartOptions,
|
225
|
+
mockAdditionOptions,
|
226
|
+
mockOpts
|
227
|
+
);
|
228
|
+
|
229
|
+
expect(result.series[0].id).toBe(123);
|
230
|
+
expect(result.series[1].id).toBe(456);
|
231
|
+
});
|
232
|
+
|
233
|
+
it('should handle boolean column IDs correctly', () => {
|
234
|
+
// Test with boolean column keys
|
235
|
+
mockPivotData.getColKeys.mockReturnValue([
|
236
|
+
[true],
|
237
|
+
[false]
|
238
|
+
]);
|
239
|
+
|
240
|
+
mockPivotData.getAggregator.mockImplementation(() => createMockAggregator(100));
|
241
|
+
|
242
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
243
|
+
mockPivotData,
|
244
|
+
mockChartOptions,
|
245
|
+
mockAdditionOptions,
|
246
|
+
mockOpts
|
247
|
+
);
|
248
|
+
|
249
|
+
expect(result.series[0].id).toBe('true');
|
250
|
+
expect(result.series[1].id).toBe('false');
|
251
|
+
});
|
252
|
+
|
253
|
+
it('should filter out null values', () => {
|
254
|
+
mockPivotData.getAggregator.mockImplementation((rowKey, colKey) => {
|
255
|
+
const rowStr = Array.isArray(rowKey) ? rowKey[0] : rowKey;
|
256
|
+
const colStr = Array.isArray(colKey) ? colKey[0] : colKey;
|
257
|
+
|
258
|
+
// Return null for specific combinations
|
259
|
+
if (rowStr === 'CITY SERVICE DEPTS' && colStr === '015-MEMPHIS') {
|
260
|
+
return { value: () => null };
|
261
|
+
}
|
262
|
+
|
263
|
+
return { value: () => 100 };
|
264
|
+
});
|
265
|
+
|
266
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
267
|
+
mockPivotData,
|
268
|
+
mockChartOptions,
|
269
|
+
mockAdditionOptions,
|
270
|
+
mockOpts
|
271
|
+
);
|
272
|
+
|
273
|
+
// Find the series for '015-MEMPHIS'
|
274
|
+
const memphisSeries = result.series.find(s => s.id === '015-MEMPHIS');
|
275
|
+
|
276
|
+
// Should not include data point with null value
|
277
|
+
expect(memphisSeries.data).not.toContainEqual(
|
278
|
+
expect.objectContaining({
|
279
|
+
name: ['CITY SERVICE DEPTS']
|
280
|
+
})
|
281
|
+
);
|
282
|
+
});
|
283
|
+
|
284
|
+
it('should handle undefined column keys', () => {
|
285
|
+
mockPivotData.getColKeys.mockReturnValue([
|
286
|
+
[undefined],
|
287
|
+
['valid-key']
|
288
|
+
]);
|
289
|
+
|
290
|
+
mockPivotData.getAggregator.mockImplementation((rowKey, colKey) => {
|
291
|
+
return { value: () => 100 }; // Return valid value for all combinations
|
292
|
+
});
|
293
|
+
|
294
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
295
|
+
mockPivotData,
|
296
|
+
mockChartOptions,
|
297
|
+
mockAdditionOptions,
|
298
|
+
mockOpts
|
299
|
+
);
|
300
|
+
|
301
|
+
// Should only process series with defined column keys (undefined keys are filtered out)
|
302
|
+
expect(result.series).toHaveLength(1);
|
303
|
+
expect(result.series[0].id).toBe('valid-key');
|
304
|
+
});
|
305
|
+
|
306
|
+
it('should handle empty row keys', () => {
|
307
|
+
mockPivotData.getRowKeys.mockReturnValue([
|
308
|
+
[null],
|
309
|
+
[''],
|
310
|
+
['valid-row']
|
311
|
+
]);
|
312
|
+
|
313
|
+
mockPivotData.getAggregator.mockImplementation((rowKey) => {
|
314
|
+
const rowStr = Array.isArray(rowKey) ? rowKey[0] : rowKey;
|
315
|
+
if (!rowStr) {
|
316
|
+
return { value: () => 100 };
|
317
|
+
}
|
318
|
+
return { value: () => 200 };
|
319
|
+
});
|
320
|
+
|
321
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
322
|
+
mockPivotData,
|
323
|
+
mockChartOptions,
|
324
|
+
mockAdditionOptions,
|
325
|
+
mockOpts
|
326
|
+
);
|
327
|
+
|
328
|
+
// Should filter out data points with null/empty row keys
|
329
|
+
result.series.forEach(series => {
|
330
|
+
series.data.forEach(dataPoint => {
|
331
|
+
expect(dataPoint.name[0]).toBeTruthy();
|
332
|
+
});
|
333
|
+
});
|
334
|
+
});
|
335
|
+
|
336
|
+
it('should convert string numbers to float', () => {
|
337
|
+
mockPivotData.getAggregator.mockImplementation(() => ({
|
338
|
+
value: () => '123.45' // Return string number
|
339
|
+
}));
|
340
|
+
|
341
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
342
|
+
mockPivotData,
|
343
|
+
mockChartOptions,
|
344
|
+
mockAdditionOptions,
|
345
|
+
mockOpts
|
346
|
+
);
|
347
|
+
|
348
|
+
result.series.forEach(series => {
|
349
|
+
series.data.forEach(dataPoint => {
|
350
|
+
expect(typeof dataPoint.y).toBe('number');
|
351
|
+
expect(dataPoint.y).toBe(123.45);
|
352
|
+
});
|
353
|
+
});
|
354
|
+
});
|
355
|
+
|
356
|
+
it('should remove duplicate data points', () => {
|
357
|
+
// Mock duplicate row keys
|
358
|
+
mockPivotData.getRowKeys.mockReturnValue([
|
359
|
+
['DUPLICATE'],
|
360
|
+
['DUPLICATE'],
|
361
|
+
['UNIQUE']
|
362
|
+
]);
|
363
|
+
|
364
|
+
mockPivotData.getAggregator.mockImplementation(() => ({
|
365
|
+
value: () => 100
|
366
|
+
}));
|
367
|
+
|
368
|
+
// Mock getFormattedRowKey to return same name for duplicates
|
369
|
+
jest.spyOn(highchartsRenderer, 'getFormattedRowKey').mockImplementation((name) => {
|
370
|
+
if (Array.isArray(name) && name[0] === 'DUPLICATE') {
|
371
|
+
return ['DUPLICATE'];
|
372
|
+
}
|
373
|
+
return Array.isArray(name) ? name : [name];
|
374
|
+
});
|
375
|
+
|
376
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
377
|
+
mockPivotData,
|
378
|
+
mockChartOptions,
|
379
|
+
mockAdditionOptions,
|
380
|
+
mockOpts
|
381
|
+
);
|
382
|
+
|
383
|
+
// Each series should have unique data points
|
384
|
+
result.series.forEach(series => {
|
385
|
+
const names = series.data.map(d => d.name.join(','));
|
386
|
+
const uniqueNames = [...new Set(names)];
|
387
|
+
expect(names.length).toBe(uniqueNames.length);
|
388
|
+
});
|
389
|
+
});
|
390
|
+
|
391
|
+
it('should call helper functions with correct parameters', () => {
|
392
|
+
highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
393
|
+
mockPivotData,
|
394
|
+
mockChartOptions,
|
395
|
+
mockAdditionOptions,
|
396
|
+
mockOpts
|
397
|
+
);
|
398
|
+
|
399
|
+
expect(highchartsRenderer.moveSeriesToSecondYAxisIfNeeded).toHaveBeenCalledWith(
|
400
|
+
expect.any(Array),
|
401
|
+
mockPivotData,
|
402
|
+
mockChartOptions,
|
403
|
+
mockAdditionOptions,
|
404
|
+
mockOpts
|
405
|
+
);
|
406
|
+
expect(highchartsRenderer.getDataLabelsStylesForDrillDown).toHaveBeenCalledWith(mockAdditionOptions);
|
407
|
+
});
|
408
|
+
});
|
409
|
+
|
410
|
+
describe('edge cases', () => {
|
411
|
+
it('should handle empty column keys', () => {
|
412
|
+
mockPivotData.getColKeys.mockReturnValue([]);
|
413
|
+
|
414
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
415
|
+
mockPivotData,
|
416
|
+
mockChartOptions,
|
417
|
+
mockAdditionOptions,
|
418
|
+
mockOpts
|
419
|
+
);
|
420
|
+
|
421
|
+
expect(result.series).toHaveLength(0);
|
422
|
+
});
|
423
|
+
|
424
|
+
it('should handle empty row keys', () => {
|
425
|
+
mockPivotData.getRowKeys.mockReturnValue([]);
|
426
|
+
|
427
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
428
|
+
mockPivotData,
|
429
|
+
mockChartOptions,
|
430
|
+
mockAdditionOptions,
|
431
|
+
mockOpts
|
432
|
+
);
|
433
|
+
|
434
|
+
// Series should exist but have no data
|
435
|
+
result.series.forEach(series => {
|
436
|
+
expect(series.data).toHaveLength(0);
|
437
|
+
});
|
438
|
+
});
|
439
|
+
|
440
|
+
it('should filter out series with no data', () => {
|
441
|
+
// Mock aggregator to return null for all combinations
|
442
|
+
mockPivotData.getAggregator.mockImplementation(() => ({
|
443
|
+
value: () => null
|
444
|
+
}));
|
445
|
+
|
446
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
447
|
+
mockPivotData,
|
448
|
+
mockChartOptions,
|
449
|
+
mockAdditionOptions,
|
450
|
+
mockOpts
|
451
|
+
);
|
452
|
+
|
453
|
+
expect(result.series).toHaveLength(0);
|
454
|
+
});
|
455
|
+
});
|
456
|
+
|
457
|
+
describe('with Others key handling', () => {
|
458
|
+
it('should replace DR_OTHERS_KEY with othersName', () => {
|
459
|
+
// Mock DR_OTHERS_KEY constant
|
460
|
+
highchartsRenderer.DR_OTHERS_KEY = 'DR_OTHERS_KEY';
|
461
|
+
|
462
|
+
mockPivotData.getColKeys.mockReturnValue([
|
463
|
+
['DR_OTHERS_KEY'],
|
464
|
+
['normal-key']
|
465
|
+
]);
|
466
|
+
|
467
|
+
mockPivotData.getRowKeys.mockReturnValue([
|
468
|
+
['DR_OTHERS_KEY'],
|
469
|
+
['normal-row']
|
470
|
+
]);
|
471
|
+
|
472
|
+
// Mock aggregator to return valid data
|
473
|
+
mockPivotData.getAggregator.mockImplementation((rowKey, colKey) => {
|
474
|
+
return { value: () => 100 }; // Return valid value for all combinations
|
475
|
+
});
|
476
|
+
|
477
|
+
const result = highchartsRenderer.ptCreateDrillDownSeriesToDrilldownChart(
|
478
|
+
mockPivotData,
|
479
|
+
mockChartOptions,
|
480
|
+
mockAdditionOptions,
|
481
|
+
mockOpts
|
482
|
+
);
|
483
|
+
|
484
|
+
// Check that DR_OTHERS_KEY is replaced with Others name
|
485
|
+
const othersColSeries = result.series.find(s => s.initialName === 'Others');
|
486
|
+
expect(othersColSeries).toBeDefined();
|
487
|
+
expect(othersColSeries.name).toBe('Others');
|
488
|
+
});
|
489
|
+
});
|
490
|
+
});
|
491
|
+
|