{"record":{"id":"a80ab145eb76549e","repo":"dotnet/wpf","slug":"brokenrule-sr-unexpectedtoken-based-parser-rule-error","errorCode":null,"errorMessage":"brokenRule (SR.UnexpectedToken-based parser rule error)","messagePattern":"brokenRule \\(SR\\.UnexpectedToken-based parser rule error\\)","errorType":"exception","errorClass":"XamlParseException","httpStatus":null,"severity":"error","filePath":"src/Microsoft.DotNet.Wpf/src/System.Xaml/System/Xaml/Parser/MePullParser.cs","lineNumber":68,"sourceCode":"        //  PositionalArgs ::= (Value (',' PositionalArgs)?) | NamedArg\n        //       Value     ::= STRING | QUOTEDMARKUPEXTENSION |MarkupExtension\n\n        public IEnumerable<XamlNode> Parse(string text, int lineNumber, int linePosition)\n        {\n            _tokenizer = new MeScanner(_context, text, lineNumber, linePosition);\n            _originalText = text;\n            Found f = new Found();\n            NextToken();\n            foreach (XamlNode node in P_MarkupExtension(f))\n            {\n                yield return node;\n            }\n\n            if (!f.found)\n            {\n                string brokenRule = _brokenRule;\n                _brokenRule = null;\n                throw new XamlParseException(_tokenizer, brokenRule);\n            }\n\n            if (_tokenizer.Token != MeTokenType.None)\n            {\n                throw new XamlParseException(_tokenizer, SR.UnexpectedTokenAfterME);\n            }\n\n            if (_tokenizer.HasTrailingWhitespace)\n            {\n                throw new XamlParseException(_tokenizer, SR.WhitespaceAfterME);\n            }\n        }\n\n        private void SetBrokenRuleString(string ruleString)\n        {\n            if (string.IsNullOrEmpty(_brokenRule))\n            {\n                _brokenRule = SR.Format(SR.UnexpectedToken,","sourceCodeStart":50,"sourceCodeEnd":86,"githubUrl":"https://github.com/dotnet/wpf/blob/81131a70a4c573cd62748a5c36908fc4d662daa9/src/Microsoft.DotNet.Wpf/src/System.Xaml/System/Xaml/Parser/MePullParser.cs#L50-L86","documentation":"MePullParser.Parse processes a markup extension string ('{...}'). If the tokenizer never found a valid markup-extension construct (f.found == false), the accumulated broken-rule description (_brokenRule) is thrown as a XamlParseException, typically carrying SR.UnexpectedToken. This is the generic 'not a parseable markup extension' error.","triggerScenarios":"Passing a string starting with '{' that does not match the markup-extension grammar: '{' alone, '{}', '{Foo' with unterminated syntax, or a token sequence violating the ME rules.","commonSituations":"Dynamically built attribute values with malformed curly syntax, strings intended as literals needing {} escape, truncation during serialization.","solutions":["Check the markup-extension string for balanced braces and valid 'Name Args' syntax","Escape literal strings that start with '{' using the '{}' prefix","Validate the extension name exists (e.g. StaticResource, Binding)","Catch XamlParseException and log the tokenizer line/column info"],"exampleFix":"// before\nbutton.Content = \"{CustomThing}\"; // malformed\n// after\nbutton.Content = \"{StaticResource myThing}\"; // or escape: \"{}{CustomThing}\"","handlingStrategy":"validation","validationCode":"bool LooksLikeMarkupExtension(string s)\n{\n    if (s == null || !s.TrimStart().StartsWith(\"{\")) return true; // literal, fine\n    string t = s.Trim();\n    if (t == \"{\" || t == \"{}\") return true; // escape sequence / empty\n    return t.EndsWith(\"}\") && t.Count(c => c=='{') == t.Count(c => c=='}');\n}","typeGuard":null,"tryCatchPattern":"try { nodes = parser.Parse(meString); }\ncatch (XamlParseException ex) { /* inspect ex.Message for the broken-rule text */ }","preventionTips":["Escape literal '{' values with '{}' prefix","Validate brace balance before parsing untrusted input","Keep extension strings minimal and machine-generated where possible"],"tags":["xaml","markup-extension","parser"],"backgroundTag":"invalid-argument-format","analyzedSha":"81131a70a4c573cd62748a5c36908fc4d662daa9","analyzedAt":"2026-09-14T10:12:48.479Z","contentChangedAt":"2026-09-14T10:12:48.479Z","schemaVersion":2},"datasetVersion":"2026-09-21T21:30:21.729Z"}