nodejs/node · error · Error
${providerFile} must end in .yml or .yaml
Error message
${providerFile} must end in .yml or .yaml What it means
Thrown by TrustCommand.flagsToOptions when `--file` exists but does not end in `.yml` or `.yaml`. Trusted-publishing claims reference a YAML pipeline definition, so a JSON, txt, or extensionless file is rejected. The check is a simple two-call endsWith OR.
Source
Thrown at deps/npm/lib/trust-cmd.js:280
entity = flags[entityKey]
entitySource = 'flag'
} else if (!invalidPkgJsonProviderType && git?.repository) {
entity = git.repository
entitySource = 'package.json'
}
const mismatchPkgJsonRepository = matchPkg && git && entity !== git.repository
const usedRepositoryInPkgJson = entitySource === 'package.json'
const warnings = []
if (!pkgName) {
throw new Error('Package name must be specified either as an argument or in package.json file')
}
if (!flags.file) {
throw new Error(`${providerFile} must be specified with the file option`)
}
if (!flags.file.endsWith('.yml') && !flags.file.endsWith('.yaml')) {
throw new Error(`${providerFile} must end in .yml or .yaml`)
}
this.validateFile?.(flags.file)
if (invalidPkgJsonProviderType) {
const message = this.warnString`Repository in package.json is not a ${providerEntity}`
if (!flags[entityKey]) {
throw new Error(message)
} else {
warnings.push(message)
}
} else {
if (mismatchPkgJsonRepository) {
warnings.push(this.warnString`Repository in package.json (${git.repository}) differs from provided ${providerEntity} (${entity})`)
}
}
if (!entity && matchPkg) {View on GitHub (pinned to 1b2de5e052)
Solutions
- Use a `.yml` or `.yaml` file: rename or convert your pipeline config.
- Check for typos and stray suffixes (e.g. .yml.bak, .yaml~).
- If your pipeline truly is JSON, wrap it in a YAML file that includes it via GitLab's `include` (the top-level claim still must be YAML).
Example fix
// before npm trust gitlab --file pipeline.json --project g/p --allow-publish // after npm trust gitlab --file .gitlab-ci.yml --project g/p --allow-publish
Defensive patterns
Strategy: validation
Validate before calling
if (!/\.(yml|yaml)$/.test(flags.file || '')) {
throw new Error(`--file must end in .yml or .yaml, got: ${flags.file}`)
} Type guard
const isYamlFile = (file) => typeof file === 'string' && /\.(yml|yaml)$/.test(file)
Try / catch
try {
await createConfigCommand(...)
} catch (err) {
if (/must end in .yml or .yaml/i.test(err.message)) {
// rename/convert the file to YAML, update flags.file, retry
} else { throw err }
} Prevention
- Author CI pipeline definitions in YAML from the start.
- Validate the file extension in your wrapper script.
- Watch for stray suffixes from editor backups (.bak, ~).
When it happens
Trigger: Passing `--file .gitlab-ci.json`, `--file Dockerfile`, `--file Makefile`, or a typo like `--file .gitlab-ci.yml.bak`. Fires immediately after the file-presence check, before provider-specific validateFile.
Common situations: Migrating from JSON-based config; wrong extension from a template generator; trailing characters from copy-paste.
Related errors
- ${this.constructor.providerEntity} must be specified in the
- GitLab CI/CD pipeline file must be just a file not a path
- Package name must be specified either as an argument or in t
- Package name must be specified either as an argument or in t
- ID of the trusted relationship to revoke must be specified w
AI-assisted analysis of nodejs/node@1b2de5e052 (2026-08-13).
Data as JSON: /api/errors/e020b771300d5e35.
Report an issue: GitHub.