From 694a0fcd55cf5adadf4b5a55b39e8cbc3178bf0c Mon Sep 17 00:00:00 2001 From: Arpit Jain Date: Tue, 28 Jul 2026 19:10:58 +0900 Subject: [PATCH] Raise TextFSMTemplateError for a Value line with no regex A Value line that has options and a name but no regex, such as 'Value Required beer', leaves self.regex empty. The bounds check that follows indexes it directly, so self.regex[0] raises IndexError: string index out of range. That escapes the TextFSMTemplateError handling in _ParseFSMVariables, so a malformed template surfaces a raw builtin from the TextFSM constructor instead of the library's own template error. Treat an empty regex as not contained within a '()' pair, which is what it is, and reuse the existing message. Regexes of length one already short-circuit on the first two comparisons, so the empty case was the only crash. Signed-off-by: Arpit Jain --- tests/textfsm_test.py | 9 +++++++++ textfsm/parser.py | 7 ++++++- 2 files changed, 15 insertions(+), 1 deletion(-) diff --git a/tests/textfsm_test.py b/tests/textfsm_test.py index 022a8b6..9177e56 100755 --- a/tests/textfsm_test.py +++ b/tests/textfsm_test.py @@ -75,6 +75,12 @@ def testFSMValue(self): textfsm.TextFSMTemplateError, v.Parse, r'Value beer (boo)hoo\)' ) + # A missing regex is a template error, not an IndexError. + v = textfsm.TextFSMValue(options_class=textfsm.TextFSMOptions) + self.assertRaises( + textfsm.TextFSMTemplateError, v.Parse, 'Value Required beer' + ) + # Unbalanced parenthesis can exist if within square "[]" braces. v = textfsm.TextFSMValue(options_class=textfsm.TextFSMOptions) v.Parse('Value beer (boo[(]hoo)') @@ -265,6 +271,9 @@ def testParseFSMVariables(self): buf = 'Value filldown,Required Wine ((c|C)laret)' f = io.StringIO(buf) self.assertRaises(textfsm.TextFSMTemplateError, t._ParseFSMVariables, f) + buf = 'Value Required Beer' + f = io.StringIO(buf) + self.assertRaises(textfsm.TextFSMTemplateError, t._ParseFSMVariables, f) # Values that look bad but are OK. buf = ( diff --git a/textfsm/parser.py b/textfsm/parser.py index c00c976..07efb96 100755 --- a/textfsm/parser.py +++ b/textfsm/parser.py @@ -305,7 +305,12 @@ def Parse(self, value): "Invalid Value name '%s' or name too long." % self.name ) - if self.regex[0] != '(' or self.regex[-1] != ')' or self.regex[-2] == '\\': + if ( + not self.regex + or self.regex[0] != '(' + or self.regex[-1] != ')' + or self.regex[-2] == '\\' + ): raise TextFSMTemplateError( "Value '%s' must be contained within a '()' pair." % self.regex )