Skip to content

Commit d976676

Browse files
committed
Fix error message for methods return type
1 parent 4d792e4 commit d976676

File tree

12 files changed

+68
-65
lines changed

12 files changed

+68
-65
lines changed

Objects/abstract.c

Lines changed: 21 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -129,8 +129,9 @@ PyObject_LengthHint(PyObject *o, Py_ssize_t defaultvalue)
129129
return defaultvalue;
130130
}
131131
if (!PyLong_Check(result)) {
132-
PyErr_Format(PyExc_TypeError, "__length_hint__ must be an integer, not %.100s",
133-
Py_TYPE(result)->tp_name);
132+
PyErr_Format(PyExc_TypeError,
133+
"%T.__length_hint__ must return type int (not %T)",
134+
o, result);
134135
Py_DECREF(result);
135136
return -1;
136137
}
@@ -140,7 +141,9 @@ PyObject_LengthHint(PyObject *o, Py_ssize_t defaultvalue)
140141
return -1;
141142
}
142143
if (res < 0) {
143-
PyErr_Format(PyExc_ValueError, "__length_hint__() should return >= 0");
144+
PyErr_Format(PyExc_ValueError,
145+
"%T.__length_hint__ must return positive int (not %T)",
146+
o, result);
144147
return -1;
145148
}
146149
return res;
@@ -884,8 +887,8 @@ PyObject_Format(PyObject *obj, PyObject *format_spec)
884887

885888
if (result && !PyUnicode_Check(result)) {
886889
PyErr_Format(PyExc_TypeError,
887-
"__format__ must return a str, not %.200s",
888-
Py_TYPE(result)->tp_name);
890+
"%T.__format__ must return type str (not %T)",
891+
obj, result);
889892
Py_SETREF(result, NULL);
890893
goto done;
891894
}
@@ -1418,13 +1421,14 @@ _PyNumber_Index(PyObject *item)
14181421

14191422
if (!PyLong_Check(result)) {
14201423
PyErr_Format(PyExc_TypeError,
1421-
"%T.__index__ returned non-int (type %T)", item, result);
1424+
"%T.__index__ must return type int (not %T)",
1425+
item, result);
14221426
Py_DECREF(result);
14231427
return NULL;
14241428
}
14251429
/* Issue #17576: warn if 'result' not of exact type int. */
14261430
if (PyErr_WarnFormat(PyExc_DeprecationWarning, 1,
1427-
"%T.__index__ returned non-int (type %T). "
1431+
"%T.__index__ must return type int (not %T). "
14281432
"The ability to return an instance of a strict subclass of int "
14291433
"is deprecated, and may be removed in a future version of Python.",
14301434
item, result)) {
@@ -1527,13 +1531,13 @@ PyNumber_Long(PyObject *o)
15271531

15281532
if (!PyLong_Check(result)) {
15291533
PyErr_Format(PyExc_TypeError,
1530-
"%T.__int__ returned non-int (type %T)", o, result);
1534+
"%T.__int__ must return type int (not %T)", o, result);
15311535
Py_DECREF(result);
15321536
return NULL;
15331537
}
15341538
/* Issue #17576: warn if 'result' not of exact type int. */
15351539
if (PyErr_WarnFormat(PyExc_DeprecationWarning, 1,
1536-
"%T.__int__ returned non-int (type %T). "
1540+
"%T.__int__ must return type int (not %T). "
15371541
"The ability to return an instance of a strict subclass of int "
15381542
"is deprecated, and may be removed in a future version of Python.",
15391543
o, result)) {
@@ -1604,13 +1608,14 @@ PyNumber_Float(PyObject *o)
16041608

16051609
if (!PyFloat_Check(res)) {
16061610
PyErr_Format(PyExc_TypeError,
1607-
"%T.__float__ returned non-float (type %T)", o, res);
1611+
"%T.__float__ must return type float (not %T)",
1612+
o, res);
16081613
Py_DECREF(res);
16091614
return NULL;
16101615
}
16111616
/* Issue #26983: warn if 'res' not of exact type float. */
16121617
if (PyErr_WarnFormat(PyExc_DeprecationWarning, 1,
1613-
"%T.__float__ returned non-float (type %T). "
1618+
"%T.__float__ must return type float (not %T). "
16141619
"The ability to return an instance of a strict subclass of float "
16151620
"is deprecated, and may be removed in a future version of Python.",
16161621
o, res)) {
@@ -2429,10 +2434,8 @@ method_output_as_list(PyObject *o, PyObject *meth)
24292434
PyThreadState *tstate = _PyThreadState_GET();
24302435
if (_PyErr_ExceptionMatches(tstate, PyExc_TypeError)) {
24312436
_PyErr_Format(tstate, PyExc_TypeError,
2432-
"%.200s.%U() returned a non-iterable (type %.200s)",
2433-
Py_TYPE(o)->tp_name,
2434-
meth,
2435-
Py_TYPE(meth_output)->tp_name);
2437+
"%T.%U() must return type iterable (not %T)",
2438+
o, meth, meth_output);
24362439
}
24372440
Py_DECREF(meth_output);
24382441
return NULL;
@@ -2812,7 +2815,7 @@ PyObject_GetIter(PyObject *o)
28122815
PyObject *res = (*f)(o);
28132816
if (res != NULL && !PyIter_Check(res)) {
28142817
PyErr_Format(PyExc_TypeError,
2815-
"%T.iter() returned non-iterator of type '%T'",
2818+
"%T.iter() must return type iterator of type '%T'",
28162819
o, res);
28172820
Py_SETREF(res, NULL);
28182821
}
@@ -2832,8 +2835,8 @@ PyObject_GetAIter(PyObject *o) {
28322835
PyObject *it = (*f)(o);
28332836
if (it != NULL && !PyAIter_Check(it)) {
28342837
PyErr_Format(PyExc_TypeError,
2835-
"aiter() returned not an async iterator of type '%.100s'",
2836-
Py_TYPE(it)->tp_name);
2838+
"%T.aiter() must return type async iterator of type '%T'",
2839+
o, it);
28372840
Py_SETREF(it, NULL);
28382841
}
28392842
return it;

Objects/bytesobject.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -567,7 +567,7 @@ format_obj(PyObject *v, const char **pbuf, Py_ssize_t *plen)
567567
return NULL;
568568
if (!PyBytes_Check(result)) {
569569
PyErr_Format(PyExc_TypeError,
570-
"%T.__bytes__ returned non-bytes (type %T)",
570+
"%T.__bytes__ must return type bytes (not %T)",
571571
v, result);
572572
Py_DECREF(result);
573573
return NULL;
@@ -2762,7 +2762,7 @@ bytes_new_impl(PyTypeObject *type, PyObject *x, const char *encoding,
27622762
return NULL;
27632763
if (!PyBytes_Check(bytes)) {
27642764
PyErr_Format(PyExc_TypeError,
2765-
"%T.__bytes__ returned non-bytes (type %T)",
2765+
"%T.__bytes__ must return type bytes (not %T)",
27662766
x, bytes);
27672767
Py_DECREF(bytes);
27682768
return NULL;

Objects/complexobject.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -499,14 +499,14 @@ try_complex_special_method(PyObject *op)
499499
}
500500
if (!PyComplex_Check(res)) {
501501
PyErr_Format(PyExc_TypeError,
502-
"%T.__complex__ returned non-complex (type %T)",
502+
"%T.__complex__ must return type complex (not %T)",
503503
op, res);
504504
Py_DECREF(res);
505505
return NULL;
506506
}
507507
/* Issue #29894: warn if 'res' not of exact type complex. */
508508
if (PyErr_WarnFormat(PyExc_DeprecationWarning, 1,
509-
"%T.__complex__ returned non-complex (type %T). "
509+
"%T.__complex__ must return type complex (not %T). "
510510
"The ability to return an instance of a strict subclass of complex "
511511
"is deprecated, and may be removed in a future version of Python.",
512512
op, res)) {

Objects/fileobject.c

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -66,9 +66,9 @@ PyFile_GetLine(PyObject *f, int n)
6666
}
6767
if (result != NULL && !PyBytes_Check(result) &&
6868
!PyUnicode_Check(result)) {
69+
PyErr_Format(PyExc_TypeError,
70+
"%T.readline() must return type str (not %T)", f, result);
6971
Py_SETREF(result, NULL);
70-
PyErr_SetString(PyExc_TypeError,
71-
"object.readline() returned non-string");
7272
}
7373

7474
if (n < 0 && result != NULL && PyBytes_Check(result)) {
@@ -191,8 +191,8 @@ PyObject_AsFileDescriptor(PyObject *o)
191191
Py_DECREF(fno);
192192
}
193193
else {
194-
PyErr_SetString(PyExc_TypeError,
195-
"fileno() returned a non-integer");
194+
PyErr_Format(PyExc_TypeError,
195+
"%T.fileno() must return type int (not %T)", o, fno);
196196
Py_DECREF(fno);
197197
return -1;
198198
}

Objects/floatobject.c

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -315,16 +315,16 @@ PyFloat_AsDouble(PyObject *op)
315315
if (!PyFloat_CheckExact(res)) {
316316
if (!PyFloat_Check(res)) {
317317
PyErr_Format(PyExc_TypeError,
318-
"%.50s.__float__ returned non-float (type %.50s)",
319-
Py_TYPE(op)->tp_name, Py_TYPE(res)->tp_name);
318+
"%T.__float__ must return type float (not %T)",
319+
op, res);
320320
Py_DECREF(res);
321321
return -1;
322322
}
323323
if (PyErr_WarnFormat(PyExc_DeprecationWarning, 1,
324-
"%.50s.__float__ returned non-float (type %.50s). "
324+
"%T.__float__ must return type float (not %T). "
325325
"The ability to return an instance of a strict subclass of float "
326326
"is deprecated, and may be removed in a future version of Python.",
327-
Py_TYPE(op)->tp_name, Py_TYPE(res)->tp_name)) {
327+
op, res) {
328328
Py_DECREF(res);
329329
return -1;
330330
}

Objects/funcobject.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -556,8 +556,9 @@ func_get_annotation_dict(PyFunctionObject *op)
556556
return NULL;
557557
}
558558
if (!PyDict_Check(ann_dict)) {
559-
PyErr_Format(PyExc_TypeError, "__annotate__ returned non-dict of type '%.100s'",
560-
Py_TYPE(ann_dict)->tp_name);
559+
PyErr_Format(PyExc_TypeError,
560+
"__annotate__ must return type dict of type '%T'",
561+
ann_dict);
561562
Py_DECREF(ann_dict);
562563
return NULL;
563564
}

Objects/genobject.c

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1076,14 +1076,14 @@ _PyCoro_GetAwaitableIter(PyObject *o)
10761076
if (PyCoro_CheckExact(res) || gen_is_coroutine(res)) {
10771077
/* __await__ must return an *iterator*, not
10781078
a coroutine or another awaitable (see PEP 492) */
1079-
PyErr_SetString(PyExc_TypeError,
1080-
"__await__() returned a coroutine");
1079+
PyErr_Format(PyExc_TypeError,
1080+
"%T.__await__ returned a coroutine", o);
10811081
Py_CLEAR(res);
10821082
} else if (!PyIter_Check(res)) {
10831083
PyErr_Format(PyExc_TypeError,
1084-
"__await__() returned non-iterator "
1085-
"of type '%.100s'",
1086-
Py_TYPE(res)->tp_name);
1084+
"%T.__await__ must return type iterator "
1085+
"of type '%T'",
1086+
o, res);
10871087
Py_CLEAR(res);
10881088
}
10891089
}

Objects/iterobject.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -342,8 +342,9 @@ anextawaitable_getiter(anextawaitableobject *obj)
342342
}
343343
Py_SETREF(awaitable, new_awaitable);
344344
if (!PyIter_Check(awaitable)) {
345-
PyErr_SetString(PyExc_TypeError,
346-
"__await__ returned a non-iterable");
345+
PyErr_Format(PyExc_TypeError,
346+
"%T.__await__ must return type iterable (not %T)",
347+
obj, awaitable);
347348
Py_DECREF(awaitable);
348349
return NULL;
349350
}

Objects/moduleobject.c

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1258,8 +1258,10 @@ module_get_annotations(PyObject *self, void *Py_UNUSED(ignored))
12581258
return NULL;
12591259
}
12601260
if (!PyDict_Check(annotations)) {
1261-
PyErr_Format(PyExc_TypeError, "__annotate__ returned non-dict of type '%.100s'",
1262-
Py_TYPE(annotations)->tp_name);
1261+
PyErr_Format(PyExc_TypeError,
1262+
"%T.__annotate__ must return type dict "
1263+
"of type '%T'",
1264+
self, annotations);
12631265
Py_DECREF(annotate);
12641266
Py_DECREF(annotations);
12651267
Py_DECREF(dict);

Objects/object.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -779,7 +779,7 @@ PyObject_Repr(PyObject *v)
779779
}
780780
if (!PyUnicode_Check(res)) {
781781
_PyErr_Format(tstate, PyExc_TypeError,
782-
"%T.__repr__ returned non-string (type %T)", v, res);
782+
"%T.__repr__ must return type str (not %T)", v, res);
783783
Py_DECREF(res);
784784
return NULL;
785785
}
@@ -821,7 +821,7 @@ PyObject_Str(PyObject *v)
821821
}
822822
if (!PyUnicode_Check(res)) {
823823
_PyErr_Format(tstate, PyExc_TypeError,
824-
"%T.__str__ returned non-string (type %T)", v, res);
824+
"%T.__str__ must return type str (not %T)", v, res);
825825
Py_DECREF(res);
826826
return NULL;
827827
}
@@ -876,7 +876,7 @@ PyObject_Bytes(PyObject *v)
876876
return NULL;
877877
if (!PyBytes_Check(result)) {
878878
PyErr_Format(PyExc_TypeError,
879-
"%T.__bytes__ returned non-bytes (type %T)",
879+
"%T.__bytes__ must return type bytes (not %T)",
880880
v, result);
881881
Py_DECREF(result);
882882
return NULL;

0 commit comments

Comments
 (0)