{"record":{"id":"8d95ffa2244fc9ec","repo":"twigphp/Twig","slug":"macro-s-is-not-defined-in-template-s","errorCode":null,"errorMessage":"Macro \"%s\" is not defined in template \"%s\".","messagePattern":"Macro \"(.+?)\" is not defined in template \"(.+?)\"\\.","errorType":"exception","errorClass":"RuntimeError","httpStatus":null,"severity":"error","filePath":"src/MacroNamespace.php","lineNumber":58,"sourceCode":"        }\n\n        if (!str_starts_with($name, 'macro_') || null === $this->findDeclaredName($bareName = substr($name, \\strlen('macro_')), $context)) {\n            return false;\n        }\n\n        trigger_deprecation('twig/twig', '3.29', 'Testing whether the macro \"%s\" is defined via the \"macro_\"-prefixed name \"%s\" is deprecated; pass the bare macro name to \"%s\" instead.', $bareName, $name, MacroReferenceExpression::class);\n\n        return true;\n    }\n\n    /**\n     * @param array<int|string, mixed> $arguments\n     */\n    public function call(string $name, array $arguments, array $context, int $line, Source $source): string|Markup\n    {\n        if (null === $macro = $this->resolve($name, $context)) {\n            if (!str_starts_with($name, 'macro_') || null === $macro = $this->resolve($bareName = substr($name, \\strlen('macro_')), $context)) {\n                throw new RuntimeError(\\sprintf('Macro \"%s\" is not defined in template \"%s\".', $name, $this->template->getTemplateName()), $line, $source);\n            }\n\n            trigger_deprecation('twig/twig', '3.29', 'Calling the macro \"%s\" via the \"macro_\"-prefixed name \"%s\" is deprecated; pass the bare macro name to \"%s\" instead.', $bareName, $name, MacroReferenceExpression::class);\n        }\n\n        return $macro->callLegacy($arguments, $source, $line);\n    }\n\n    /**\n     * @return array{string, string}|null\n     */\n    private function findDeclaredName(string $name, array $context): ?array\n    {\n        $namespace = $this;\n        while (true) {\n            if (isset($namespace->macros[$name])) {\n                return [$name, $namespace->template->getTemplateName()];\n            }","sourceCodeStart":40,"sourceCodeEnd":76,"githubUrl":"https://github.com/twigphp/Twig/blob/a414c3a491defb5a60f2fc88ef79ff37c90010cd/src/MacroNamespace.php#L40-L76","documentation":"MacroNamespace::call resolves a macro name within a template's macro namespace; if neither the given name nor (for legacy \"macro_\"-prefixed names) the bare name resolves to a defined macro, Twig throws this RuntimeError. It means the macro you invoked is not defined (or imported) in the template being executed.","triggerScenarios":"Calling a macro that is not defined in the template: calling without {% import %}/{% from %}, a typo in the macro name, or (twig/twig >= 3.29) programmatically calling via the deprecated \"macro_\"-prefixed internal name when no such macro exists in the namespace.","commonSituations":"Refactorings that rename or remove a macro while callers still reference it; forgetting to import the template defining the macro; generated or compiled code using legacy macro_ prefixed names after upgrading twig/twig (deprecation added in 3.29).","solutions":["Import the template defining the macro first: {% import \"forms.twig\" as forms %} or {% from \"forms.twig\" import input %}.","Check spelling/case of the macro name against its {% macro name(...) %} definition.","If using the \"macro_\"-prefixed name programmatically, pass the bare macro name instead (deprecated since twig/twig 3.29).","Verify the macro exists in the namespace you are calling into (macros are namespaced per importing template)."],"exampleFix":"// before (Twig template)\n{{ input('text', 'email') }} {# RuntimeError: Macro \"input\" is not defined #}\n// after\n{% from \"forms.twig\" import input %}\n{{ input('text', 'email') }}","handlingStrategy":"try-catch","validationCode":"// ensure the macro exists before calling\n$src = $twig->load('forms.twig')->getSourceContext()->getCode();\nif (!preg_match('/\\{%\\s*macro\\s+input\\b/', $src)) {\n    throw new RuntimeException('Macro \"input\" is not defined in forms.twig');\n}","typeGuard":null,"tryCatchPattern":"try {\n    $html = $twig->render('page.twig', $ctx);\n} catch (\\Twig\\Error\\RuntimeError $e) {\n    if (str_contains($e->getMessage(), 'is not defined in template')) {\n        // missing/renamed macro — fix import or name\n    }\n    throw $e;\n}","preventionTips":["Always import macro templates ({% import %}/{% from %}) before calling macros.","Keep macro names centralized to avoid rename drift.","After upgrading twig/twig 3.29+, replace macro_-prefixed calls with bare macro names.","Add compile/render smoke tests for templates using macros."],"tags":["template","macro","runtime"],"backgroundTag":"method-not-implemented","analyzedSha":"a414c3a491defb5a60f2fc88ef79ff37c90010cd","analyzedAt":"2026-09-13T15:10:46.849Z","contentChangedAt":"2026-09-13T15:10:46.849Z","schemaVersion":2},"datasetVersion":"2026-09-20T23:17:15.980Z"}