googleapis/mcp-toolbox · error

doc %d: invalid config format at key %q: %w

Error message

doc %d: invalid config format at key %q: %w

What it means

ConvertConfig returns this when transforming a document section fails: a top-level key (e.g. 'sources', 'tools', 'prompts', 'groups') maps to a slice whose documents cannot be transformed by transformDocs into the flat format. It wraps the inner transform error with the doc index and source key for pinpointing the bad section.

Source

Thrown at cmd/internal/config.go:279

				switch key {
				case "authServices":
					key = "authService"
				case "sources":
					key = "source"
				case "embeddingModels":
					key = "embeddingModel"
				case "tools":
					key = "tool"
				case "toolsets":
					key = "toolset"
				case "prompts":
					key = "prompt"
				case "groups":
					key = "group"
				}
				transformed, err := transformDocs(key, slice)
				if err != nil {
					return nil, fmt.Errorf("doc %d: invalid config format at key %q: %w", docIndex, srcKey, err)
				}
				// encode per-doc
				for _, doc := range transformed {
					if err := encoder.Encode(migrateToolsetKind(ctx, doc)); err != nil {
						return nil, err
					}
				}
			} else {
				return nil, fmt.Errorf("doc %d: invalid config format at key %q: expected nested format keys and type map", docIndex, key)
			}
		}
	}
	return buf.Bytes(), nil
}

// hasKindField is a helper function to check if an input is in flat format
func hasKindField(input yaml.MapSlice) bool {
	for _, item := range input {

View on GitHub (pinned to 8cc6e09de2)

Solutions

  1. Follow the wrapped inner error to the exact doc and key; restore the expected nested keys and type map for that entry.
  2. Ensure each entry has the required 'kind' field and correct fields for that kind.
  3. Run the full migration command on the original legacy config rather than hand-editing.
  4. Compare the failing section against a working example in current docs and align it.

Example fix

# before: malformed tool entry
prompts:
  - name: greet
# missing kind/body
# after
prompts:
  - kind: prompt
    name: greet
    description: Greets the user
    messages:
      - content: "Hello!"
Defensive patterns

Strategy: validation

Validate before calling

for _, e := range cfg.Tools {
    if e["kind"] == nil { log.Fatalf("tool entry missing 'kind': %v", e) }
}

Try / catch

if strings.Contains(err.Error(), "invalid config format at key") {
    log.Fatalf("fix the section named in the error (doc index + key provided): %v", err)
}

Prevention

When it happens

Trigger: A legacy config section like `tools:` or `prompts:` contains a list of docs where an entry has an unexpected shape (missing expected fields/kind, wrong nesting), causing transformDocs to fail during ConvertConfig/runMigrate.

Common situations: Partially hand-migrated configs mixing old and new shapes per section; copy-pasted fragments from different toolbox versions; edits that removed required 'kind' or renamed fields.

Related errors


AI-assisted analysis of googleapis/mcp-toolbox@8cc6e09de2 (2026-09-05). Data as JSON: /api/errors/a663dc09986a4e73. Report an issue: GitHub.