10000 impl re.template(), · moreal/RustPython@d9375b9 · GitHub
[go: up one dir, main page]

Skip to content

Commit d9375b9

Browse files
qingshi163youknowone
authored andcommitted
impl re.template(),
template_compile template_expand subx
1 parent 1e3d578 commit d9375b9

File tree

5 files changed

+191
-97
lines changed

5 files changed

+191
-97
lines changed

Cargo.lock

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Lib/string.py

Lines changed: 30 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -45,7 +45,7 @@ def capwords(s, sep=None):
4545
sep is used to split and join the words.
4646
4747
"""
48-
return (sep or ' ').join(x.capitalize() for x in s.split(sep))
48+
return (sep or ' ').join(map(str.capitalize, s.split(sep)))
4949

5050

5151
####################################################################
@@ -141,6 +141,35 @@ def convert(mo):
141141
self.pattern)
142142
return self.pattern.sub(convert, self.template)
143143

144+
def is_valid(self):
145+
for mo in self.pattern.finditer(self.template):
146+
if mo.group('invalid') is not None:
147+
return False
148+
if (mo.group('named') is None
149+
and mo.group('braced') is None
150+
and mo.group('escaped') is None):
151+
# If all the groups are None, there must be
152+
# another group we're not expecting
153+
raise ValueError('Unrecognized named group in pattern',
154+
self.pattern)
155+
return True
156+
157+
def get_identifiers(self):
158+
ids = []
159+
for mo in self.pattern.finditer(self.template):
160+
named = mo.group('named') or mo.group('braced')
161+
if named is not None and named not in ids:
162+
# add a named group only the first time it appears
163+
ids.append(named)
164+
elif (named is None
165+
and mo.group('invalid') is None
166+
and mo.group('escaped') is None):
167+
# If all the groups are None, there must be
168+
# another group we're not expecting
169+
raise ValueError('Unrecognized named group in pattern',
170+
self.pattern)
171+
return ids
172+
144173
# Initialize Template.pattern. __init_subclass__() is automatically called
145174
# only for subclasses, not for the Template class itself.
146175
Template.__init_subclass__()

Lib/test/test_re.py

Lines changed: 4 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -116,8 +116,6 @@ def bump_num(self, matchobj):
116116
int_value = int(matchobj.group(0))
117117
return str(int_value + 1)
118118

119-
# TODO: RUSTPYTHON
120-
@unittest.expectedFailure
121119
def test_basic_re_sub(self):
122120
self.assertTypedEqual(re.sub('y', 'a', 'xyz'), 'xaz')
123121
self.assertTypedEqual(re.sub('y', S('a'), S('xyz')), 'xaz')
@@ -161,15 +159,11 @@ def test_basic_re_sub(self):
161159

162160
self.assertEqual(re.sub(r'^\s*', 'X', 'test'), 'Xtest')
163161

164-
# TODO: RUSTPYTHON
165-
@unittest.expectedFailure
166162
def test_bug_449964(self):
167163
# fails for group followed by other escape
168164
self.assertEqual(re.sub(r'(?P<unk>x)', r'\g<1>\g<1>\b', 'xx'),
169165
'xx\bxx\b')
170166

171-
# TODO: RUSTPYTHON
172-
@unittest.expectedFailure
173167
def test_bug_449000(self):
174168
# Test for sub() on escaped characters
175169
self.assertEqual(re.sub(r'\r\n', r'\n', 'abc\r\ndef\r\n'),
@@ -193,8 +187,6 @@ def test_bug_3629(self):
193187
# A regex that triggered a bug in the sre-code validator
194188
re.compile("(?P<quote>)(?(quote))")
195189

196-
# TODO: RUSTPYTHON
197-
@unittest.expectedFailure
198190
def test_sub_template_numeric_escape(self):
199191
# bug 776311 and friends
200192
self.assertEqual(re.sub('x', r'\0', 'x'), '\0')
@@ -248,8 +240,6 @@ def test_qualified_re_sub(self):
248240
self.assertEqual(re.sub('a', 'b', 'aaaaa', 1), 'baaaa')
249241
self.assertEqual(re.sub('a', 'b', 'aaaaa', count=1), 'baaaa')
250242

251-
# TODO: RUSTPYTHON
252-
@unittest.expectedFailure
253243
def test_bug_114660(self):
254244
self.assertEqual(re.sub(r'(\S)\s+(\S)', r'\1 \2', 'hello there'),
255245
'hello there')
@@ -303,8 +293,6 @@ def test_symbolic_groups_errors(self):
303293
self.checkPatternError(b'(?(\xc2\xb5)y)',
304294
r"bad character in group name '\xc2\xb5'", 3)
305295

306-
# TODO: RUSTPYTHON
307-
@unittest.expectedFailure
308296
def test_symbolic_refs(self):
309297
self.assertEqual(re.sub('(?P<a>x)|(?P<b>y)', r'\g<b>', 'xx'), '')
310298
self.assertEqual(re.sub('(?P<a>x)|(?P<b>y)', r'\2', 'xx'), '')
@@ -316,8 +304,6 @@ def test_symbolic_refs(self):
316304
pat = '|'.join('x(?P<a%d>%x)y' % (i, i) for i in range(1, 200 + 1))
317305
self.assertEqual(re.sub(pat, r'\g<200>', 'xc8yzxc8y'), 'c8zc8')
318306

319-
# TODO: RUSTPYTHON
320-
@unittest.expectedFailure
321307
def test_symbolic_refs_errors(self):
322308
self.checkTemplateError('(?P<a>x)', r'\g<a', 'xx',
323309
'missing >, unterminated name', 3)
@@ -651,8 +637,6 @@ def test_re_groupref_exists_validation_bug(self):
651637
with self.subTest(code=i):
652638
re.compile(r'()(?(1)\x%02x?)' % i)
653639

654-
# TODO: RUSTPYTHON
655-
@unittest.expectedFailure
656640
def test_re_groupref_overflow(self):
657641
from re._constants import MAXGROUPS
658642
self.checkTemplateError('()', r'\g<%s>' % MAXGROUPS, 'xx',
@@ -1754,8 +1738,6 @@ def test_comments(self):
17541738
self.assertTrue(re.fullmatch('(?x)#x\na|#y\nb', 'a'))
17551739
self.assertTrue(re.fullmatch('(?x)#x\na|#y\nb', 'b'))
17561740

1757-
# TODO: RUSTPYTHON
1758-
@unittest.expectedFailure
17591741
def test_bug_6509(self):
17601742
# Replacement strings of both types must parse properly.
17611743
# all strings
@@ -1902,8 +1884,6 @@ def test_match_repr(self):
19021884
)
19031885
self.assertRegex(repr(second), pattern)
19041886

1905-
# TODO: RUSTPYTHON
1906-
@unittest.expectedFailure
19071887
def test_zerowidth(self):
19081888
# Issues 852532, 1647489, 3262, 25054.
19091889
self.assertEqual(re.split(r"\b", "a::bc"), ['', 'a', '::', 'bc', ''])
@@ -2235,8 +2215,6 @@ def test_MIN_REPEAT_ONE_mark_bug(self):
22352215
p = r'(?:a*?(xx)??z)*'
22362216
self.assertEqual(re.match(p, s).groups(), ('xx',))
22372217

2238-
# TODO: RUSTPYTHON
2239-
@unittest.expectedFailure
22402218
def test_ASSERT_NOT_mark_bug(self):
22412219
# Fixed in issue35859, reported in issue725149.
22422220
# JUMP_ASSERT_NOT should LASTMARK_SAVE()
@@ -2249,16 +2227,12 @@ def test_ASSERT_NOT_mark_bug(self):
22492227
self.assertEqual(m.span(3), (3, 4))
22502228
self.assertEqual(m.groups(), ('b', None, 'b'))
22512229

2252-
# TODO: RUSTPYTHON
2253-
@unittest.expectedFailure
22542230
def test_bug_40736(self):
22552231
with self.assertRaisesRegex(TypeError, "got 'int'"):
22562232
re.search("x*", 5)
22572233
with self.assertRaisesRegex(TypeError, "got 'type'"):
22582234
re.search("x*", type)
22592235

2260-
# TODO: RUSTPYTHON
2261-
@unittest.expectedFailure
22622236
def test_search_anchor_at_beginning(self):
22632237
s = 'x'*10**7
22642238
start = time.perf_counter()
@@ -2273,7 +2247,8 @@ def test_search_anchor_at_beginning(self):
22732247
# With optimization -- 0.0003 seconds.
22742248
self.assertLess(t, 0.1)
22752249

2276-
@unittest.skip('dead lock')
2250+
# TODO: RUSTPYTHON
2251+
@unittest.expectedFailure
22772252
def test_possessive_quantifiers(self):
22782253
"""Test Possessive Quantifiers
22792254
Test quantifiers of the form @+ for some repetition operator @,
@@ -2342,7 +2317,6 @@ def test_fullmatch_possessive_quantifiers(self):
23422317
self.assertTrue(re.fullmatch(r'(?:ab)?+c', 'abc'))
23432318
self.assertTrue(re.fullmatch(r'(?:ab){1,3}+c', 'abc'))
23442319

2345-
@unittest.skip("dead lock")
23462320
def test_findall_possessive_quantifiers(self):
23472321
self.assertEqual(re.findall(r'a++', 'aab'), ['aa'])
23482322
self.assertEqual(re.findall(r'a*+', 'aab'), ['aa', '', ''])
@@ -2354,8 +2328,6 @@ def test_findall_possessive_quantifiers(self):
23542328
self.assertEqual(re.findall(r'(?:ab)?+', 'ababc'), ['ab', 'ab', '', ''])
23552329
self.assertEqual(re.findall(r'(?:ab){1,3}+', 'ababc'), ['abab'])
23562330

2357-
# TODO: RUSTPYTHON
2358-
@unittest.expectedFailure
23592331
def test_atomic_grouping(self):
23602332
"""Test Atomic Grouping
23612333
Test non-capturing groups of the form (?>...), which does
@@ -2399,8 +2371,6 @@ def test_fullmatch_atomic_grouping(self):
23992371
self.assertTrue(re.fullmatch(r'(?>(?:ab)?)c', 'abc'))
24002372
self.assertTrue(re.fullmatch(r'(?>(?:ab){1,3})c', 'abc'))
24012373

2402-
# TODO: RUSTPYTHON
2403-
@unittest.expectedFailure
24042374
def test_findall_atomic_grouping(self):
24052375
self.assertEqual(re.findall(r'(?>a+)', 'aab'), ['aa'])
24062376
self.assertEqual(re.findall(r'(?>a*)', 'aab'), ['aa', '', ''])
@@ -2412,6 +2382,8 @@ def test_findall_atomic_grouping(self):
24122382
self.assertEqual(re.findall(r'(?>(?:ab)?)', 'ababc'), ['ab', 'ab', '', ''])
24132383
self.assertEqual(re.findall(r'(?>(?:ab){1,3})', 'ababc'), ['abab'])
24142384

2385+
# TODO: RUSTPYTHON
2386+
@unittest.expectedFailure
24152387
def test_bug_gh91616(self):
24162388
self.assertTrue(re.fullmatch(r'(?s:(?>.*?\.).*)\Z', "a.txt")) # reproducer
24172389
self.assertTrue(re.fullmatch(r'(?s:(?=(?P<g0>.*?\.))(?P=g0).*)\Z', "a.txt"))
@@ -2442,8 +2414,6 @@ def test_template_function_and_flag_is_deprecated(self):
24422414
self.assertTrue(template_re1.match('ahoy'))
24432415
self.assertFalse(template_re1.match('nope'))
24442416

2445-
# TODO: RUSTPYTHON
2446-
@unittest.expectedFailure
24472417
def test_bug_gh106052(self):
24482418
# gh-100061
24492419
self.assertEqual(re.match('(?>(?:.(?!D))+)', 'ABCDE').span(), (0, 2))

vm/Cargo.toml

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -80,9 +80,8 @@ timsort = "0.1.2"
8080
# RustPython crates implementing functionality based on CPython
8181
# sre-engine = "0.4.1"
8282
# to work on sre-engine locally or git version
83-
# sre-engine = { git = "https://github.com/RustPython/sre-engine", rev = "refs/pull/14/head" }
83+
sre-engine = { git = "https://github.com/RustPython/sre-engine", rev = "refs/pull/17/head" }
8484
# sre-engine = { git = "https://github.com/RustPython/sre-engine" }
85-
sre-engine = { path = "../../sre-engine" }
8685

8786
## unicode stuff
8887
unicode_names2 = { workspace = true }

0 commit comments

Comments
 (0)
0