hashicorp/packer · error
Error opening powershell script: %s
Error message
Error opening powershell script: %s
What it means
After successfully stating the script, Provision opens it locally with os.Open to read its contents for upload. An open failure (permissions, file locked, deleted between Stat and Open) produces "Error opening powershell script: %s" and aborts provisioning.
Source
Thrown at provisioner/powershell/provisioner.go:375
}
// every provisioner run will only have one env var script file so lets add it first
uploadedScripts := []string{p.config.RemoteEnvVarPath}
for _, path := range scripts {
ui.Say(fmt.Sprintf("Provisioning with powershell script: %s", path))
log.Printf("Opening %s for reading", path)
fi, err := os.Stat(path)
if err != nil {
return fmt.Errorf("Error stating powershell script: %s", err)
}
if os.IsPathSeparator(p.config.RemotePath[len(p.config.RemotePath)-1]) {
// path is a directory
p.config.RemotePath += filepath.Base(fi.Name())
}
f, err := os.Open(path)
if err != nil {
return fmt.Errorf("Error opening powershell script: %s", err)
}
defer f.Close()
command, err := p.createCommandText()
if err != nil {
return fmt.Errorf("Error processing command: %s", err)
}
// Upload the file and run the command. Do this in the context of a
// single retryable function so that we don't end up with the case
// that the upload succeeded, a restart is initiated, and then the
// command is executed but the file doesn't exist any longer.
var cmd *packersdk.RemoteCmd
err = retry.Config{StartTimeout: p.config.StartRetryTimeout}.Run(ctx, func(ctx context.Context) error {
if _, err := f.Seek(0, 0); err != nil {
return err
}
if err := comm.Upload(p.config.RemotePath, f, &fi); err != nil {View on GitHub (pinned to eb36e3c3e4)
Solutions
- Grant the packer process read permission on the script (chmod/chmod +r or icacls).
- Close programs or exclude the script from AV locking, then retry.
- Copy the script to a local path with normal permissions instead of reading from a network share.
- Run packer as a user with access to the scripts directory.
Example fix
// shell // before: -rw------- bootstrap.ps1 (packer runs as different user) // after chmod 644 scripts/bootstrap.ps1
Defensive patterns
Strategy: validation
Validate before calling
// Go, before Provision: verify readability
for _, p := range cfg.Scripts {
f, err := os.Open(p)
if err != nil {
return fmt.Errorf("cannot read script %q: %w", p, err)
}
f.Close()
} Try / catch
// Go
err := prov.Provision(ctx, ui, comm, genData)
if err != nil {
if errors.Is(err, os.ErrPermission) || strings.Contains(err.Error(), "Error opening powershell script") {
// fix permissions or re-run as a user with read access
}
return err
} Prevention
- chmod scripts to be readable by the packer process user (0644 is typical).
- Run CI packer jobs with a service account granted access to the scripts directory.
- Copy scripts from network shares to a local writable dir before building.
- Beware editors/AV holding write-locks on .ps1 files during builds.
When it happens
Trigger: Provision called with a stat-able script path whose os.Open fails — most commonly a permission denied or the file being locked by another process.
Common situations: File readable only by another user; running packer as a restricted service account; on Windows the .ps1 is locked by an editor or AV scanner; NFS/network share permission issues.
Understand the failure class
Background: Permission denied / not authorized / 403 Forbidden: access-control rejections when the caller lacks the required role, grant, or ownership — this error's family across 18 libraries.
Related errors
- Error stating powershell script: %s
- Error processing command: %s
- Only one of script or scripts can be specified.
- Must supply an 'elevated_user' if 'elevated_password' provid
- Either a script file or inline script must be specified.
AI-assisted analysis of hashicorp/packer@eb36e3c3e4 (2026-09-05).
Data as JSON: /api/errors/c63a1a0493dd8248.
Report an issue: GitHub.