V2 fix delay (#340)

* fix: avoid modifying original objects
This commit is contained in:
Carlos Valente
2023-04-15 13:26:57 +02:00
committed by GitHub
parent e9fe0c0a3a
commit 6732314f15
3 changed files with 244 additions and 128 deletions
@@ -1,127 +1,232 @@
import { formatEventList, getEventsWithDelay, trimEventlist } from '../eventsManager'; import { formatEventList, getEventsWithDelay, trimEventlist } from '../eventsManager';
test('getEventsWithDelay function', () => { describe('getEventsWithDelay function', () => {
const testData = [ test('with positive delays', () => {
{ const testData = [
title: 'Welcome to Ontime', {
timeStart: 28800000, title: 'Welcome to Ontime',
timeEnd: 30600000, timeStart: 28800000,
colour: '', timeEnd: 30600000,
type: 'event', colour: '',
id: '5946', type: 'event',
}, id: '5946',
{ },
duration: 60000, {
type: 'delay', duration: 60000,
id: '24240', type: 'delay',
}, id: '24240',
{ },
title: 'Unless recalled by the OSC address', {
timeStart: 34920000, title: 'Unless recalled by the OSC address',
timeEnd: 35520000, timeStart: 34920000,
colour: '', timeEnd: 35520000,
type: 'event', colour: '',
id: '8ee5', type: 'event',
}, id: '8ee5',
{ },
title: 'Use simpler times to create a timer', {
timeStart: 120000, title: 'Use simpler times to create a timer',
timeEnd: 720000, timeStart: 120000,
colour: '', timeEnd: 720000,
type: 'event', colour: '',
id: '8222', type: 'event',
}, id: '8222',
{ },
duration: 900000, {
type: 'delay', duration: 900000,
revision: 0, type: 'delay',
id: 'a386', revision: 0,
}, id: 'a386',
{ },
title: 'Add delay blocks to affect all events', {
timeStart: 37320000, title: 'Add delay blocks to affect all events',
timeEnd: 38520000, timeStart: 37320000,
colour: '', timeEnd: 38520000,
type: 'event', colour: '',
id: '6dce', type: 'event',
}, id: '6dce',
{ },
title: 'Add and remove events with [+] and [-]', {
timeStart: 38520000, title: 'Add and remove events with [+] and [-]',
timeEnd: 45120000, timeStart: 38520000,
colour: '', timeEnd: 45120000,
type: 'event', colour: '',
id: '2651', type: 'event',
}, id: '2651',
{ },
type: 'block', {
id: 'e6a1', type: 'block',
}, id: 'e6a1',
{ },
title: 'And control whether they are public', {
timeStart: 46800000, title: 'And control whether they are public',
timeEnd: 57600000, timeStart: 46800000,
colour: '', timeEnd: 57600000,
type: 'event', colour: '',
id: '1358', type: 'event',
}, id: '1358',
]; },
];
const expected = [ const expected = [
{ {
title: 'Welcome to Ontime', title: 'Welcome to Ontime',
timeStart: 28800000, timeStart: 28800000,
timeEnd: 30600000, timeEnd: 30600000,
colour: '', colour: '',
type: 'event', type: 'event',
id: '5946', id: '5946',
}, },
{ {
title: 'Unless recalled by the OSC address', title: 'Unless recalled by the OSC address',
timeStart: 34920000 + 60000, timeStart: 34920000 + 60000,
timeEnd: 35520000 + 60000, timeEnd: 35520000 + 60000,
colour: '', colour: '',
type: 'event', type: 'event',
id: '8ee5', id: '8ee5',
}, },
{ {
title: 'Use simpler times to create a timer', title: 'Use simpler times to create a timer',
timeStart: 120000 + 60000, timeStart: 120000 + 60000,
timeEnd: 720000 + 60000, timeEnd: 720000 + 60000,
colour: '', colour: '',
type: 'event', type: 'event',
id: '8222', id: '8222',
}, },
{ {
title: 'Add delay blocks to affect all events', title: 'Add delay blocks to affect all events',
timeStart: 37320000 + 60000 + 900000, timeStart: 37320000 + 60000 + 900000,
timeEnd: 38520000 + 60000 + 900000, timeEnd: 38520000 + 60000 + 900000,
colour: '', colour: '',
type: 'event', type: 'event',
id: '6dce', id: '6dce',
}, },
{ {
title: 'Add and remove events with [+] and [-]', title: 'Add and remove events with [+] and [-]',
timeStart: 38520000 + 60000 + 900000, timeStart: 38520000 + 60000 + 900000,
timeEnd: 45120000 + 60000 + 900000, timeEnd: 45120000 + 60000 + 900000,
colour: '', colour: '',
type: 'event', type: 'event',
id: '2651', id: '2651',
}, },
{ {
title: 'And control whether they are public', title: 'And control whether they are public',
timeStart: 46800000, timeStart: 46800000,
timeEnd: 57600000, timeEnd: 57600000,
colour: '', colour: '',
type: 'event', type: 'event',
id: '1358', id: '1358',
}, },
]; ];
expect(getEventsWithDelay(testData)).toStrictEqual(expected); expect(getEventsWithDelay(testData)).toStrictEqual(expected);
});
test('with negative delays', () => {
const testData = [
{
duration: -20,
type: 'delay',
id: '24240',
},
{
title: 'Welcome to Ontime',
timeStart: 100,
timeEnd: 200,
colour: '',
type: 'event',
id: '5946',
},
];
const expected = [
{
title: 'Welcome to Ontime',
timeStart: 80,
timeEnd: 180,
colour: '',
type: 'event',
id: '5946',
},
];
expect(getEventsWithDelay(testData)).toStrictEqual(expected);
});
}); });
describe('getEventsWithDelay edge cases', () => { describe('getEventsWithDelay edge cases', () => {
it('ensures time start cannot be below 0', () => {
const testData = [
{
duration: -200,
type: 'delay',
id: '24240',
},
{
title: 'Welcome to Ontime',
timeStart: 10,
timeEnd: 20,
colour: '',
type: 'event',
id: '5946',
},
];
const expected = [
{
title: 'Welcome to Ontime',
timeStart: 0,
timeEnd: 0,
colour: '',
type: 'event',
id: '5946',
},
];
expect(getEventsWithDelay(testData)).toStrictEqual(expected);
});
it('does not modify original array', () => {
const testData = [
{
duration: 10,
type: 'delay',
id: '24240',
},
{
title: 'Welcome to Ontime',
timeStart: 10,
timeEnd: 20,
colour: '',
type: 'event',
id: '5946',
},
];
const expected = [
{
title: 'Welcome to Ontime',
timeStart: 20,
timeEnd: 30,
colour: '',
type: 'event',
id: '5946',
},
];
const expectedSafe = [
{
title: 'Welcome to Ontime',
timeStart: 20,
timeEnd: 30,
colour: '',
type: 'event',
id: '5946',
},
];
expect(getEventsWithDelay(testData)).toStrictEqual(expected);
expect(getEventsWithDelay(expectedSafe)).toStrictEqual(expected);
});
it('given an empty array', () => { it('given an empty array', () => {
const emptyArray = { const emptyArray = {
test: [], test: [],
+21 -10
View File
@@ -11,21 +11,27 @@ import { formatTime } from './time';
export const getEventsWithDelay = (events: OntimeRundownEntry[]): OntimeEvent[] => { export const getEventsWithDelay = (events: OntimeRundownEntry[]): OntimeEvent[] => {
if (events == null) return []; if (events == null) return [];
const unfilteredEvents = [...events]; const delayedEvents: OntimeEvent[] = [];
// Add running delay // Add running delay
let delay = 0; let delay = 0;
for (const event of unfilteredEvents) { for (const event of events) {
if (event.type === SupportedEvent.Block) delay = 0; if (event.type === SupportedEvent.Block) delay = 0;
else if (event.type === SupportedEvent.Delay) delay = delay + event.duration; else if (event.type === SupportedEvent.Delay) {
else if (event.type === SupportedEvent.Event && delay > 0) { if (typeof event.duration === 'number') {
event.timeStart += delay; delay += event.duration;
event.timeEnd += delay; }
} else if (event.type === SupportedEvent.Event) {
const delayedEvent = { ...event };
if (delay !== 0) {
delayedEvent.timeStart = Math.max(delayedEvent.timeStart + delay, 0);
delayedEvent.timeEnd = Math.max(delayedEvent.timeEnd + delay, 0);
}
delayedEvents.push(delayedEvent);
} }
} }
// filter just events return delayedEvents;
return unfilteredEvents.filter((event) => event.type === SupportedEvent.Event) as OntimeEvent[];
}; };
/** /**
@@ -57,7 +63,7 @@ export const trimEventlist = (events: OntimeRundownEntry[], selectedId: string,
type FormatEventListOptionsProp = { type FormatEventListOptionsProp = {
showEnd?: boolean; showEnd?: boolean;
} };
/** /**
* @description Returns list of events formatted to be displayed * @description Returns list of events formatted to be displayed
* @param {Object[]} events - given events * @param {Object[]} events - given events
@@ -67,7 +73,12 @@ type FormatEventListOptionsProp = {
* @param {boolean} [options.showEnd] - whether to show the end time * @param {boolean} [options.showEnd] - whether to show the end time
* @returns {Object[]} Formatted list of events [{time: -, title: -, isNow, isNext}] * @returns {Object[]} Formatted list of events [{time: -, title: -, isNow, isNext}]
*/ */
export const formatEventList = (events: OntimeEvent[], selectedId: string, nextId: string, options: FormatEventListOptionsProp) => { export const formatEventList = (
events: OntimeEvent[],
selectedId: string,
nextId: string,
options: FormatEventListOptionsProp,
) => {
if (events == null) return []; if (events == null) return [];
const { showEnd = false } = options; const { showEnd = false } = options;
+1 -1
View File
@@ -46,7 +46,7 @@ type FormatOptions = {
* @param {function} resolver * @param {function} resolver
* @return {string} * @return {string}
*/ */
export const formatTime = (milliseconds: number | null, options: FormatOptions, resolver = resolveTimeFormat) => { export const formatTime = (milliseconds: number | null, options?: FormatOptions, resolver = resolveTimeFormat) => {
if (milliseconds === null) { if (milliseconds === null) {
return '...'; return '...';
} }