mirror of
https://github.com/grafana/grafana.git
synced 2025-02-12 00:25:46 -06:00
Transforms: allow boolean in field calculations (#30802)
This commit is contained in:
parent
25ef563a53
commit
c9c7bfbcaa
@ -21,6 +21,7 @@ const seriesBC = toDataFrame({
|
||||
{ name: 'B', type: FieldType.number, values: [2, 200] },
|
||||
{ name: 'C', type: FieldType.number, values: [3, 300] },
|
||||
{ name: 'D', type: FieldType.string, values: ['first', 'second'] },
|
||||
{ name: 'E', type: FieldType.boolean, values: [true, false] },
|
||||
],
|
||||
});
|
||||
|
||||
@ -48,6 +49,7 @@ describe('calculateField transformer w/ timeseries', () => {
|
||||
B: 2,
|
||||
C: 3,
|
||||
D: 'first',
|
||||
E: true,
|
||||
'The Total': 6,
|
||||
TheTime: 1000,
|
||||
},
|
||||
@ -56,6 +58,7 @@ describe('calculateField transformer w/ timeseries', () => {
|
||||
B: 200,
|
||||
C: 300,
|
||||
D: 'second',
|
||||
E: false,
|
||||
'The Total': 600,
|
||||
TheTime: 2000,
|
||||
},
|
||||
@ -129,7 +132,7 @@ describe('calculateField transformer w/ timeseries', () => {
|
||||
mode: CalculateFieldMode.BinaryOperation,
|
||||
binary: {
|
||||
left: 'B',
|
||||
operation: BinaryOperationID.Add,
|
||||
operator: BinaryOperationID.Add,
|
||||
right: 'C',
|
||||
},
|
||||
replaceFields: true,
|
||||
@ -160,7 +163,7 @@ describe('calculateField transformer w/ timeseries', () => {
|
||||
mode: CalculateFieldMode.BinaryOperation,
|
||||
binary: {
|
||||
left: 'B',
|
||||
operation: BinaryOperationID.Add,
|
||||
operator: BinaryOperationID.Add,
|
||||
right: '2',
|
||||
},
|
||||
replaceFields: true,
|
||||
@ -183,4 +186,37 @@ describe('calculateField transformer w/ timeseries', () => {
|
||||
]);
|
||||
});
|
||||
});
|
||||
|
||||
it('boolean field', async () => {
|
||||
const cfg = {
|
||||
id: DataTransformerID.calculateField,
|
||||
options: {
|
||||
mode: CalculateFieldMode.BinaryOperation,
|
||||
binary: {
|
||||
left: 'E',
|
||||
operator: BinaryOperationID.Multiply,
|
||||
right: '1',
|
||||
},
|
||||
replaceFields: true,
|
||||
},
|
||||
};
|
||||
|
||||
await expect(transformDataFrame([cfg], [seriesBC])).toEmitValuesWith((received) => {
|
||||
const data = received[0];
|
||||
const filtered = data[0];
|
||||
const rows = new DataFrameView(filtered).toArray();
|
||||
expect(rows).toMatchInlineSnapshot(`
|
||||
Array [
|
||||
Object {
|
||||
"E * 1": 1,
|
||||
"TheTime": 1000,
|
||||
},
|
||||
Object {
|
||||
"E * 1": 0,
|
||||
"TheTime": 2000,
|
||||
},
|
||||
]
|
||||
`);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
@ -7,6 +7,7 @@ import { getFieldMatcher } from '../matchers';
|
||||
import { FieldMatcherID } from '../matchers/ids';
|
||||
import { RowVector } from '../../vector/RowVector';
|
||||
import { ArrayVector, BinaryOperationVector, ConstantVector } from '../../vector';
|
||||
import { AsNumberVector } from '../../vector/AsNumberVector';
|
||||
import { getTimeField } from '../../dataframe/processDataFrame';
|
||||
import defaults from 'lodash/defaults';
|
||||
import { BinaryOperationID, binaryOperators } from '../../utils/binaryOperators';
|
||||
@ -187,6 +188,9 @@ function findFieldValuesWithNameOrConstant(frame: DataFrame, name: string, allFr
|
||||
|
||||
for (const f of frame.fields) {
|
||||
if (name === getFieldDisplayName(f, frame, allFrames)) {
|
||||
if (f.type === FieldType.boolean) {
|
||||
return new AsNumberVector(f.values);
|
||||
}
|
||||
return f.values;
|
||||
}
|
||||
}
|
||||
|
16
packages/grafana-data/src/vector/AsNumberVector.ts
Normal file
16
packages/grafana-data/src/vector/AsNumberVector.ts
Normal file
@ -0,0 +1,16 @@
|
||||
import { Vector } from '../types';
|
||||
import { FunctionalVector } from './FunctionalVector';
|
||||
|
||||
export class AsNumberVector extends FunctionalVector<number> {
|
||||
constructor(private field: Vector) {
|
||||
super();
|
||||
}
|
||||
|
||||
get length() {
|
||||
return this.field.length;
|
||||
}
|
||||
|
||||
get(index: number) {
|
||||
return +this.field.get(index);
|
||||
}
|
||||
}
|
@ -6,5 +6,6 @@ export * from './BinaryOperationVector';
|
||||
export * from './SortedVector';
|
||||
export * from './FormattedVector';
|
||||
export * from './IndexVector';
|
||||
export * from './AsNumberVector';
|
||||
|
||||
export { vectorator } from './FunctionalVector';
|
||||
|
@ -39,6 +39,8 @@ const calculationModes = [
|
||||
{ value: CalculateFieldMode.ReduceRow, label: 'Reduce row' },
|
||||
];
|
||||
|
||||
const okTypes = new Set<FieldType>([FieldType.time, FieldType.number, FieldType.string]);
|
||||
|
||||
export class CalculateFieldTransformerEditor extends React.PureComponent<
|
||||
CalculateFieldTransformerEditorProps,
|
||||
CalculateFieldTransformerEditorState
|
||||
@ -86,7 +88,7 @@ export class CalculateFieldTransformerEditor extends React.PureComponent<
|
||||
|
||||
for (const frame of input) {
|
||||
for (const field of frame.fields) {
|
||||
if (field.type !== FieldType.number) {
|
||||
if (!okTypes.has(field.type)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user