{"record":{"id":"f17ee678742181c6","repo":"apache/answer","slug":"failed-to-install-plugin-dependencies-w","errorCode":null,"errorMessage":"failed to install plugin dependencies: %w","messagePattern":"failed to install plugin dependencies: %w","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/cli/build.go","lineNumber":368,"sourceCode":"\tif err != nil {\n\t\treturn fmt.Errorf(\"failed to read plugins dir: %w\", err)\n\t}\n\tfor _, entry := range pluginsDirEntries {\n\t\tif !entry.IsDir() {\n\t\t\tcontinue\n\t\t}\n\t\tsourcePluginDir := filepath.Join(pluginsDir, entry.Name())\n\t\t// check if plugin is a ui plugin\n\t\tpackageJsonPath := filepath.Join(sourcePluginDir, \"package.json\")\n\t\tfmt.Printf(\"check if %s is a ui plugin\\n\", packageJsonPath)\n\t\tif !dir.CheckFileExist(packageJsonPath) {\n\t\t\tcontinue\n\t\t}\n\n\t\tpnpmInstallCmd := b.newExecCmd(\"pnpm\", \"install\")\n\t\tpnpmInstallCmd.Dir = sourcePluginDir\n\t\tif err = pnpmInstallCmd.Run(); err != nil {\n\t\t\treturn fmt.Errorf(\"failed to install plugin dependencies: %w\", err)\n\t\t}\n\n\t\tlocalPluginDir := filepath.Join(localUIPluginDir, entry.Name())\n\t\tfmt.Printf(\"try to copy dir from %s to %s\\n\", sourcePluginDir, localPluginDir)\n\t\tif err = copyDirEntries(os.DirFS(sourcePluginDir), \".\", localPluginDir, \"node_modules\"); err != nil {\n\t\t\treturn fmt.Errorf(\"failed to copy ui files: %w\", err)\n\t\t}\n\t}\n\tformatUIPluginsDirName(localUIPluginDir)\n\treturn nil\n}\n\n// buildUI run pnpm install and pnpm build commands to build ui\nfunc buildUI(b *buildingMaterial) (err error) {\n\tlocalUIBuildDir := filepath.Join(b.tmpDir, \"vendor/github.com/apache/answer/ui\")\n\n\tpnpmInstallCmd := b.newExecCmd(\"pnpm\", \"pre-install\")\n\tpnpmInstallCmd.Dir = localUIBuildDir","sourceCodeStart":350,"sourceCodeEnd":386,"githubUrl":"https://github.com/apache/answer/blob/3b9f1370612e690a0b7f230f05e688930db4c6d3/internal/cli/build.go#L350-L386","documentation":"For each vendored plugin that has a package.json (i.e. a UI plugin), copyUIFiles runs `pnpm install` inside the plugin's source directory to install its frontend dependencies. This error wraps the exec.ExitError from a failing pnpm install — the plugin's JS dependencies could not be installed.","triggerScenarios":"b.newExecCmd(\"pnpm\", \"install\").Run() with Dir=sourcePluginDir returns an error: pnpm binary not on PATH, the plugin's package.json/pnpm-lock.yaml is broken or references unpublished versions/registry packages, network failure reaching the npm registry, or pnpm exits non-zero (peer conflicts, unsupported Node version).","commonSituations":"Custom third-party plugin with an outdated lockfile or dependencies that no longer resolve; corporate proxy/firewall blocking registry.npmjs.org; pnpm not installed (answer build requires it) or wrong Node/pnpm version; plugin's package.json pinned to a removed package version.","solutions":["Ensure pnpm is installed and on PATH (`pnpm -v`); install the version the answer build expects (e.g. `npm i -g pnpm` or corepack).","Reproduce manually: `cd <plugin-dir> && pnpm install` and read the pnpm output to see the real failure (registry 404, peer conflict, Node version).","Fix the plugin's package.json/pnpm-lock.yaml: update deps or run `pnpm install --no-frozen-lockfile`; for private/old packages check registry access.","Check network/proxy config for pnpm (npm registry mirror, HTTPS_PROXY) and Node version compatibility, then rebuild."],"exampleFix":"// before: pnpm failure surfaced with no context\npnpmInstallCmd := b.newExecCmd(\"pnpm\", \"install\")\npnpmInstallCmd.Dir = sourcePluginDir\nif err = pnpmInstallCmd.Run(); err != nil {\n\treturn fmt.Errorf(\"failed to install plugin dependencies: %w\", err)\n}\n// after: verify pnpm availability and capture output\nif _, err := exec.LookPath(\"pnpm\"); err != nil {\n\treturn fmt.Errorf(\"pnpm is required to build UI plugins: %w\", err)\n}\npnpmInstallCmd := b.newExecCmd(\"pnpm\", \"install\")\npnpmInstallCmd.Dir = sourcePluginDir\npnpmInstallCmd.Stdout = os.Stdout\npnpmInstallCmd.Stderr = os.Stderr\nif err = pnpmInstallCmd.Run(); err != nil {\n\treturn fmt.Errorf(\"failed to install plugin dependencies in %s: %w\", sourcePluginDir, err)\n}","handlingStrategy":"try-catch","validationCode":"if _, err := exec.LookPath(\"pnpm\"); err != nil {\n\treturn fmt.Errorf(\"pnpm not found in PATH; install it (npm i -g pnpm or corepack enable)\")\n}\npkgJson := filepath.Join(sourcePluginDir, \"package.json\")\nif _, err := os.Stat(pkgJson); err != nil {\n\treturn fmt.Errorf(\"plugin %s has no package.json\", sourcePluginDir)\n}\n// optional connectivity check\nif err := probeRegistry(\"https://registry.npmjs.org\"); err != nil {\n\treturn fmt.Errorf(\"npm registry unreachable; check proxy/network: %w\", err)\n}","typeGuard":"func pnpmAvailable() bool {\n\tp, err := exec.LookPath(\"pnpm\")\n\treturn err == nil && p != \"\"\n}\nfunc isUIPlugin(pluginDir string) bool {\n\tfi, err := os.Stat(filepath.Join(pluginDir, \"package.json\"))\n\treturn err == nil && !fi.IsDir()\n}","tryCatchPattern":"var exitErr *exec.ExitError\nif err := pnpmInstallCmd.Run(); err != nil {\n\tif errors.As(err, &exitErr) {\n\t\treturn fmt.Errorf(\"pnpm install failed in %s (exit %d); run 'cd %s && pnpm install' for details: %w\",\n\t\t\tsourcePluginDir, exitErr.ExitCode(), sourcePluginDir, err)\n\t}\n\treturn fmt.Errorf(\"failed to start pnpm (is it installed?): %w\", err)\n}","preventionTips":["Install pnpm and a compatible Node version before running `answer build` (check .nvmrc / packageManager field).","Pin plugin dependencies and commit pnpm-lock.yaml so installs are reproducible.","Configure npm registry mirrors / HTTPS_PROXY for corporate or restricted networks.","Test third-party plugins with a standalone `pnpm install` in the plugin dir before adding them to the build.","Avoid pinning deps to versions that may be unpublished/removed from the registry."],"tags":["pnpm","nodejs","dependencies","build","plugins"],"backgroundTag":"pnpm-install-failed","analyzedSha":"3b9f1370612e690a0b7f230f05e688930db4c6d3","analyzedAt":"2026-09-05T18:18:39.533Z","contentChangedAt":"2026-09-05T18:18:39.533Z","schemaVersion":2},"datasetVersion":"2026-09-12T22:17:10.623Z"}