quasarframework/quasar · warning
Failed to render template "${sourcePath}". This may break th
Error message
Failed to render template "${sourcePath}". This may break the App Extension... What it means
During App Extension installation, renderFile copies template files and renders placeholders like <%= ... %> via Lodash-style templates. If template compilation/rendering throws, the content equals the sentinel templateRenderError and only this warning is emitted; the file is skipped (not written to the target). The extension's prompts/inject may then be incomplete and break at runtime.
Source
Thrown at app-vite/lib/app-extension/AppExtensionInstance.js:68
if (overwritePrompt && fse.existsSync(targetPath)) {
const action = await promptOverwrite({
targetPath,
options: ['overwrite', 'skip'],
ctx
})
if (action === 'skip') return
}
if (rawCopy || isBinaryFile(sourcePath)) {
fse.ensureFileSync(targetPath)
fse.copyFileSync(sourcePath, targetPath)
} else {
const rawContent = fse.readFileSync(sourcePath, 'utf8')
const content = renderTemplate(rawContent, scope, renderTemplateCompileOpts)
if (content === templateRenderError) {
logger.warn(
`Failed to render template "${sourcePath}". This may break the App Extension...`
)
} else {
fse.ensureFileSync(targetPath)
fse.writeFileSync(targetPath, content, 'utf8')
}
}
}
async function renderFolders({ source, rawCopy, scope }, ctx, logger) {
let overwrite
const { globSync } = await import('tinyglobby')
const files = globSync(['**/*'], { cwd: source })
for (const rawPath of files) {
const targetRelativePath = rawPath
.split('/')
.map(name => {View on GitHub (pinned to 4841521b5f)
Solutions
- Open the logged sourcePath and fix the template syntax around the failing expression
- Report/patch the App Extension (update it to a version with the template fixed)
- As a workaround, copy the file manually into the target path with placeholders pre-resolved
- Re-run the extension install after fixing to regenerate the skipped file
Example fix
// before (template file, unbalanced tag) const x = <%= data.x % // after const x = <%= data.x %>
Defensive patterns
Strategy: validation
Validate before calling
// sanity-check extension templates before shipping/publishing
const fs = require('fs')
for (const f of templateFiles) {
const src = fs.readFileSync(f, 'utf8')
const opens = (src.match(/<%=/g) || []).length
const closes = (src.match(/%>/g) || []).length
if (opens !== closes) throw new Error(`Unbalanced EJS tags in ${f}`)
} Prevention
- Escape literal ${ and template-like syntax in template files
- Test `quasar ext add` of your extension in a scratch app before publishing
- Include template files in the npm package and keep them free of renderer-unsupported syntax
- After install, diff generated files against templates to catch silently skipped renders
When it happens
Trigger: A template file in the extension's /template folder contains syntax that fails renderTemplate compilation (e.g. unbalanced <%= %>, ES template literal syntax unsupported by the compile options) during ext install or runInstallScript's renderFolders.
Common situations: Third-party App Extension shipped with a broken template; template containing code with `${...}` or special characters clashing with the template engine; extension written for an older Quasar template renderer.
Related errors
- extendPackageJson() - cannot locate ${extPkg}. Skipping...
- extendPackageJson() - "${extPkg}" is a folder instead of fil
- extendPackageJson() - "${extPkg}" is malformed. Exiting...
- Quasar App Extension is not installed...
- Quasar App Extension is missing...
AI-assisted analysis of quasarframework/quasar@4841521b5f (2026-08-30).
Data as JSON: /api/errors/545b1c0b1779f84e.
Report an issue: GitHub.