{"record":{"id":"46cbf1282c6cbda4","repo":"vuejs/vue-cli","slug":"invalid-package-name-packagename","errorCode":null,"errorMessage":"Invalid package name ${packageName}","messagePattern":"Invalid package name (.+?)","errorType":"validation","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/@vue/cli/lib/util/ProjectPackageManager.js","lineNumber":82,"sourceCode":"    upgrade: ['update', '--loglevel', 'error'],\n    remove: ['uninstall', '--loglevel', 'error']\n  },\n  pnpm: hasPnpmVersionOrLater('4.0.0') ? PACKAGE_MANAGER_PNPM4_CONFIG : PACKAGE_MANAGER_PNPM3_CONFIG,\n  yarn: {\n    install: [],\n    add: ['add'],\n    upgrade: ['upgrade'],\n    remove: ['remove']\n  }\n}\n\n// extract the package name 'xx' from the format 'xx@1.1'\nfunction stripVersion (packageName) {\n  const nameRegExp = /^(@?[^@]+)(@.*)?$/\n  const result = packageName.match(nameRegExp)\n\n  if (!result) {\n    throw new Error(`Invalid package name ${packageName}`)\n  }\n\n  return result[1]\n}\n\n// extract the package scope from the full package name\n// the result includes the initial @ character\nfunction extractPackageScope (packageName) {\n  const scopedNameRegExp = /^(@[^/]+)\\/.*$/\n  const result = packageName.match(scopedNameRegExp)\n\n  if (!result) {\n    return undefined\n  }\n\n  return result[1]\n}\n","sourceCodeStart":64,"sourceCodeEnd":100,"githubUrl":"https://github.com/vuejs/vue-cli/blob/7eb93c169c7520935252e2473387f923ef80d856/packages/@vue/cli/lib/util/ProjectPackageManager.js#L64-L100","documentation":"Thrown by stripVersion in ProjectPackageManager when a package name string does not match the expected pattern /^(@?[^@]+)(@.*)?$/. This pattern requires at least one non-@ character before any optional @version suffix. The function extracts the bare package name from formats like 'pkg@1.0.0' or '@scope/pkg@2.0'.","triggerScenarios":"Calling an internal package manager method (add, upgrade, remove) with a malformed package string — e.g., '@@1.0', an empty string, a string starting with '@' followed immediately by '@version', or a string that is only a version like '@1.0.0'.","commonSituations":"A plugin or script programmatically constructs a package specifier incorrectly. User passes a bare version string or double-scoped name to a package manager command. Usually an internal/programmatic error rather than a direct user typo.","solutions":["Ensure the package specifier is a valid npm package name optionally followed by @version (e.g., 'lodash', '@vue/cli-service@4.5.0').","If building the string dynamically, validate it against the regex /^(@?[^@]+)(@.*)?$/ before use.","Separate the package name and version into distinct arguments rather than concatenating if the API supports it."],"exampleFix":"// before\nconst spec = '@' + version  // e.g. '@1.0.0'\npm.add(spec)\n// after\nconst spec = `vue-cli-plugin-${name}@${version}`\npm.add(spec)","handlingStrategy":"validation","validationCode":"function isValidPackageName(spec) {\n  return /^(@?[^@]+)(@.*)?$/.test(spec);\n}\nif (!isValidPackageName(packageSpec)) {\n  throw new Error(`Invalid package name: ${packageSpec}`);\n}","typeGuard":"function isPackageName(spec) {\n  return typeof spec === 'string' && /^(@?[^@]+)(@.*)?$/.test(spec);\n}","tryCatchPattern":"try {\n  const name = stripVersion(spec);\n} catch (e) {\n  if (e.message.startsWith('Invalid package name')) {\n    console.error(`Package spec '${spec}' is malformed. Expected format: name or @scope/name or name@version.`);\n  }\n  throw e;\n}","preventionTips":["Validate package name specs against the npm naming rules before passing to package manager APIs.","Avoid constructing package strings by string concatenation of potentially-empty parts.","Separate name and version into distinct parameters when the API allows it."],"tags":["package-manager","validation","npm","package-name","programmer-error"],"backgroundTag":null,"analyzedSha":"7eb93c169c7520935252e2473387f923ef80d856","analyzedAt":"2026-08-13T10:13:37.803Z","schemaVersion":2},"datasetVersion":"2026-08-13T14:17:21.547Z"}