cloudflare/cloudflared · error

expected int found %T for %s

Error message

expected int found %T for %s

What it means

Returned by configFileSettings.Int when a setting with the requested name exists in the parsed config file but its value is not a Go int. The error includes the actual dynamic type (%T) of the stored value, so it doubles as a type-mismatch diagnostic for YAML/TOML-parsed settings.

Source

Thrown at config/configuration.go:284

	TCPKeepAlive   *CustomDuration `yaml:"tcpKeepAlive" json:"tcpKeepAlive,omitempty"`
}

type configFileSettings struct {
	Configuration `yaml:",inline"`
	// older settings will be aggregated into the generic map, should be read via cli.Context
	Settings map[string]interface{} `yaml:",inline"`
}

func (c *Configuration) Source() string {
	return c.sourceFile
}

func (c *configFileSettings) Int(name string) (int, error) {
	if raw, ok := c.Settings[name]; ok {
		if v, ok := raw.(int); ok {
			return v, nil
		}
		return 0, fmt.Errorf("expected int found %T for %s", raw, name)
	}
	return 0, nil
}

func (c *configFileSettings) Duration(name string) (time.Duration, error) {
	if raw, ok := c.Settings[name]; ok {
		switch v := raw.(type) {
		case time.Duration:
			return v, nil
		case string:
			return time.ParseDuration(v)
		}
		return 0, fmt.Errorf("expected duration found %T for %s", raw, name)
	}
	return 0, nil
}

func (c *configFileSettings) Float64(name string) (float64, error) {

View on GitHub (pinned to 2253eeeb25)

Solutions

  1. Unquote the value in the config file so it parses as an int (retries: 5 not retries: "5").
  2. Check the %T in the message to see the actual type and convert the call to the matching getter (e.g. use String + strconv.Atoi, or Float64).
  3. If values come from a format that decodes ints as float64, normalize in a custom input source before calling Int.

Example fix

// before (config.yml)
retries: "5"
// after
retries: 5
Defensive patterns

Strategy: validation

Validate before calling

// Go
typeAssertInt := func(v interface{}) (int, bool) { i, ok := v.(int); return i, ok }

Type guard

func asInt(v interface{}) (int, bool) { i, ok := v.(int); return i, ok }

Try / catch

n, err := settings.Int("retries")
if err != nil {
    log.Printf("setting 'retries' must be an unquoted int: %v", err)
    return err
}

Prevention

When it happens

Trigger: Calling Int(name) on a config file setting whose underlying value is a string, bool, float64, etc. — e.g. `retries: "5"` (quoted number in YAML) read via Int.

Common situations: Quoted numbers in YAML config files; TOML/YAML parsers decoding integers as float64; users putting durations or strings where an int is expected.

Related errors


AI-assisted analysis of cloudflare/cloudflared@2253eeeb25 (2026-09-06). Data as JSON: /api/errors/9bc9dc999477ab7c. Report an issue: GitHub.