From 417907b36d0edc84984f29f17ab079eee236b196 Mon Sep 17 00:00:00 2001 From: Rasmus Lerchedahl Petersen Date: Mon, 25 Sep 2023 11:44:56 +0200 Subject: [PATCH] Python: switch to inline expectations --- .../regexparser/Locations.expected | 22 +--------- .../library-tests/regexparser/Locations.ql | 30 ++++++++++--- .../library-tests/regexparser/locations.py | 44 +++++++++---------- 3 files changed, 49 insertions(+), 47 deletions(-) diff --git a/python/ql/test/library-tests/regexparser/Locations.expected b/python/ql/test/library-tests/regexparser/Locations.expected index 3b07d5d758c..8ec8033d086 100644 --- a/python/ql/test/library-tests/regexparser/Locations.expected +++ b/python/ql/test/library-tests/regexparser/Locations.expected @@ -1,20 +1,2 @@ -| locations.py | 14 | 2 | -| locations.py | 19 | 3 | -| locations.py | 24 | 3 | -| locations.py | 29 | 4 | -| locations.py | 34 | 4 | -| locations.py | 39 | 5 | -| locations.py | 44 | 5 | -| locations.py | 49 | 6 | -| locations.py | 54 | 2 | -| locations.py | 54 | 23 | -| locations.py | 59 | 2 | -| locations.py | 59 | 23 | -| locations.py | 65 | 2 | -| locations.py | 65 | 23 | -| locations.py | 72 | 6 | -| locations.py | 72 | 27 | -| locations.py | 80 | 3 | -| locations.py | 85 | 5 | -| locations.py | 90 | 2 | -| locations.py | 90 | 23 | +testFailures +failures diff --git a/python/ql/test/library-tests/regexparser/Locations.ql b/python/ql/test/library-tests/regexparser/Locations.ql index 79956e487e9..bef14918dc6 100644 --- a/python/ql/test/library-tests/regexparser/Locations.ql +++ b/python/ql/test/library-tests/regexparser/Locations.ql @@ -1,7 +1,27 @@ +import python import semmle.python.regexp.RegexTreeView::RegexTreeView +import TestUtilities.InlineExpectationsTest +private import semmle.python.dataflow.new.internal.PrintNode -from RegExpTerm t, string file, int line, int column -where - t.toString() = "[this]" and - t.hasLocationInfo(file, line, column, _, _) -select file, line, column +module RegexLocationTest implements TestSig { + string getARelevantTag() { result = "location" } + + predicate hasActualResult(Location location, string element, string tag, string value) { + exists(location.getFile().getRelativePath()) and + exists(Call compile, RegExpTerm t, int line, int column | + // All the tested regexes are inside a call to `compile` + compile.getAnArg() = t.getRegex() and + t.toString() = "[this]" and + t.hasLocationInfo(_, line, column, _, _) + | + // put the annotation on the start line of the call to `compile` + location = compile.getFunc().getLocation() and + element = t.toString() and + // show the (relative) line and column for the fragment + value = (line - location.getStartLine()).toString() + ":" + column.toString() and + tag = "location" + ) + } +} + +import MakeTest diff --git a/python/ql/test/library-tests/regexparser/locations.py b/python/ql/test/library-tests/regexparser/locations.py index bbfb6b2840f..a7a9b38d130 100644 --- a/python/ql/test/library-tests/regexparser/locations.py +++ b/python/ql/test/library-tests/regexparser/locations.py @@ -7,86 +7,86 @@ import re # # To make the location information easier to understand, we generally put each # regexp on its own line, even though this is not idiomatic Python. -# Comments indicate cases we currently do not handle correctly. +# Comments indicate the found locations relative to the call to `compile`. # plain string -re.compile( +re.compile( # $location=1:2 '[this] is a test' ) # raw string -re.compile( +re.compile( # $ location=1:3 r'[this] is a test' ) # byte string -re.compile( +re.compile( # $ location=1:3 b'[this] is a test' ) # byte raw string -re.compile( +re.compile( # $ location=1:4 br'[this] is a test' ) # multiline string -re.compile( +re.compile( # $ location=1:4 '''[this] is a test''' ) # multiline raw string -re.compile( +re.compile( # $ location=1:5 r'''[this] is a test''' ) # multiline byte string -re.compile( +re.compile( # $ location=1:5 b'''[this] is a test''' ) # multiline byte raw string -re.compile( +re.compile( # $ location=1:6 br'''[this] is a test''' ) -# plain string with multiple parts (second [this] gets wrong column: 23 instead of 26) -re.compile( +# plain string with multiple parts +re.compile( # $ location=1:2 SPURIOUS:location=1:23 MISSING:location=1:26 '[this] is a test' ' and [this] is another test' ) -# plain string with multiple parts across lines (second [this] gets wrong location: 59:23 instead of 60:7) -re.compile( +# plain string with multiple parts across lines +re.compile( # $ location=1:2 SPURIOUS:location=1:23 MISSING:location=2:7 '[this] is a test' ' and [this] is another test' ) -# plain string with multiple parts across lines and comments (second [this] gets wrong location: 65:23 instead of 67:7) -re.compile( +# plain string with multiple parts across lines and comments +re.compile( # $ location=1:2 SPURIOUS:location=1:23 MISSING:location=3:7 '[this] is a test' # comment ' and [this] is another test' ) -# actual multiline string (both [this]s get wrong location: 72:6 and 72:27 instead of 73:1 and 74:5) -re.compile( +# actual multiline string +re.compile( # $ SPURIOUS:location=1:6 location=1:27 MISSING:location=2:1 location=3:5 r''' [this] is a test and [this] is another test ''' ) -# plain string with escape sequences ([this] gets wrong location: 80:3 instead of 80:4) -re.compile( +# plain string with escape sequences +re.compile( # $ SPURIOUS:location=1:3 MISSING:location=1:4 '\t[this] is a test' ) # raw string with escape sequences -re.compile( +re.compile( # $ location=1:5 r'\A[this] is a test' ) -# plain string with escaped newline (second [this] gets wrong location: 90:23 instead of 91:6) -re.compile( +# plain string with escaped newline +re.compile( # $ location=1:2 SPURIOUS:location=1:23 MISSING:location=2:6 '[this] is a test\ and [this] is another test' ) \ No newline at end of file