hashicorp/terraform · error

invalid md5

Error message

invalid md5

What it means

An Attribute must declare at least one of Optional, Required, or Computed — otherwise Terraform cannot decide whether the value comes from config, the provider, or both. The validator treats an attribute with all three false as ill-defined.

Solutions

  1. Mark the attribute Optional if the user may set it (optionally overridden by the provider).
  2. Mark it Required if the user must set it.
  3. Mark it Computed if only the provider supplies it (typically also Optional to allow overrides).

Example fix

// before
"name": { Type: cty.String },
// after
"name": { Type: cty.String, Optional: true, Computed: true },
Defensive patterns

Strategy: validation

Validate before calling

// Require at least one of Optional, Required, Computed.
func hasBehaviorFlag(a *configschema.Attribute) bool {
    return a != nil && (a.Optional || a.Required || a.Computed)
}

Type guard

func hasAtLeastOneBehavior(optional, required, computed bool) bool {
    return optional || required || computed
}

Prevention

When it happens

Trigger: An Attribute literal that sets Type but omits Optional/Required/Computed. Guard at internal_validate.go:146 is `!a.Optional && !a.Required && !a.Computed`.

Common situations: Forgetting the behavior flags when focusing on the type; schema codegen that emits the type only; copy-paste that drops the flags.

Related errors


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

Appendix: source

Thrown at internal/backend/remote-state/oss/client.go:247

	log.Printf("[DEBUG] Retrieving state serial in tablestore: %#v", getParams)

	object, err := c.otsClient.GetRow(&tablestore.GetRowRequest{
		SingleRowQueryCriteria: getParams,
	})

	if err != nil {
		return nil, err
	}

	var val string
	if v, ok := object.GetColumnMap().Columns["Digest"]; ok && len(v) > 0 {
		val = v[0].Value.(string)
	}

	sum, err := hex.DecodeString(val)
	if err != nil || len(sum) != md5.Size {
		return nil, errors.New("invalid md5")
	}

	return sum, nil
}

// store the hash of the state to that clients can check for stale state files.
func (c *RemoteClient) putMD5(sum []byte) error {
	if c.otsTable == "" {
		return nil
	}

	if len(sum) != md5.Size {
		return errors.New("invalid payload md5")
	}

	putParams := &tablestore.PutRowChange{
		TableName: c.otsTable,
		PrimaryKey: &tablestore.PrimaryKey{

View on GitHub (pinned to d32a084675)