Skip to content
20 changes: 10 additions & 10 deletions Lib/test/test_bytes.py
Original file line number Diff line number Diff line change
Expand Up @@ -781,16 +781,16 @@ def __int__(self):
pi = PseudoFloat(3.1415)

exceptions_params = [
('%x format: an integer is required, not float', b'%x', 3.14),
('%X format: an integer is required, not float', b'%X', 2.11),
('%o format: an integer is required, not float', b'%o', 1.79),
('%x format: an integer is required, not PseudoFloat', b'%x', pi),
('%x format: an integer is required, not complex', b'%x', 3j),
('%X format: an integer is required, not complex', b'%X', 2j),
('%o format: an integer is required, not complex', b'%o', 1j),
('%u format: a real number is required, not complex', b'%u', 3j),
('%i format: a real number is required, not complex', b'%i', 2j),
('%d format: a real number is required, not complex', b'%d', 2j),
('an integer is required for format %x, not float', b'%x', 3.14),
('an integer is required for format %X, not float', b'%X', 2.11),
('an integer is required for format %o, not float', b'%o', 1.79),
(r'an integer is required for format %x, not .*\.PseudoFloat', b'%x', pi),
('an integer is required for format %x, not complex', b'%x', 3j),
('an integer is required for format %X, not complex', b'%X', 2j),
('an integer is required for format %o, not complex', b'%o', 1j),
('a real number is required for format %u, not complex', b'%u', 3j),
('a real number is required for format %i, not complex', b'%i', 2j),
('a real number is required for format %d, not complex', b'%d', 2j),
(
r'%c requires an integer in range\(256\)'
r' or a single byte, not .*\.PseudoFloat',
Expand Down
222 changes: 185 additions & 37 deletions Lib/test/test_format.py

Large diffs are not rendered by default.

19 changes: 12 additions & 7 deletions Lib/test/test_peepholer.py
Original file line number Diff line number Diff line change
Expand Up @@ -733,22 +733,27 @@ def test_format_errors(self):
with self.assertRaisesRegex(TypeError,
'not all arguments converted during string formatting'):
eval("'%s' % (x, y)", {'x': 1, 'y': 2})
with self.assertRaisesRegex(ValueError, 'incomplete format'):
with self.assertRaisesRegex(ValueError, 'stray % at position 2'):
Comment thread
vstinner marked this conversation as resolved.
eval("'%s%' % (x,)", {'x': 1234})
with self.assertRaisesRegex(ValueError, 'incomplete format'):
with self.assertRaisesRegex(ValueError, 'stray % at position 4'):
eval("'%s%%%' % (x,)", {'x': 1234})
with self.assertRaisesRegex(TypeError,
'not enough arguments for format string'):
eval("'%s%z' % (x,)", {'x': 1234})
with self.assertRaisesRegex(ValueError, 'unsupported format character'):
with self.assertRaisesRegex(ValueError,
'unsupported format %z at position 2'):
eval("'%s%z' % (x, 5)", {'x': 1234})
with self.assertRaisesRegex(TypeError, 'a real number is required, not str'):
with self.assertRaisesRegex(TypeError,
'format argument 1: a real number is required for format %d, not str'):
eval("'%d' % (x,)", {'x': '1234'})
with self.assertRaisesRegex(TypeError, 'an integer is required, not float'):
with self.assertRaisesRegex(TypeError,
'format argument 1: an integer is required for format %x, not float'):
eval("'%x' % (x,)", {'x': 1234.56})
with self.assertRaisesRegex(TypeError, 'an integer is required, not str'):
with self.assertRaisesRegex(TypeError,
'format argument 1: an integer is required for format %x, not str'):
eval("'%x' % (x,)", {'x': '1234'})
with self.assertRaisesRegex(TypeError, 'must be real number, not str'):
with self.assertRaisesRegex(TypeError,
'format argument 1: a real number is required for format %f, not str'):
eval("'%f' % (x,)", {'x': '1234'})
with self.assertRaisesRegex(TypeError,
'not enough arguments for format string'):
Expand Down
22 changes: 11 additions & 11 deletions Lib/test/test_str.py
Original file line number Diff line number Diff line change
Expand Up @@ -1578,17 +1578,17 @@ def __int__(self):
self.assertEqual('%X' % letter_m, '6D')
self.assertEqual('%o' % letter_m, '155')
self.assertEqual('%c' % letter_m, 'm')
self.assertRaisesRegex(TypeError, '%x format: an integer is required, not float', operator.mod, '%x', 3.14)
self.assertRaisesRegex(TypeError, '%X format: an integer is required, not float', operator.mod, '%X', 2.11)
self.assertRaisesRegex(TypeError, '%o format: an integer is required, not float', operator.mod, '%o', 1.79)
self.assertRaisesRegex(TypeError, '%x format: an integer is required, not PseudoFloat', operator.mod, '%x', pi)
self.assertRaisesRegex(TypeError, '%x format: an integer is required, not complex', operator.mod, '%x', 3j)
self.assertRaisesRegex(TypeError, '%X format: an integer is required, not complex', operator.mod, '%X', 2j)
self.assertRaisesRegex(TypeError, '%o format: an integer is required, not complex', operator.mod, '%o', 1j)
self.assertRaisesRegex(TypeError, '%u format: a real number is required, not complex', operator.mod, '%u', 3j)
self.assertRaisesRegex(TypeError, '%i format: a real number is required, not complex', operator.mod, '%i', 2j)
self.assertRaisesRegex(TypeError, '%d format: a real number is required, not complex', operator.mod, '%d', 1j)
self.assertRaisesRegex(TypeError, r'%c requires an int or a unicode character, not .*\.PseudoFloat', operator.mod, '%c', pi)
self.assertRaisesRegex(TypeError, 'an integer is required for format %x, not float', operator.mod, '%x', 3.14)
self.assertRaisesRegex(TypeError, 'an integer is required for format %X, not float', operator.mod, '%X', 2.11)
self.assertRaisesRegex(TypeError, 'an integer is required for format %o, not float', operator.mod, '%o', 1.79)
self.assertRaisesRegex(TypeError, r'an integer is required for format %x, not .*\.PseudoFloat', operator.mod, '%x', pi)
self.assertRaisesRegex(TypeError, 'an integer is required for format %x, not complex', operator.mod, '%x', 3j)
self.assertRaisesRegex(TypeError, 'an integer is required for format %X, not complex', operator.mod, '%X', 2j)
self.assertRaisesRegex(TypeError, 'an integer is required for format %o, not complex', operator.mod, '%o', 1j)
self.assertRaisesRegex(TypeError, 'a real number is required for format %u, not complex', operator.mod, '%u', 3j)
self.assertRaisesRegex(TypeError, 'a real number is required for format %i, not complex', operator.mod, '%i', 2j)
self.assertRaisesRegex(TypeError, 'a real number is required for format %d, not complex', operator.mod, '%d', 1j)
self.assertRaisesRegex(TypeError, r'%c requires an integer or a unicode character, not .*\.PseudoFloat', operator.mod, '%c', pi)

class RaisingNumber:
def __int__(self):
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
Improve error messages for printf-style formatting.
For errors in the format string, always include the position of the
start of the format unit.
For errors related to the formatted arguments, always include the number
or the name of the argument.
Raise more specific errors and include more information (type and number
of arguments, most probable causes of error).
Loading
Loading