crowdsecurity/crowdsec · error

document %d: %w

Error message

document %d: %w

What it means

NewPluginConfigList decodes a yaml stream document-by-document with a yaml.Decoder; any Decode error other than io.EOF is wrapped as "document %d: %w" with the 0-based document index. It pinpoints which yaml document inside a (possibly multi-document) notification config file is malformed.

Source

Thrown at pkg/csplugin/broker.go:456

	parsedConfigs := make(PluginConfigList, 0)

	dec := yaml.NewDecoder(fin)
	dec.SetStrict(true)

	idx := -1

	for {
		var pc PluginConfig

		idx += 1

		err := dec.Decode(&pc)
		if err != nil {
			if errors.Is(err, io.EOF) {
				break
			}

			return nil, fmt.Errorf("document %d: %w", idx, err)
		}

		// if the yaml document is empty, skip
		if reflect.DeepEqual(pc, PluginConfig{}) {
			continue
		}

		parsedConfigs = append(parsedConfigs, pc)
	}

	return parsedConfigs, nil
}

func getUUID() (string, error) {
	uuidv4, err := uuid.NewRandom()
	if err != nil {
		return "", err
	}

View on GitHub (pinned to 909b515798)

Solutions

  1. Open the reported file and inspect the Nth document after the Nth '---' separator (index is 0-based).
  2. Fix yaml syntax there: no tabs, correct types (timeout as duration like 10s, lists as - items).
  3. Validate the whole file with yamllint or python -c 'import yaml,sys; list(yaml.safe_load_all(open(sys.argv[1])))' file.yaml.
  4. Remove empty/garbage trailing documents; empty PluginConfig docs are skipped but broken ones are not.

Example fix

// before: document 1 has bad type
timeout: soon
// after
timeout: 30s
Defensive patterns

Strategy: validation

Validate before calling

// pre-validate multi-doc yaml
import "gopkg.in/yaml.v3"
dec := yaml.NewDecoder(fin)
for i := 0; ; i++ {
    var pc PluginConfig
    if err := dec.Decode(&pc); err != nil { break }
}

Try / catch

configs, err := NewPluginConfigList(fin)
if err != nil {
    var docErr string
    if _, scan := fmt.Sscanf(err.Error(), "document %d", new(int)); scan == nil {
        docErr = "check the numbered yaml document"
    }
    return fmt.Errorf("notification config invalid (%s): %w", docErr, err)
}

Prevention

When it happens

Trigger: loadConfig -> NewPluginConfigList(fin): dec.Decode returns a non-EOF error on document idx — invalid yaml syntax (tabs, bad types like a string where a list is expected) in the Nth --- separated document.

Common situations: Multi-document yaml where a later document has a syntax error or wrong types (e.g. timeout: soon instead of a duration); mixed content after ---; truncated file upload/edit.

Related errors


AI-assisted analysis of crowdsecurity/crowdsec@909b515798 (2026-09-06). Data as JSON: /api/errors/2088be1029defc56. Report an issue: GitHub.