{"record":{"id":"42897f3de6123934","repo":"tui-cs/Terminal.Gui","slug":"propertyname-mod-is-not-a-valid-modifier","errorCode":null,"errorMessage":"{propertyName}: \"{mod}\" is not a valid modifier.","messagePattern":"(.+?): \"(.+?)\" is not a valid modifier\\.","errorType":"exception","errorClass":"JsonException","httpStatus":null,"severity":"error","filePath":"Terminal.Gui/Configuration/KeyCodeJsonConverter.cs","lineNumber":96,"sourceCode":"                        case \"modifiers\":\n                            if (reader.TokenType == JsonTokenType.StartArray)\n                            {\n                                while (reader.Read ())\n                                {\n                                    if (reader.TokenType == JsonTokenType.EndArray)\n                                    {\n                                        break;\n                                    }\n\n                                    string mod = reader.GetString ();\n\n                                    try\n                                    {\n                                        modifiers.Add (modifierDict [mod]);\n                                    }\n                                    catch (KeyNotFoundException e)\n                                    {\n                                        throw new JsonException ($\"{propertyName}: \\\"{mod}\\\" is not a valid modifier.\", e);\n                                    }\n                                }\n                            }\n                            else\n                            {\n                                throw new JsonException (\n                                                         $\"{propertyName}: Expected an array of modifiers, but got \\\"{reader.TokenType}\\\".\"\n                                                        );\n                            }\n\n                            break;\n\n                        default:\n                            throw new JsonException ($\"{propertyName}: Unexpected Key property.\");\n                    }\n                }\n            }\n","sourceCodeStart":78,"sourceCodeEnd":114,"githubUrl":"https://github.com/tui-cs/Terminal.Gui/blob/2e47b11478db083499917f2ad27c34d30efb0df1/Terminal.Gui/Configuration/KeyCodeJsonConverter.cs#L78-L114","documentation":"Thrown by KeyCodeJsonConverter.Read (KeyCodeJsonConverter.cs:94-97) when an element of the \"Modifiers\" array string does not match any key in the modifier dictionary (which contains only 'Shift', 'Ctrl', 'Alt', matched case-insensitively). The lookup throws KeyNotFoundException, which is wrapped as a JsonException naming the invalid modifier.","triggerScenarios":"A keybinding JSON object's \"Modifiers\" array contains a string other than Shift/Ctrl/Alt, e.g. [\"Win\"], [\"Command\"], [\"Control\"] (note: the dict key is \"Ctrl\", not \"Control\"), or a typo like [\"Ctrk\"].","commonSituations":"User writes \"Control\" instead of \"Ctrl\". User adds a platform modifier (Windows/Super/Command) that Terminal.Gui does not model. Typos. Inconsistent casing is tolerated, but alternate synonyms are not.","solutions":["Use only the three supported modifier names: \"Shift\", \"Ctrl\", \"Alt\" (case-insensitive).","Replace \"Control\" with \"Ctrl\".","Remove unsupported platform modifiers; Terminal.Gui keybindings only model Shift/Ctrl/Alt.","If you need a multi-modifier binding, list each in the array: [\"Ctrl\", \"Shift\"]."],"exampleFix":"// before\n{ \"Key\": \"A\", \"Modifiers\": [\"Control\"] }\n\n// after\n{ \"Key\": \"A\", \"Modifiers\": [\"Ctrl\"] }","handlingStrategy":"validation","validationCode":"using System.Collections.Generic;\n\nstatic readonly HashSet<string> ValidModifiers = new (System.StringComparer.OrdinalIgnoreCase)\n{ \"Shift\", \"Ctrl\", \"Alt\" };\n\nstatic bool AreModifiersValid (IEnumerable<string?>? mods)\n    => mods?.All (m => m is not null && ValidModifiers.Contains (m)) ?? true;\n\nif (!AreModifiersValid (modifierList))\n{\n    // replace synonyms/typos before writing config\n}","typeGuard":"static bool IsValidModifier (string? mod)\n    => mod is not null\n       && (mod.Equals (\"Shift\", StringComparison.OrdinalIgnoreCase)\n           || mod.Equals (\"Ctrl\", StringComparison.OrdinalIgnoreCase)\n           || mod.Equals (\"Alt\", StringComparison.OrdinalIgnoreCase));","tryCatchPattern":"try\n{\n    ConfigurationManager.Load (configJson);\n}\ncatch (JsonException ex) when (ex.Message.Contains (\"is not a valid modifier\"))\n{\n    // A Modifiers array entry is not Shift/Ctrl/Alt. Replace synonyms (Control->Ctrl) and reload.\n}","preventionTips":["Use only \"Shift\", \"Ctrl\", \"Alt\" (case-insensitive) in Modifiers arrays.","Replace \"Control\" with \"Ctrl\".","Do not include platform-specific modifiers (Win/Command) — Terminal.Gui does not model them.","List multiple modifiers as separate array elements."],"tags":["json","configuration","keybindings","key","modifiers","serialization"],"backgroundTag":null,"analyzedSha":"2e47b11478db083499917f2ad27c34d30efb0df1","analyzedAt":"2026-08-13T19:20:08.826Z","schemaVersion":2},"datasetVersion":"2026-08-14T00:17:13.853Z"}