OrchardCMS/OrchardCore · error · FormatException

Can't use the numeric key

Error message

Can't use the numeric key '{child.Key}' inside an object.

What it means

ToJsonNode builds a JsonArray when child keys are numeric and a JsonObject otherwise. A numeric key inside an object-shaped level is invalid, so the method throws FormatException naming the offending key; mixing array items and object properties at one level is not representable.

Solutions

  1. Make the level consistently array-shaped: use only numeric keys 0..n-1 for that section.
  2. Or use only named keys and drop/renumber the numeric ones.
  3. Locate the offending key with configuration.GetDebugView()/GetChildren() and fix the source provider (env vars, args, JSON).
  4. Use ToJsonNode() and read as JsonNode, checking kind, if your data can be either shape.

Example fix

// before
"App": { "Name": "x", "Items": { "0": "a", "1": "b" } } // fine, but sibling 'App:0' breaks it
// after
"App": { "Name": "x", "Items": ["a", "b"] }
Defensive patterns

Strategy: validation

Validate before calling

var keys = configuration.GetChildren().Select(c => c.Key).ToList();
bool mixed = keys.Any(k => int.TryParse(k, out _)) && keys.Any(k => !int.TryParse(k, out _));
if (mixed) throw new FormatException("Config level mixes numeric and named keys.");

Type guard

bool IsArrayShaped(IConfiguration c) => c.GetChildren().All(ch => int.TryParse(ch.Key, out _));

Try / catch

try { var node = configuration.ToJsonNode(); }
catch (FormatException ex) when (ex.Message.Contains("numeric key")) { /* fix provider keys or bind to typed model */ }

Prevention

When it happens

Trigger: A configuration level contains both named keys and numeric keys, or a parent has a named key while a sibling has key '0' (e.g. 'Foo:Bar' plus 'Foo:0' patterns), triggering the jObject-not-null branch.

Common situations: Environment variables like App__Items__0 and App__Items__1 mixed with App__Name; hand-edited appsettings mixing arrays and objects at the same level; command-line args adding indexed keys to an object section.

Understand the failure class

Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.

Related errors


AI-assisted analysis of OrchardCMS/OrchardCore@4306c0717f (2026-09-13). Data as JSON: /api/errors/a103f1e4b8093318. Report an issue: GitHub.

Appendix: source

Thrown at src/OrchardCore/OrchardCore.Abstractions/Shell/Configuration/Internal/ConfigurationExtensions.cs:31

        {
            throw new FormatException($"Top level JSON element must be an object. Instead, {jsonNode.GetValueKind()} was found.");
        }

        return jObject;
    }

    public static JsonNode ToJsonNode(this IConfiguration configuration)
    {
        JsonArray jArray = null;
        JsonObject jObject = null;

        foreach (var child in configuration.GetChildren())
        {
            if (int.TryParse(child.Key, out var index))
            {
                if (jObject is not null)
                {
                    throw new FormatException($"Can't use the numeric key '{child.Key}' inside an object.");
                }

                jArray ??= [];
                if (index > jArray.Count)
                {
                    // Inserting null values is useful to override arrays items,
                    // it allows to keep non null items at the right position.
                    for (var i = jArray.Count; i < index; i++)
                    {
                        jArray.Add(null);
                    }
                }

                if (child.GetChildren().Any())
                {
                    jArray.Add(ToJsonNode(child));
                }
                else

View on GitHub (pinned to 4306c0717f)