hashicorp/terraform · error

failed to decode action %s: %w

Error message

failed to decode action %s: %w

What it means

Returned by jsonplan.MarshalActionInvocations when MarshalActionInvocation fails for a single action (action_invocations.go:106-109). The %s is the action address and %w wraps the underlying decode error from action.Decode(&schema). The error aborts marshalling of all action invocations and propagates to the caller producing the JSON plan.

Source

Thrown at internal/command/jsonplan/action_invocations.go:108

		}

		if latA.ActionsListIndex < latB.ActionsListIndex {
			return -1

		} else if latA.ActionsListIndex > latB.ActionsListIndex {
			return 1
		}
	}

	return 0
}

func MarshalActionInvocations(actions []*plans.ActionInvocationInstanceSrc, schemas *terraform.Schemas) ([]ActionInvocation, error) {
	ret := make([]ActionInvocation, 0, len(actions))
	for _, action := range actions {
		ai, err := MarshalActionInvocation(action, schemas)
		if err != nil {
			return ret, fmt.Errorf("failed to decode action %s: %w", action.Addr, err)
		}
		ret = append(ret, ai)
	}
	return ret, nil
}

func MarshalActionInvocation(action *plans.ActionInvocationInstanceSrc, schemas *terraform.Schemas) (ActionInvocation, error) {
	ai := ActionInvocation{
		Address:      action.Addr.String(),
		Type:         action.Addr.Action.Action.Type,
		Name:         action.Addr.Action.Action.Name,
		ProviderName: action.ProviderAddr.Provider.String(),
	}
	schema := schemas.ActionTypeConfig(
		action.ProviderAddr.Provider,
		action.Addr.Action.Action.Type,
	)
	if schema.ConfigSchema == nil {

View on GitHub (pinned to c9def3e214)

Solutions

  1. Inspect the wrapped error (%w) to find the specific decode failure and address it (e.g. ephemeral config values are unsupported — remove them).
  2. Re-run the plan with a provider version whose action schema matches the rendering terraform build.
  3. Ensure the same provider versions are locked (terraform init / lock file) when planning and when running show -json.
  4. If the action type is unsupported, remove the action from the configuration or upgrade the provider.
Defensive patterns

Strategy: try-catch

Validate before calling

// Ensure the action type has a schema and the config has no unsupported marks.
if schemas.ActionTypeConfig(provider, actionType).ConfigSchema == nil {
    return fmt.Errorf("no schema for action %s; run terraform init", actionType)
}

Try / catch

// Skip / report a single bad action without failing the whole marshal.
out := []ActionInvocation{}
for _, a := range actions {
    ai, err := MarshalActionInvocation(a, schemas)
    if err != nil { log.Printf("skipping action %s: %v", a.Addr, err); continue }
    out = append(out, ai)
}

Prevention

When it happens

Trigger: Producing JSON plan output (`terraform show -json`) for a plan that contains action invocations whose encoded config cannot be decoded against the action's schema: type mismatches, values failing schema validation, ephemeral marks, or unsupported value marks (see the inner MarshalActionInvocation error branches).

Common situations: Provider action schemas changed between plan creation and rendering; corrupted action invocation bytes in the plan; action config carrying marks Terraform can't serialize (ephemeral, custom marks); version skew between the provider that planned the action and the one loaded at show time.

Understand the failure class

Related errors


AI-assisted analysis of hashicorp/terraform@c9def3e214 (2026-08-07). Data as JSON: /api/errors/38f8f098a5fab6f5. Report an issue: GitHub.