pulumi/pulumi · error

npm pack: %w

Error message

npm pack: %w

What it means

This wraps a failure of the `npm pack <pkgdir> --pack-destination <dest>` command run by the language host when packing a NodeJS SDK. npm pack returns non-zero when the tarball cannot be produced (invalid package.json, lifecycle script failure, bad destination). The host then fails the Pack RPC with this error.

Source

Thrown at sdk/nodejs/cmd/pulumi-language-nodejs/main.go:2099

		if err != nil {
			return nil, fmt.Errorf("copy package.json: %w", err)
		}
	}

	err = writeString("$ npm pack\n")
	if err != nil {
		return nil, fmt.Errorf("write to output: %w", err)
	}
	var stdoutBuffer bytes.Buffer
	npmPackCmd := exec.Command(npm,
		"pack",
		filepath.Join(req.PackageDirectory, "bin"),
		"--pack-destination", req.DestinationDirectory)
	npmPackCmd.Stdout = &stdoutBuffer
	npmPackCmd.Stderr = struct{ io.Writer }{os.Stderr}
	err = npmPackCmd.Run()
	if err != nil {
		return nil, fmt.Errorf("npm pack: %w", err)
	}

	artifactName := strings.TrimSpace(stdoutBuffer.String())

	return &pulumirpc.PackResponse{
		ArtifactPath: filepath.Join(req.DestinationDirectory, artifactName),
	}, nil
}

// Nodejs sometimes sets stdout/stderr to non-blocking mode. When a nodejs subprocess is directly
// handed the go process's stdout/stderr file descriptors, nodejs's non-blocking configuration goes
// unnoticed by go, and a write from go can result in an error `write /dev/stdout: resource
// temporarily unavailable`.
//
// The solution to this is to not provide nodejs with the go process's stdout/stderr file
// descriptors, and instead proxy the writes through something else.
// In https://github.com/pulumi/pulumi/pull/16504 we used Cmd.StdoutPipe/StderrPipe for this.
// However this introduced a potential bug, as it is not safe to use these specific pipes along

View on GitHub (pinned to 793f7b2e16)

Solutions

  1. Run `npm pack bin/ --pack-destination <dir>` manually in the package directory to see the real npm error.
  2. Validate bin/package.json has valid name, version, and main/files entries.
  3. Fix failing lifecycle scripts (prepack/prepare) or run them directly to see their failure.
  4. Ensure DestinationDirectory exists and is writable; create it before packing.
  5. Update npm/Node to supported versions and clear a corrupted npm cache (`npm cache verify`).

Example fix

// before: destination never created
os.MkdirTemp("", "pulumipack")
// after: ensure destination exists before Pack
os.MkdirAll(destDir, 0o755)
Defensive patterns

Strategy: validation

Validate before calling

const pkg = JSON.parse(fs.readFileSync('bin/package.json', 'utf8'));
if (!pkg.name || !pkg.version) throw new Error('bin/package.json needs name and version before npm pack');
if (!fs.existsSync(destDir)) fs.mkdirSync(destDir, { recursive: true });

Try / catch

try { await pack(); } catch (err) { if (/npm pack/.test(String(err))) { console.error('Run `npm pack bin/` manually for the underlying npm error'); } throw err; }

Prevention

When it happens

Trigger: Running Pack on a NodeJS package where `npm pack bin/ --pack-destination <dir>` exits non-zero: malformed or incomplete bin/package.json, npm lifecycle scripts (prepack/prepare) failing, missing files field collisions, unwritable DestinationDirectory, or npm not on PATH/npm registry issues triggering scripts.

Common situations: package.json missing required fields (name/version) in bin/; prepack script error; destination directory doesn't exist or is read-only; npm cache permission problems in CI; Node/npm version mismatch breaking the build scripts invoked by pack.

Related errors


AI-assisted analysis of pulumi/pulumi@793f7b2e16 (2026-08-31). Data as JSON: /api/errors/64b471cc0e145e9f. Report an issue: GitHub.