fix(cicd-statistics): date-fns -> luxon

Signed-off-by: Gustaf Räntilä <g.rantila@gmail.com>
This commit is contained in:
Gustaf Räntilä
2022-01-20 15:25:52 +01:00
committed by blam
parent 0a7179538a
commit ecaa8e7a15
6 changed files with 286 additions and 39 deletions
@@ -34,8 +34,8 @@ import {
Typography,
} from '@material-ui/core';
import ExpandMoreIcon from '@material-ui/icons/ExpandMore';
import { formatISO9075, parseISO } from 'date-fns';
import { countBy } from 'lodash';
import { DateTime } from 'luxon';
import { Build, FilterStatusType, statusTypes } from '../apis/types';
import { labelFormatterWithoutTime, tickFormatterX } from './utils';
@@ -56,9 +56,7 @@ export function StatusChart(props: StatusChartProps) {
builds.forEach(build => {
foundStatuses.add(build.status);
const dayString = formatISO9075(build.requestedAt, {
representation: 'date',
});
const dayString = DateTime.fromJSDate(build.requestedAt).toISODate();
const dayList = buildsByDay.get(dayString);
if (dayList) {
dayList.push(build);
@@ -75,7 +73,7 @@ export function StatusChart(props: StatusChartProps) {
),
],
values: [...buildsByDay.entries()].map(([dayString, buildThisDay]) => ({
__epoch: parseISO(dayString).getTime(),
__epoch: DateTime.fromISO(dayString).toMillis(),
...countBy(buildThisDay, 'status'),
})),
};
+43 -14
View File
@@ -15,7 +15,7 @@
*/
import React, { CSSProperties } from 'react';
import { formatISO9075, formatDistanceStrict } from 'date-fns';
import { DateTime, Duration } from 'luxon';
const infoText: CSSProperties = { color: 'InfoText' };
@@ -40,20 +40,25 @@ export function pickElements<T>(arr: ReadonlyArray<T>, num: number): Array<T> {
];
}
export function labelFormatter(epoch: number) {
return <span style={infoText}>{formatISO9075(new Date(epoch))}</span>;
function formatDateShort(milliseconds: number) {
return DateTime.fromMillis(milliseconds).toLocaleString(DateTime.DATE_SHORT);
}
export function labelFormatterWithoutTime(epoch: number) {
return (
<span style={infoText}>
{formatISO9075(new Date(epoch), { representation: 'date' })}
</span>
function formatDateTimeShort(milliseconds: number) {
return DateTime.fromMillis(milliseconds).toLocaleString(
DateTime.DATETIME_SHORT,
);
}
export function labelFormatter(epoch: number) {
return <span style={infoText}>{formatDateTimeShort(epoch)}</span>;
}
export function labelFormatterWithoutTime(epoch: number) {
return <span style={infoText}>{formatDateShort(epoch)}</span>;
}
export function tickFormatterX(epoch: number) {
return formatISO9075(new Date(epoch), { representation: 'date' });
return formatDateShort(epoch);
}
export function tickFormatterY(duration: number) {
@@ -80,8 +85,32 @@ export function tooltipValueFormatter(duration: number, name: string) {
];
}
const baseDate = new Date();
const baseEpoch = baseDate.getTime();
export function formatDuration(milliseconds: number) {
return formatDistanceStrict(baseDate, new Date(baseEpoch + milliseconds));
export function formatDuration(millis: number) {
let rest = Math.round(millis);
const days = Math.floor(rest / (1000 * 60 * 60 * 24));
rest -= days * (1000 * 60 * 60 * 24);
const hours = Math.floor(rest / (1000 * 60 * 60));
rest -= hours * (1000 * 60 * 60);
const minutes = Math.floor(rest / (1000 * 60));
rest -= minutes * (1000 * 60);
const seconds = Math.floor(rest / 1000);
rest -= seconds * 1000;
const milliseconds = rest;
if (!days && !hours && !minutes) {
if (seconds < 1) {
return `${milliseconds}ms`;
} else if (seconds < 2) {
return `${((milliseconds + seconds * 1000) / 1000).toFixed(1)}s`;
}
}
const dur = Duration.fromObject({
...(days && { days }),
...(hours && { hours }),
...(minutes && !days && { minutes }),
...(seconds && !days && !hours && { seconds }),
});
return dur.toHuman({ unitDisplay: 'narrow' }).replace(/, /g, '');
}
@@ -33,8 +33,8 @@ import {
MuiPickersUtilsProvider,
KeyboardDatePicker,
} from '@material-ui/pickers';
import { subMonths, isSameDay } from 'date-fns';
import DateFnsUtils from '@date-io/date-fns';
import { DateTime } from 'luxon';
import LuxonUtils from '@date-io/luxon';
import {
CicdConfiguration,
@@ -89,7 +89,9 @@ export function getDefaultChartFilter(
): ChartFilter {
const toDate = cicdConfiguration.defaults?.timeTo ?? new Date();
return {
fromDate: cicdConfiguration.defaults?.timeFrom ?? subMonths(toDate, 1),
fromDate:
cicdConfiguration.defaults?.timeFrom ??
DateTime.fromJSDate(toDate).minus({ months: 1 }).toJSDate(),
toDate,
branch: cicdConfiguration.defaults?.filterType ?? 'branch',
status:
@@ -104,8 +106,11 @@ function isSameChartFilter(a: ChartFilter, b: ChartFilter): boolean {
return (
a.branch === b.branch &&
[...a.status].sort().join(' ') === [...b.status].sort().join(' ') &&
isSameDay(a.fromDate, b.fromDate) &&
isSameDay(a.toDate, b.toDate)
DateTime.fromJSDate(a.fromDate).hasSame(
DateTime.fromJSDate(b.fromDate),
'day',
) &&
DateTime.fromJSDate(a.toDate).hasSame(DateTime.fromJSDate(b.toDate), 'day')
);
}
@@ -218,7 +223,7 @@ export function ChartFilters(props: ChartFiltersProps) {
const toggleUseNowAsDate = useCallback(() => {
setUseNowAsToDate(!useNowAsToDate);
if (!isSameDay(toDate, new Date())) {
if (!DateTime.fromJSDate(toDate).hasSame(DateTime.now(), 'day')) {
setToDate(new Date());
}
}, [useNowAsToDate, toDate]);
@@ -248,7 +253,7 @@ export function ChartFilters(props: ChartFiltersProps) {
}, [toDate, fromDate, branch, selectedStatus, updateFetchFilter]);
return (
<MuiPickersUtilsProvider utils={DateFnsUtils}>
<MuiPickersUtilsProvider utils={LuxonUtils}>
<Card className={classes.rootCard}>
<CardHeader
action={
@@ -283,7 +288,7 @@ export function ChartFilters(props: ChartFiltersProps) {
format="yyyy-MM-dd"
value={fromDate}
InputAdornmentProps={{ position: 'start' }}
onChange={date => setFromDate(date as any as Date)}
onChange={date => setFromDate(date?.toJSDate() ?? new Date())}
/>
<br />
<FormControl component="fieldset">
@@ -306,7 +311,7 @@ export function ChartFilters(props: ChartFiltersProps) {
format="yyyy-MM-dd"
value={toDate}
InputAdornmentProps={{ position: 'start' }}
onChange={date => setToDate(date as any as Date)}
onChange={date => setToDate(date?.toJSDate() ?? new Date())}
/>
)}
</FormGroup>
+8 -1
View File
@@ -16,9 +16,9 @@
import React, { useCallback, useState, useMemo, useEffect } from 'react';
import { Grid, makeStyles, Theme } from '@material-ui/core';
import { startOfDay, endOfDay } from 'date-fns';
import { useEntity } from '@backstage/plugin-catalog-react';
import { useApi, errorApiRef } from '@backstage/core-plugin-api';
import { DateTime } from 'luxon';
import {
useCicdStatistics,
@@ -58,6 +58,13 @@ const useStyles = makeStyles<Theme>(
},
);
function startOfDay(date: Date) {
return DateTime.fromJSDate(date).startOf('day').toJSDate();
}
function endOfDay(date: Date) {
return DateTime.fromJSDate(date).endOf('day').toJSDate();
}
interface CicdChartsProps {
cicdConfiguration: CicdConfiguration;
}