quasarframework/quasar · error · Error
Project directory must be a non-empty path
Error message
Project directory must be a non-empty path
What it means
getBuildArtifactsCleanTarget requires a non-empty projectDir string to anchor path resolution and containment checks. It throws 'Project directory must be a non-empty path' when projectDir is missing, not a string, or blank, since safety checks (home/project containment) cannot be computed without it.
Source
Thrown at app-vite/lib/utils/remove-build-artifacts.js:62
return resolve(realAncestor, relative(existingAncestor, target))
}
function isFilesystemRoot(target) {
return target === parse(target).root
}
export function getBuildArtifactsCleanTarget({
targetDir,
projectDir,
allowOutsideProject
}) {
if (typeof targetDir !== 'string' || targetDir.trim() === '') {
throw new Error('Build output directory must be a non-empty path')
}
if (typeof projectDir !== 'string' || projectDir.trim() === '') {
throw new Error('Project directory must be a non-empty path')
}
const project = resolve(projectDir)
const effectiveProject = fse.realpathSync(project)
const home = fse.realpathSync(resolve(homedir()))
const target = resolve(projectDir, targetDir)
const effectiveTarget = getEffectivePath(target)
if (isFilesystemRoot(target) || isFilesystemRoot(effectiveTarget)) {
throw new Error('Refusing to remove a filesystem root as build output')
}
if (target === home || effectiveTarget === home) {
throw new Error(
'Refusing to remove the user home directory as build output'
)
}
View on GitHub (pinned to 4841521b5f)
Solutions
- Pass an explicit absolute projectDir (e.g. path.resolve(__dirname)) instead of relying on cwd
- Restore or cd into an existing working directory before running the command
- Verify the option key (projectDir) is forwarded correctly through your wrapper/script
Example fix
// before
await removeBuildArtifacts({ targetDir: 'dist', projectDir: '' })
// after
await removeBuildArtifacts({ targetDir: 'dist', projectDir: '/home/me/my-app' }) Defensive patterns
Strategy: validation
Validate before calling
const path = require('node:path')
function assertNonEmptyString(v, name) {
if (typeof v !== 'string' || v.trim() === '') throw new TypeError(`${name} must be a non-empty string`)
}
assertNonEmptyString(opts.projectDir, 'projectDir')
// better: pass an explicit absolute path
const projectDir = path.resolve(opts.projectDir || process.cwd()) Type guard
function isNonEmptyString(v) {
return typeof v === 'string' && v.trim() !== ''
} Try / catch
try {
await removeBuildArtifacts(opts)
} catch (err) {
if (err.message === 'Project directory must be a non-empty path') {
// fall back to process.cwd() or abort with a clear message
} else throw err
} Prevention
- Pass explicit absolute projectDir values; never rely on cwd in scripts/CI
- Forward option names exactly (projectDir) through wrappers
- Guard against deleted working directories in long-lived processes
When it happens
Trigger: Invoking the clean-artifacts API without projectDir, or with '' / whitespace / a non-string — e.g. when process.cwd() resolution failed or the option was never forwarded from the build pipeline.
Common situations: Running the cleaner outside a normal build context (scripts, CI) where cwd assumptions break; a refactor renamed the option; empty environment (deleted cwd directory, so cwd resolution yields '').
Related errors
- Build output directory must be a non-empty path
- Build output directory must remain inside the project. Set b
- Could not resolve an existing ancestor for "${target}"
- Refusing to remove the project root as build output
- Invalid SSR nonce. Expected a non-empty base64 or base64url
AI-assisted analysis of quasarframework/quasar@4841521b5f (2026-08-30).
Data as JSON: /api/errors/05a3c8742e18f361.
Report an issue: GitHub.