Shaheer Kochai 8d6731c7ba
feat: Centralize and Standardize Date/Time Format Handling (#6925)
* feat: change the format of uplot x axis to 24 hours

* feat: centralize date/time formats

* refactor: use the centralized 24 hour date/time formatting across components

* refactor: centralize uPlot x-axis values formatting

* feat: make the x axis of alert history in 24 hour format
2025-01-27 11:58:54 +00:00

133 lines
3.8 KiB
TypeScript

import { UsageResponsePayloadProps } from 'api/billing/getUsage';
import { DATE_TIME_FORMATS } from 'constants/dateTimeFormats';
import dayjs from 'dayjs';
import { getUPlotChartData } from 'lib/uPlotLib/utils/getUplotChartData';
import { isEmpty, isNull } from 'lodash-es';
import { unparse } from 'papaparse';
import { MetricRangePayloadProps } from 'types/api/metrics/getQueryRange';
import generateCsvData, { QuantityData } from './generateCsvData';
export const convertDataToMetricRangePayload = (
data: any,
): MetricRangePayloadProps => {
const emptyStateData = {
data: {
newResult: { data: { result: [], resultType: '' } },
result: [],
resultType: '',
},
};
if (isEmpty(data)) {
return emptyStateData;
}
const {
details: { breakdown = [] },
} = data || {};
if (isNull(breakdown) || breakdown.length === 0) {
return emptyStateData;
}
const payload = breakdown.map((info: any) => {
const metric = info.type;
const sortedBreakdownData = (info?.dayWiseBreakdown?.breakdown || []).sort(
(a: any, b: any) => a.timestamp - b.timestamp,
);
const values = (sortedBreakdownData || []).map((categoryInfo: any) => [
categoryInfo.timestamp,
categoryInfo.total,
]);
const queryName = info.type;
const legend = info.type;
const { unit } = info;
const quantity = sortedBreakdownData.map(
(categoryInfo: any) => categoryInfo.quantity,
);
return { metric, values, queryName, legend, quantity, unit };
});
const sortedData = payload.sort((a: any, b: any) => {
const sumA = a.values.reduce((acc: any, val: any) => acc + val[1], 0);
const avgA = a.values.length ? sumA / a.values.length : 0;
const sumB = b.values.reduce((acc: any, val: any) => acc + val[1], 0);
const avgB = b.values.length ? sumB / b.values.length : 0;
return sumA === sumB ? avgB - avgA : sumB - sumA;
});
return {
data: {
newResult: { data: { result: sortedData, resultType: '' } },
result: sortedData,
resultType: '',
},
};
};
export function quantityDataArr(data: any, timestampArray: number[]): any[] {
const { result } = data.data;
const transformedResultArr: any[] = [];
result.forEach((item: any) => {
const timestampToQuantityMap: { [timestamp: number]: number } = {};
item.values.forEach((val: number[], index: number) => {
timestampToQuantityMap[val[0]] = item.quantity[index];
});
const quantityArray = timestampArray.map(
(timestamp: number) => timestampToQuantityMap[timestamp] ?? null,
);
transformedResultArr.push({ ...item, quantity: quantityArray });
});
return transformedResultArr;
}
export function fillMissingValuesForQuantities(
data: any,
timestampArray: number[],
): MetricRangePayloadProps {
const transformedResultArr = quantityDataArr(data, timestampArray);
return {
data: {
newResult: { data: { result: transformedResultArr, resultType: '' } },
result: transformedResultArr,
resultType: '',
},
};
}
const formatDate = (timestamp: number): string =>
dayjs.unix(timestamp).format(DATE_TIME_FORMATS.US_DATE);
export function csvFileName(csvData: QuantityData[]): string {
if (!csvData.length) {
return `billing-usage.csv`;
}
const { values } = csvData[0];
const timestamps = values.map((item) => item[0]);
const startDate = formatDate(Math.min(...timestamps));
const endDate = formatDate(Math.max(...timestamps));
return `billing_usage_(${startDate}-${endDate}).csv`;
}
export function prepareCsvData(
data: Partial<UsageResponsePayloadProps>,
): {
csvData: string;
fileName: string;
} {
const graphCompatibleData = convertDataToMetricRangePayload(data);
const chartData = getUPlotChartData(graphCompatibleData);
const quantityMapArr = quantityDataArr(graphCompatibleData, chartData[0]);
return {
csvData: unparse(generateCsvData(quantityMapArr)),
fileName: csvFileName(quantityMapArr),
};
}