remotion-dev/remotion · error · Error

input ${input} does not end with a valid unit. Valid units a

Error message

input ${input} does not end with a valid unit. Valid units are: ${units.join(', ')}

What it means

Thrown by isUnitWithString (used by the transform helpers translate, translateX/Y/Z, translate3d, rotate, scale, skew, etc.) when a string argument does not end with one of the allowed units for that function. The helper validates the suffix before parsing the number, so an unrecognized suffix is rejected up front with the list of valid units.

Source

Thrown at packages/animation-utils/src/transformation-helpers/make-transform/is-unit-with-string.ts:9

import {lengthUnits} from '../../type';

export const isUnitWithString = (input: unknown, units: readonly string[]) => {
	if (typeof input !== 'string') {
		return false;
	}

	if (!units.find((u) => input.endsWith(u))) {
		throw new Error(
			`input ${input} does not end with a valid unit. Valid units are: ${units.join(
				', ',
			)}`,
		);
	}

	const match = input.match(/([0-9.]+)([a-z%]+)/);
	if (!match) {
		throw new Error(
			`input ${input} is not a valid transform. Must be a number or a string ending in one of the following units: ${lengthUnits.join(
				', ',
			)}`,
		);
	}

	return true;
};

View on GitHub (pinned to 78fe4bb3fd)

Solutions

  1. Append a valid unit from the message's list ('10' -> '10px' for lengths, '0.5' -> '0.5turn' for angles).
  2. Pass a plain number instead of a string so the helper appends its default unit (e.g. translate(100) -> 'translate(100px)').
  3. Use the template-literal types (LengthUnitString, AngleUnitString, LengthPercentageUnitString) for compile-time validation.

Example fix

// before
translate('100');     // no unit
rotate('0.25');       // no angle unit

// after
translate('100px');
rotate('0.25turn');
// or pass numbers and let the helper append the default unit:
translate(100);
rotate(0.25);
Defensive patterns

Strategy: type-guard

Validate before calling

import {lengthUnits, angleUnits, lengthPercentageUnits} from '@remotion/animation-utils/type';
const endsWithValidUnit = (s: string, units: readonly string[]): boolean =>
  units.some((u) => s.endsWith(u));
// usage: endsWithValidUnit('100', lengthPercentageUnits)

Type guard

import type {LengthUnitString, AngleUnitString, LengthPercentageUnitString} from '@remotion/animation-utils/type';
// The template-literal types enforce a number prefix + valid unit at compile time:
const translate = (x: LengthPercentageUnitString | number) => x;
translate('100px'); // ok
translate('100');    // type error

Prevention

When it happens

Trigger: Calling translate('100') (no unit), rotate('0.5') (no deg/rad/grad/turn), translate('10vw') when vw is not in the function's allowed unit list, or a typo like '10pxx'.

Common situations: Forgetting the unit on angle transforms (rotate needs deg/rad/grad/turn); using a unit not allowed for that function; passing a raw number-as-string instead of a number.

Related errors


AI-assisted analysis of remotion-dev/remotion@78fe4bb3fd (2026-08-12). Data as JSON: /api/errors/1ea5e9235e55fb0f. Report an issue: GitHub.