hashicorp/terraform · critical

attempted to encode a malformed backend state file; it…

Error message

attempted to encode a malformed backend state file; it contains state for both a 'backend' and a 'state_store' block. This is a bug in Terraform and should be reported.

What it means

EncodeBackendStateFile hit the case where the in-memory BackendStateFile has BOTH a non-nil Backend and a non-nil StateStore — an impossible state for any correctly-running Terraform. The message explicitly says 'This is a bug in Terraform and should be reported,' i.e. it is an internal invariant guard, not a user-config error.

Solutions

  1. File a bug report against Terraform/OpenTofu with the steps to reproduce and the version.
  2. Work around by clearing one of the two (delete .terraform/terraform.tfstate and re-init) to get back to a known-good state.
  3. If running a fork/experimental build, audit the code that populates BackendStateFile to ensure it never sets both fields.

Example fix

// code-level fix: enforce mutual exclusion at the source
if f.Backend != nil && f.StateStore != nil {
    f.Backend = nil // or f.StateStore = nil, depending on intended mode
}
return json.Marshal(f)
Defensive patterns

Strategy: validation

Validate before calling

// encode-time invariant: enforce mutual exclusion before writing
if f.Backend != nil && f.StateStore != nil {
    return nil, errors.New("refusing to encode: both backend and state_store set (internal bug)")
}

Type guard

func backendStateIsConsistent(f *BackendStateFile) bool {
    return !(f.Backend != nil && f.StateStore != nil)
}

Prevention

When it happens

Trigger: Code path that mutates BackendStateFile in memory sets both Backend and StateStore before calling EncodeBackendStateFile. Cannot be produced by config alone — requires a bug in init/plan/apply wiring.

Common situations: Almost never seen in released builds; surfaces during development of new backend/state-store code, with experimental/fork builds, or after a partial refactor.

Understand the failure class

Related errors


AI-assisted analysis of hashicorp/terraform@d32a084675 (2026-08-11). Data as JSON: /api/errors/15303400eff2fbca. Report an issue: GitHub.

Appendix: source

Thrown at internal/command/workdir/backend_state.go:128

	if stateFile.Backend != nil && stateFile.StateStore != nil {
		return nil, fmt.Errorf("encountered a malformed backend state file that contains state for both a 'backend' and a 'state_store' block")
	}
	if stateFile.StateStore != nil && stateFile.StateStore.ProviderSupplyMode == "" {
		// Check for this, as lacking this data can cause problems later when an empty provider version
		// is encountered. This error will make debugging much easier.
		return nil, fmt.Errorf("encountered a malformed backend state file with a 'state_store' block that is missing the required 'provider_supply_mode' property")
	}

	return &stateFile, nil
}

func EncodeBackendStateFile(f *BackendStateFile) ([]byte, error) {
	f.Version = 3 // we only support version 3
	f.TFVersion = version.SemVer.String()

	switch {
	case f.Backend != nil && f.StateStore != nil:
		return nil, fmt.Errorf("attempted to encode a malformed backend state file; it contains state for both a 'backend' and a 'state_store' block. This is a bug in Terraform and should be reported.")
	case f.Backend == nil && f.StateStore == nil:
		// This is valid - if the user has a backend state file and an implied local backend in use
		// the backend state file exists but has no Backend data.
	case f.Backend != nil:
		// Not implementing anything here - risk of breaking changes
	case f.StateStore != nil:
		err := f.StateStore.Validate()
		if err != nil {
			return nil, err
		}
	default:
		panic("error when determining whether backend state file was valid. This is a bug in Terraform and should be reported.")
	}

	return json.MarshalIndent(f, "", "  ")
}

func (f *BackendStateFile) DeepCopy() *BackendStateFile {

View on GitHub (pinned to d32a084675)