[issue26140] inspect.iscoroutinefunction raises TypeError when checks Mock of function or coroutinefunction

2016-01-17 Thread Hiroyuki Takagi

New submission from Hiroyuki Takagi:

inspect.iscoroutinefunction and asyncio.iscoroutinefunction with patch of 
issue25599 (https://bugs.python.org/issue25599) raise TypeError when used to 
check Mock object which mocks function or coroutinefunction.

How to reproduce:

- For the mock of function

>>> from unittest.mock import Mock
>>> import inspect
>>> def a():...
... 
>>> inspect.iscoroutinefunction(Mock(a))

Expected: False
Actual: 
Traceback (most recent call last):
  File "", line 1, in 
  File ".../cpython/Lib/inspect.py", line 187, in iscoroutinefunction
object.__code__.co_flags & CO_COROUTINE)
TypeError: unsupported operand type(s) for &: 'Mock' and 'int'


- For the mock of coroutine-function

>>> async def b():...
... 
>>> inspect.iscoroutinefunction(Mock(b))

Expected: True
Actual:
Traceback (most recent call last):
  File "", line 1, in 
  File ".../cpython/Lib/inspect.py", line 187, in iscoroutinefunction
object.__code__.co_flags & CO_COROUTINE)
TypeError: unsupported operand type(s) for &: 'Mock' and 'int'


Without the patch of issue25599, asyncio.iscoroutinefunction does not raise 
error and returns Mock object. But I don't think it is expected behavior, as 
discussed in that issue.

I wrote a patch to solve this problem.

--
components: asyncio
files: mock.patch
keywords: patch
messages: 258464
nosy: gvanrossum, haypo, miyakogi, yselivanov
priority: normal
severity: normal
status: open
title: inspect.iscoroutinefunction raises TypeError when checks Mock of 
function or coroutinefunction
type: behavior
versions: Python 3.5
Added file: http://bugs.python.org/file41638/mock.patch

___
Python tracker 
<http://bugs.python.org/issue26140>
___
___
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com



[issue26140] inspect.iscoroutinefunction raises TypeError when checks Mock of function or coroutinefunction

2016-01-18 Thread Hiroyuki Takagi

Hiroyuki Takagi added the comment:

Thank you for review and comment.

Honestly speaking, I couldn't find any other good place to fix it.

One possible solution might be to use isinstance(mock, Mock) in 
iscoroutinefunction, but I don't think it's good for inspect module to add 
special check and depend on unittest.mock. Mocks are usually used only in 
debug/test, but iscoroutinefunction is used in production code. Adding some 
check to iscoroutinefunction only for test is not good for performance (though, 
actually its effect will be very small).

The reasons why I think this behavior should be fixed are,

- Raising error and stopping test is not kind for mock users
- After the patch (issue25599), no mock object can become `True` to 
iscoroutinefunction, which will make it impossible to test the block after 
if-iscoroutinefunction by using mock.


Now, I checked inspect module again, and found one more unexpected behavior 
(not error).

>>> def a(): yield 1
>>> inspect.isgeneratorfunction(a)
True

>>> inspect.isgeneratorfunction(Mock(a))
False

With the patch, inspect.isgeneratorfunction(Mock(a)) returns True.

--

___
Python tracker 
<http://bugs.python.org/issue26140>
___
___
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com



[issue26140] inspect.iscoroutinefunction raises TypeError when checks Mock of function or coroutinefunction

2016-01-19 Thread Hiroyuki Takagi

Hiroyuki Takagi added the comment:

Thank you for reviewing patch.

I wrote test and updated patch. To pass the test, both this patch and 
issue25599's patch are required.

Changes of the patch:
- copy __code__ not only functions but also methods
- add autospec (create_autospec) suppoort

I have completely missed about autospec, thank you for a mention about it.
For autospec, simply copying original __code__ to funcopy makes error on 
existing tests.
That's why I changed the src of exec, but it seems to be quite ad-hoc. It may 
be better to be improved, but I don't have any good idea, sorry.

On the tests of this patch, I wonder if it's better to use assertIs(.., 
True/False) instead of assertTrue/False, since it was one of the problem in 
issue25599.
To apply this change and pass test, need to change asyncio.iscoroutinefunction 
to return bool. The change would be very easy, just update issue25599's patch 
like `return_value = bool(getattr(func, ...`.

--
Added file: http://bugs.python.org/file41664/mock2.patch

___
Python tracker 
<http://bugs.python.org/issue26140>
___
___
Python-bugs-list mailing list
Unsubscribe: 
https://mail.python.org/mailman/options/python-bugs-list/archive%40mail-archive.com