withastro/astro · error · AstroError
NoMatchingRenderer
NoMatchingRenderer
Error message
Unable to render `${componentName}`.
There are ${validRenderersCount} renderers configured in your `astro.config.mjs` file,
but none were able to server-side render `${componentName}`. What it means
With client:only="react|preact|vue|svelte|solid(-js)" the hint string is recognized (rendererAliases maps solid to solid-js), but no configured renderer matches it: none of the integrations in astro.config can hydrate that framework, so NoMatchingRenderer is thrown stating how many renderers are configured and hinting at the probable ones. The renderer must be installed and registered even for client:only components.
Solutions
- Run npx astro add <framework> (e.g. npx astro add preact) to install and register the matching integration
- Verify the integrations array in astro.config.mjs actually includes the renderer for the hinted framework
- Restart the dev server after config changes
- Alternatively change the hint to a framework you already have installed, if the component supports it
Example fix
// before: astro.config.mjs integrations: [react()] // component uses client:only="preact" // after import preact from '@astrojs/preact'; integrations: [react(), preact()]
Defensive patterns
Strategy: validation
Validate before calling
// CI check: every client:only hint must have a matching integration
const hints = ['react', 'preact', 'vue', 'svelte', 'solid-js']; // values used in templates
const installed = config.integrations.map((i) => i.name);
for (const h of hints) {
if (!installed.some((n) => n.includes(h.replace('-js', '')))) {
throw new Error('client:only="' + h + '" used but its renderer is not in astro.config');
}
} Type guard
function hasRendererFor(config: { integrations: { name: string }[] }, framework: string): boolean {
return config.integrations.some((i) => i.name.includes(framework));
} Prevention
- Add integrations with npx astro add instead of manual installs
- Keep the astro.config integrations list in sync with every client:only hint used in templates
- Restart the dev server after changing integrations
When it happens
Trigger: client:only="preact" while only @astrojs/react is in integrations; client:only="solid" without @astrojs/solid; the framework package was npm-installed but the Astro integration was never added to astro.config; integrations array assembled conditionally and the branch omitted the renderer.
Common situations: Copy-pasting components between projects with different integrations; manually installing framework deps instead of running astro add; config refactors that dropped an integration; monorepos sharing a config template.
Related errors
- NoClientOnlyHint
- Error: invalid hydration directive
- MissingMediaQueryDirective
- NoMatchingImport
- Unable to render ! This component likely uses , but Astro…
AI-assisted analysis of withastro/astro@52e6c34790 (2026-08-18).
Data as JSON: /api/errors/89c1b562313a7971.
Report an issue: GitHub.
Appendix: source
Thrown at packages/astro/src/runtime/server/render/component.ts:204
if (!renderer && metadata.hydrateArgs) {
const rendererName = metadata.hydrateArgs;
if (typeof rendererName === 'string') {
renderer = renderers.find(({ name }) => name === rendererName);
}
}
}
let componentServerRenderEndTime;
// If no one claimed the renderer
if (!renderer) {
if (metadata.hydrate === 'only') {
const rendererName = rendererAliases.has(metadata.hydrateArgs)
? rendererAliases.get(metadata.hydrateArgs)
: metadata.hydrateArgs;
if (clientOnlyValues.has(rendererName)) {
// throw an error if provide correct client:only directive but not find the renderer
const plural = validRenderers.length > 1;
throw new AstroError({
...AstroErrorData.NoMatchingRenderer,
message: AstroErrorData.NoMatchingRenderer.message(
metadata.displayName,
metadata?.componentUrl?.split('.').pop(),
plural,
validRenderers.length,
),
hint: AstroErrorData.NoMatchingRenderer.hint(
formatList(probableRendererNames.map((r) => '`' + r + '`')),
),
});
} else {
// throw an error if an invalid hydration directive was provided
throw new AstroError({
...AstroErrorData.NoClientOnlyHint,
message: AstroErrorData.NoClientOnlyHint.message(metadata.displayName),
hint: AstroErrorData.NoClientOnlyHint.hint(
probableRendererNames.map((r) => r.replace('@astrojs/', '')).join('|'),View on GitHub (pinned to 52e6c34790)