Skip to content

Commit 57a3451

Browse files
committed
improve tests
1 parent b40003b commit 57a3451

File tree

3 files changed

+34
-14
lines changed

3 files changed

+34
-14
lines changed

Lib/test/test_dstring.py

Lines changed: 26 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,50 @@
11
import unittest
22

3+
_dstring_prefixes = "d db df dt dr drb drf drt".split()
4+
_dstring_prefixes += [p.upper() for p in _dstring_prefixes]
35

46
class DStringTestCase(unittest.TestCase):
57
def assertAllRaise(self, exception_type, regex, error_strings):
68
for str in error_strings:
79
with self.subTest(str=str):
810
with self.assertRaisesRegex(exception_type, regex) as cm:
911
eval(str)
10-
# print("Testing expression:", repr(str))
11-
# print(repr(cm.exception))
12-
# print(repr(cm.exception.text))
1312

1413
def test_single_quote(self):
1514
exprs = [
16-
"d'hello'",
17-
'D"hello"',
18-
"d'hello\\nworld'",
15+
f"{p}'hello, world'" for p in _dstring_prefixes
16+
] + [
17+
f'{p}"hello, world"' for p in _dstring_prefixes
1918
]
2019
self.assertAllRaise(SyntaxError, "d-string must be triple-quoted", exprs)
2120

2221
def test_empty_dstring(self):
2322
exprs = [
24-
"d''''''",
25-
'D""""""',
23+
f"{p}''''''" for p in _dstring_prefixes
24+
] + [
25+
f'{p}""""""' for p in _dstring_prefixes
2626
]
2727
self.assertAllRaise(SyntaxError, "d-string must start with a newline", exprs)
2828

2929
def test_simple_dstring(self):
30-
self.assertEqual(eval('d"""\n hello world\n """'), "hello world\n")
31-
self.assertEqual(eval('d"""\n hello world\n """'), " hello world\n")
32-
self.assertEqual(eval('d"""\n hello world\n"""'), " hello world\n")
33-
self.assertEqual(eval('d"""\n hello world\\\n """'), " hello world")
34-
self.assertEqual(eval('dr"""\n hello world\\\n """'), " hello world\\\n")
30+
cases = [
31+
('{prefix}"""\n hello world\n """', "hello world\n"),
32+
('{prefix}"""\n hello world\n """', " hello world\n"),
33+
('{prefix}"""\n hello world\n"""', " hello world\n"),
34+
('{prefix}"""\n hello world\\\n """', " hello world"),
35+
('{prefix}"""\n hello world\\\n """', " hello world\\\n"),
36+
]
37+
38+
for p in _dstring_prefixes:
39+
bstring = 'b' in p.lower()
40+
rstring = 'r' in p.lower()
41+
for source, expected in cases:
42+
source = source.format(prefix=p)
43+
if rstring:
44+
expected = expected.replace('\\', '\\\\').replace('\n', '\\n')
45+
if bstring:
46+
expected = expected.encode()
47+
self.assertEqual(eval(source), expected)
3548

3649

3750
if __name__ == '__main__':

Parser/action_helpers.c

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1481,6 +1481,13 @@ _get_resized_exprs(Parser *p, Token *a, asdl_expr_seq *raw_expressions, Token *b
14811481
Py_ssize_t common_indent_len = 0;
14821482

14831483
if (is_dedent) {
1484+
if (total_items == 0) {
1485+
RAISE_SYNTAX_ERROR_KNOWN_LOCATION(
1486+
a,
1487+
"d-string must start with a newline"
1488+
);
1489+
return NULL;
1490+
}
14841491
expr_ty first_item = asdl_seq_GET(raw_expressions, 0);
14851492
if (first_item->kind != Constant_kind
14861493
|| PyUnicode_ReadChar(first_item->v.Constant.value, 0) != '\n') {

Parser/lexer/lexer.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1124,7 +1124,7 @@ tok_get_normal_mode(struct tok_state *tok, tokenizer_mode* current_tok, struct t
11241124
case 'd':
11251125
case 'D':
11261126
if (quote_size != 3) {
1127-
return MAKE_TOKEN(_PyTokenizer_syntaxerror(tok, "d-string must be a multiline string"));
1127+
return MAKE_TOKEN(_PyTokenizer_syntaxerror(tok, "d-string must be triple-quoted"));
11281128
}
11291129
break;
11301130
default:

0 commit comments

Comments
 (0)