Index: Objects/descrobject.c =================================================================== --- Objects/descrobject.c (revision 72178) +++ Objects/descrobject.c (working copy) @@ -1288,9 +1288,23 @@ if ((doc == NULL || doc == Py_None) && get != NULL) { PyObject *get_doc = PyObject_GetAttrString(get, "__doc__"); if (get_doc != NULL) { - Py_XDECREF(prop->prop_doc); - prop->prop_doc = get_doc; /* get_doc already INCREF'd by GetAttr */ - prop->getter_doc = 1; + /* get_doc already INCREF'd by GetAttr */ + if (Py_TYPE(self)==&PyProperty_Type) { + Py_XDECREF(prop->prop_doc); + prop->prop_doc = get_doc; + prop->getter_doc = 1; + } else { + /* Put __doc__ in dict of the subclass instance instead, + otherwise it gets shadowed by class's __doc__. */ + if (PyObject_SetAttrString(self, "__doc__", get_doc) != 0) + { + Py_XDECREF(get); + Py_XDECREF(set); + Py_XDECREF(del); + Py_XDECREF(doc); + return -1; + } + } } else { PyErr_Clear(); } Index: Lib/test/test_property.py =================================================================== --- Lib/test/test_property.py (revision 72149) +++ Lib/test/test_property.py (working copy) @@ -91,8 +91,30 @@ self.assertEqual(base.__class__.spam.__doc__, "spam spam spam") self.assertEqual(sub.__class__.spam.__doc__, "spam spam spam") +class PropertySub(property): + """This is a subclass of property""" + + +# Issue 5890: subclasses of property do not preserve method __doc__ strings +class PSBaseClass(object): + + @PropertySub + def spam(self): + """spam wrapped in a property subclass""" + return 1 + + +class PropertySubclassTests(unittest.TestCase): + + def test_docstring(self): + base = PSBaseClass() + self.assertEqual( + base.__class__.spam.__doc__, + "spam wrapped in a property subclass") + + def test_main(): - run_unittest(PropertyTests) + run_unittest(PropertyTests, PropertySubclassTests) if __name__ == '__main__': test_main()