mifi/lossless-cut · error · UserFacingError

Invalid start or end value. Must contain a number of seconds

Error message

Invalid start or end value. Must contain a number of seconds

What it means

Thrown by parseCsv() after all rows are mapped, when the every() check finds at least one segment whose start (or end) is NaN. The parseTimeFn callback (e.g. parseCsvTime or a frame-based parser) returned NaN for a cell, meaning the cell could not be interpreted as a number of seconds or a recognized timecode. The error is raised because LosslessCut cannot place a segment whose boundary is not a finite number on the timeline.

Source

Thrown at src/renderer/src/edlFormats.ts:103

      ...(name != null && { name: name?.trim() }),
      ...(tagsColumns.length > 0 && {
        tags: Object.fromEntries(tagsColumns.flatMap((tagValue, tagIndex) => {
          if (tagValue.trim() === '') return [];
          return [[
            tagsKeys?.[tagIndex] ?? `tag${tagIndex + 1}`,
            tagValue.trim(),
          ]];
        })),
      }),
    }];
  });

  if (!mapped.every(({ start, end }) => (
    !Number.isNaN(start)
    && (end === undefined || !Number.isNaN(end))
  ))) {
    console.log(mapped);
    throw new UserFacingError(i18n.t('Invalid start or end value. Must contain a number of seconds'));
  }

  return mapped;
}

export async function parseCutlist(clStr: string) {
  // first parse INI-File into "iniValue" object
  const regex = {
    section: /^\s*\[\s*([^\]]*)\s*]\s*$/,
    param: /^\s*([^=]+?)\s*=\s*(.*?)\s*$/,
    comment: /^\s*;.*$/,
  };
  const iniValue: Record<string, string | undefined | Record<string, string | undefined>> = {};

  const lines = clStr.split(/[\n\r]+/);
  let section: string | undefined;
  lines.forEach((line) => {
    if (regex.comment.test(line)) {

View on GitHub (pinned to 3b9a59c288)

Solutions

  1. Inspect console.log(mapped) output (the source logs it before throwing) to find which row has NaN start/end.
  2. Correct or remove the offending cell so the Start/End columns contain a value the active parser understands (plain seconds like 12.5, or a supported timecode).
  3. Match the import time parser to the CSV's actual format (seconds vs HH:MM:SS vs frame number).
  4. Sanitize the CSV in a spreadsheet: force Start/End columns to numeric, remove thousands separators and convert commas to dots.

Example fix

// before
return parseCsv(text, parseCsvTime);

// after
// pre-validate each Start/End cell is a finite number of seconds
const rows = csvParse(text, {});
const bad = rows.find(([s]) => s != null && Number.isNaN(parseCsvTime(s)));
if (bad) throw new Error(`Unparseable start time: '${bad[0]}'`);
return parseCsv(text, parseCsvTime);
Defensive patterns

Strategy: validation

Validate before calling

// Pre-validate that every Start/End cell parses to a finite number
import { csvParse } from 'csv-parse/sync';
export function validateCsvTimes(csvStr: string, parseTimeFn: (s: string) => number | undefined): string[] {
  const rows = csvParse(csvStr, {});
  const problems: string[] = [];
  rows.forEach(([start, end], i) => {
    if (start != null && Number.isNaN(parseTimeFn(start) ?? NaN)) problems.push(`Row ${i + 1} start '${start}' is not a number`);
    if (end != null && Number.isNaN(parseTimeFn(end) ?? NaN)) problems.push(`Row ${i + 1} end '${end}' is not a number`);
  });
  return problems;
}

Type guard

const isFiniteSeconds = (v: unknown): v is number => typeof v === 'number' && Number.isFinite(v);

Try / catch

try {
  return parseCsv(text, parser);
} catch (err) {
  if (err instanceof UserFacingError && /Invalid start or end/.test(err.message)) {
    const problems = validateCsvTimes(text, parser);
    showError('Unparseable time values', problems.join('\n'));
    return [];
  }
  throw err;
}

Prevention

When it happens

Trigger: A CSV row whose Start or End column contains non-numeric text (e.g. 'foo', '', 'N/A') while using a numeric/seconds parser; a timecode string the chosen parseTimeFn does not recognize (e.g. '1:23:45.6' fed to a pure-seconds parser); a locale-specific decimal separator ('1,5') parsed by a parseFloat that yields NaN.

Common situations: Hand-edited CSVs where a user typed a label into the Start column; CSVs exported with a different time format (HH:MM:SS vs seconds) than the selected import parser expects; spreadsheets that formatted times as text or inserted stray quote characters; mixed delimiter (semicolon CSV opened as comma).

Related errors


AI-assisted analysis of mifi/lossless-cut@3b9a59c288 (2026-08-12). Data as JSON: /api/errors/35843a297fe0adfd. Report an issue: GitHub.