twigphp/Twig · error · RuntimeError

" " is not an enum.

Error message

"%s" is not an enum.

What it means

Thrown by CoreExtension::enum, which backs Twig's `enum` function for fetching a single enum case. When the given class string is not an existing enum (unknown class or non-enum class), it throws this RuntimeError. This is distinct from the follow-up 'is an empty enum' error thrown when the enum exists but has no cases.

Solutions

  1. Pass the exact fully-qualified enum class name and confirm with var_dump(enum_exists('App\Color'))
  2. Ensure composer autoloading is up to date (composer dump-autoload)
  3. If you have an enum instance already, you do not need this function — access ->name/->value directly
  4. Upgrade to PHP 8.1+ and convert the referenced type to a real enum if it currently is a plain class

Example fix

// before (Twig)
{{ enum('Color', 'Red').value }}
// after
{{ enum('App\\Enum\\Color', 'Red').value }}
Defensive patterns

Strategy: type-guard

Validate before calling

if (!\is_string($enum) || !\enum_exists($enum)) {
    throw new \InvalidArgumentException("Not a valid enum class: " . print_r($enum, true));
}

Type guard

function isUsableEnumClass(mixed $class): bool {
    return \is_string($class) && \enum_exists($class) && \count($class::cases()) > 0;
}

Try / catch

try {
    $case = $twig->render('t.html', ['enumClass' => $enumClass, 'case' => $caseName]);
} catch (\Twig\Error\RuntimeError $e) {
    if (str_contains($e->getMessage(), 'is not an enum') || str_contains($e->getMessage(), 'is an empty enum')) {
        // correct the class string or choose a default enum
    } else { throw $e; }
}

Prevention

When it happens

Trigger: Calling `enum('App\Color', 'Red')` in a Twig template with a wrong or non-autoloaded class name, passing a plain class or interface instead of an enum, or passing an instance/short name where the FQCN string is required.

Common situations: Typos in namespace; using an enum that was renamed or removed; referencing a const-class of a non-enum; tests rendering templates before the enum autoloads; supporting PHP < 8.1 where enum_exists is always false.

Understand the failure class

Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.

Related errors


AI-assisted analysis of twigphp/Twig@a414c3a491 (2026-09-13). Data as JSON: /api/errors/63d6ae0352e73d3d. Report an issue: GitHub.

Appendix: source

Thrown at src/Extension/CoreExtension.php:1653

        return $enum::cases();
    }

    /**
     * Provides the ability to access enums by their class names.
     *
     * @template T of \UnitEnum
     *
     * @param class-string<T> $enum
     *
     * @return T
     *
     * @internal
     */
    public static function enum(string $enum): \UnitEnum
    {
        if (!enum_exists($enum)) {
            throw new RuntimeError(\sprintf('"%s" is not an enum.', $enum));
        }

        if (!$cases = $enum::cases()) {
            throw new RuntimeError(\sprintf('"%s" is an empty enum.', $enum));
        }

        return $cases[0];
    }

    /**
     * Provides the ability to get constants from instances as well as class/global constants.
     *
     * @param string      $constant     The name of the constant
     * @param object|null $object       The object to get the constant from
     * @param bool        $checkDefined Whether to check if the constant is defined or not
     *
     * @return mixed Class constants can return many types like scalars, arrays, and
     *               objects depending on the PHP version (\BackedEnum, \UnitEnum, etc.)

View on GitHub (pinned to a414c3a491)