hashicorp/packer · error

failed to update HCP Packer Build status for %q: %s

Error message

failed to update HCP Packer Build status for %q: %s

What it means

startBuild marks the build as BUILDRUNNING in HCP Packer before any provisioning starts, so registry consumers see it in progress. If bucket.UpdateBuildStatus fails (API error, stale RunUUID, cancelled context), the build cannot be tracked and Packer aborts the build with this wrapped error.

Source

Thrown at internal/hcp/registry/types.bucket.go:679

		}

		log.Printf("[TRACE] stopped heartbeating build %s", build)
	}()
	return func() {
		close(heartbeatChan)
	}, nil
}

func (bucket *Bucket) startBuild(ctx context.Context, buildName string) error {
	if !bucket.IsExpectingBuildForComponent(buildName) {
		return &ErrBuildAlreadyDone{
			Message: "build is already done",
		}
	}

	err := bucket.UpdateBuildStatus(ctx, buildName, hcpPackerModels.HashicorpCloudPacker20230101BuildStatusBUILDRUNNING)
	if err != nil {
		return fmt.Errorf("failed to update HCP Packer Build status for %q: %s", buildName, err)
	}

	cleanupHeartbeat, err := bucket.HeartbeatBuild(ctx, buildName)
	if err != nil {
		log.Printf("[ERROR] failed to start heartbeat function")
	}

	buildDone := make(chan struct{}, 1)
	go func() {
		log.Printf("[TRACE] waiting for heartbeat completion")
		select {
		case <-ctx.Done():
			cleanupHeartbeat()
			err := bucket.UpdateBuildStatus(
				context.Background(),
				buildName,
				hcpPackerModels.HashicorpCloudPacker20230101BuildStatusBUILDCANCELLED)
			if err != nil {

View on GitHub (pinned to eb36e3c3e4)

Solutions

  1. Ensure only one Packer run targets the same bucket/fingerprint at a time; use distinct fingerprints for parallel runs
  2. Re-authenticate / refresh HCP credentials and retry the build
  3. Check the inner error for HTTP status; if 5xx, retry after confirming HCP Packer service health
  4. If a ctx cancellation caused it, re-run the build without immediately cancelling
Defensive patterns

Strategy: try-catch

Validate before calling

// Serialize runs that share a bucket/fingerprint before starting Packer
// if !flock("/tmp/packer-<bucket>-<fingerprint>.lock") { exit "another run is active" }
// test -n "$HCP_CLIENT_ID" && test -n "$HCP_CLIENT_SECRET" || exit 1

Try / catch

// Go
if err := bucket.StartBuild(ctx, buildName); err != nil {
	if strings.Contains(err.Error(), "failed to update HCP Packer Build status") {
		// status update failed: check RunUUID ownership, credentials, and service health,
		// then retry once with a fresh context
		return retryWithFreshCtx(ctx, bucket.StartBuild, buildName)
	}
	return err
}

Prevention

When it happens

Trigger: Bucket.StartBuild -> startBuild calls UpdateBuildStatus(ctx, buildName, BUILDRUNNING) and the underlying UpdateBuild API call fails — network errors, invalid/expired RunUUID mismatch (another Packer run owns the build), 4xx/5xx responses, or the passed ctx is already cancelled.

Common situations: Two concurrent Packer runs using the same bucket+fingerprint (second run's RunUUID rejected); expired HCP credentials mid-run; HCP Packer service incident; cancelled context from Ctrl-C or CI timeout right at build start.

Related errors


AI-assisted analysis of hashicorp/packer@eb36e3c3e4 (2026-09-05). Data as JSON: /api/errors/395b948eaa15bdd7. Report an issue: GitHub.