hashicorp/terraform · critical

Unknown type: %s

Error message

Unknown type: %s

What it means

A panic in `ConfigFieldReader.readField` (internal/legacy/helper/schema/field_reader_config.go:141), default branch of the switch over `schema.Type`. The config-backed reader handles TypeBool/TypeInt/TypeFloat/TypeString/TypeList/TypeMap/TypeSet/typeObject; any other value panics with 'Unknown type: %s'. This is a malformed-schema / provider-bug condition specific to the config-source field reader.

Source

Thrown at internal/legacy/helper/schema/field_reader_config.go:141

		if schema.PromoteSingle {
			result, err := r.readPrimitive(k, schema.Elem.(*Schema))
			if err == nil && result.Exists {
				result.Value = []interface{}{result.Value}
				return result, nil
			}
		}

		return readListField(&nestedConfigFieldReader{r}, address, schema)
	case TypeMap:
		return r.readMap(k, schema)
	case TypeSet:
		return r.readSet(address, schema)
	case typeObject:
		return readObjectField(
			&nestedConfigFieldReader{r},
			address, schema.Elem.(map[string]*Schema))
	default:
		panic(fmt.Sprintf("Unknown type: %s", schema.Type))
	}
}

func (r *ConfigFieldReader) readMap(k string, schema *Schema) (FieldReadResult, error) {
	// We want both the raw value and the interpolated. We use the interpolated
	// to store actual values and we use the raw one to check for
	// computed keys. Actual values are obtained in the switch, depending on
	// the type of the raw value.
	mraw, ok := r.Config.GetRaw(k)
	if !ok {
		// check if this is from an interpolated field by seeing if it exists
		// in the config
		_, ok := r.Config.Get(k)
		if !ok {
			// this really doesn't exist
			return FieldReadResult{}, nil
		}

View on GitHub (pinned to c9def3e214)

Solutions

  1. Find the schema attribute whose Type is invalid and set it to a valid ValueType.
  2. Add a schema self-test in the provider that asserts every attribute has a known Type.
  3. Pin the provider SDK version consistent with the schema code.
  4. Report/fix in the provider repo with a minimal resource definition.

Example fix

null
Defensive patterns

Strategy: validation

Validate before calling

// Go (provider): validate all schema Types handled by the config reader
for name, s := range resource.Schema {
    switch s.Type {
    case schema.TypeString, schema.TypeBool, schema.TypeInt, schema.TypeFloat,
         schema.TypeList, schema.TypeMap, schema.TypeSet:
    default:
        return fmt.Errorf("config reader cannot handle schema %q Type %d", name, s.Type)
    }
}

Type guard

// Go: guard a schema Type is config-reader-compatible
func configReadableType(t schema.ValueType) bool {
    switch t {
    case schema.TypeString, schema.TypeBool, schema.TypeInt, schema.TypeFloat,
         schema.TypeList, schema.TypeMap, schema.TypeSet:
        return true
    }
    return false
}

Prevention

When it happens

Trigger: Reading a field from HCL config via the legacy ConfigFieldReader when the corresponding schema entry has a Type outside the recognized set (unset TypeInvalid, or a constant the reader does not know).

Common situations: Provider schema with an unset or invalid Type on an attribute; SDK version drift introducing/removing a ValueType; a schema entry that was supposed to be a collection but got a scalar constant or vice versa.

Related errors


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