twigphp/Twig · error · Twig\Error\RuntimeError

Block " " on template " " does not exist.

Error message

Block "%s" on template "%s" does not exist.

What it means

BlockChain tracks the chain of template inheritance for a rendered template. throwUnknownBlock raises a RuntimeError when a block name cannot be found anywhere in the template's lineage. It is thrown by streamBlock, renderBlock and displayBlock, meaning a caller (template or PHP code) asked for a block that no template in the inheritance chain defines.

Solutions

  1. Verify the block name exists (grep the template and its parents for {% block name %}).
  2. Fix typos or update call sites after renaming a block.
  3. Clear the Twig cache (rm -rf var/cache/twig or $twig->getCache()->clear equivalent) so compiled templates match current sources.
  4. Use $template->hasBlock('name', $context) before renderBlock/displayBlock to check existence.

Example fix

// before
if ($template->hasBlock('content', $context)) {
    echo $template->renderBlock('content', $context);
}
echo $template->renderBlock('contnet', $context); // typo -> RuntimeError
// after
if ($template->hasBlock('content', $context)) {
    echo $template->renderBlock('content', $context);
}
Defensive patterns

Strategy: type-guard

Validate before calling

<?php
if (!$template->hasBlock('content', $context)) {
    throw new InvalidArgumentException("Template '{$template->getTemplateName()}' has no block 'content'");
}
echo $template->renderBlock('content', $context);

Type guard

<?php
function canRenderBlock(Twig\Template $template, string $name, array $context = []): bool
{
    return $template->hasBlock($name, $context);
}

Try / catch

<?php
use Twig\Error\RuntimeError;
try {
    $html = $template->renderBlock('content', $context);
} catch (RuntimeError $e) {
    if (str_contains($e->getMessage(), 'does not exist')) {
        $html = ''; // or a default block
    } else {
        throw $e;
    }
}

Prevention

When it happens

Trigger: Calling $template->renderBlock('name', ...), displayBlock(), or streamBlock() for a block that does not exist in the template or any of its parents; a compiled child template referencing a parent block via $this->getParent() chains that has been renamed or removed.

Common situations: Renaming or deleting a {% block %} in a parent template while children still override or render it; calling renderBlock() from PHP with a misspelled block name; template inheritance misconfiguration (extends pointing at the wrong parent); stale compiled templates after refactoring.

Understand the failure class

Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.

Related errors


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

Appendix: source

Thrown at src/BlockChain.php:189

                $lineage[] = $template;

                $parent = $template->getParent($context);
                $fixed = $fixed && $template->hasFixedParent();

                // a dynamic parent expression can evaluate to a template from another environment
                $template = $parent instanceof TemplateWrapper ? $parent->unwrap() : $parent;
                if (false !== $template && !$template->isOwnedBy($this->env)) {
                    throw new \LogicException('A block chain cannot contain templates from different Twig environments.');
                }
            } while (false !== $template);
        }

        return [$lineage, $fixed];
    }

    private function throwUnknownBlock(string $name): never
    {
        throw new RuntimeError(\sprintf('Block "%s" on template "%s" does not exist.', $name, $this->templates[0]->getTemplateName()), -1, $this->templates[0]->getSourceContext());
    }
}

View on GitHub (pinned to a414c3a491)