Skip to content

v1.15.0 breaking checks using Coroutine #18634

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
gabrielcocenza opened this issue Feb 7, 2025 · 2 comments
Closed

v1.15.0 breaking checks using Coroutine #18634

gabrielcocenza opened this issue Feb 7, 2025 · 2 comments
Labels
bug mypy got something wrong

Comments

@gabrielcocenza
Copy link

gabrielcocenza commented Feb 7, 2025

Bug Report

Since the new release, one of the projects that I use mypy is failing for the type Coroutine.

The code is like this:

from typing import Coroutine,

def compare_step_coroutines(
    coro1: Optional[Coroutine], coro2: Optional[Coroutine]
) -> bool:
    """Compare two coroutines.

    :param coro1: coroutine to compare
    :type coro1: Optional[coroutine]
    :param coro2: coroutine to compare
    :type coro2: Optional[coroutine]
    :return: True if coroutines are equal
    :rtype: bool
    """
    if coro1 is None or coro2 is None:
        # compare two None or one None and one Coroutine
        return coro1 == coro2

    return (
        # check if same coroutine was used
        coro1.cr_code == coro2.cr_code
        # check coroutine arguments
        and inspect.getcoroutinelocals(coro1) == inspect.getcoroutinelocals(coro2)
    )
lint: commands[2]> mypy --install-types --non-interactive .
cou/steps/__init__.py:48: error: "Coroutine[Any, Any, Any]" has no attribute "cr_code"  [attr-defined]

With this new release Coroutine doesn't recognize cr_code as a valid property.
I've tried to change to use types.CoroutineType and fixed for this issue, but errors started showing on other parts of the code. mypy still consider as Coroutine. E.g:

class Foo
def __init__(self, coro: Optional[types.CoroutineType] = None):
    self._coro: Optional[[types.CoroutineType] = coro

foo = Foo(coro=my_coro_func)

async def my_coro_func():
    return None
Argument "coro" to "Foo" has incompatible type "Coroutine[Any, Any, None]"; expected "CoroutineType[Any, Any, Any] | None"  [arg-type] note: Maybe you forgot to use "await"?

Basically Coroutine cannot be used anymore like before and I don't see a possible workaround without ignoring the line that is complaining or pinning mypy to use a version < 1.15.0

Your Environment

  • Mypy version used: 1.15.0
  • Mypy command-line flags: mypy --install-types --non-interactive .
  • Mypy configuration options from mypy.ini (and other config files):
warn_unused_ignores = true
warn_unused_configs = true
warn_unreachable = true
disallow_untyped_defs = true
ignore_missing_imports = true
exclude = [
    ".eggs",
    ".git",
    ".tox",
    ".venv",
    ".build",
    "build",
    "lib",
    "report",
    "tests",
    "docs"
]
  • Python version used:3.12
@gabrielcocenza gabrielcocenza added the bug mypy got something wrong label Feb 7, 2025
gabrielcocenza added a commit to gabrielcocenza/charmed-openstack-upgrader-1 that referenced this issue Feb 7, 2025
Since the new release of the new mypy version (1.15.0), our lint
started failing. The bug discription can be found here:
- python/mypy#18634

I propose we pin the version to lower than the new release until
the upstream code fix it.
@A5rocks
Copy link
Collaborator

A5rocks commented Feb 7, 2025

This is intentional. You can have coroutines without cr_code. This works:

from typing import Coroutine

def compare_step_coroutines(
    coro1: Coroutine, coro2: Coroutine
) -> bool:
    assert hasattr(coro1, "cr_code")
    assert hasattr(coro2, "cr_code")
    return coro1.cr_code == coro2.cr_code

Comment I left on typeshed for more information: python/typeshed#10816 (comment)

@A5rocks A5rocks closed this as not planned Won't fix, can't repro, duplicate, stale Feb 7, 2025
@A5rocks
Copy link
Collaborator

A5rocks commented Feb 7, 2025

Note of course that the more correct thing to check is isinstance(coro, types.CoroutineType):

from typing import Coroutine
from types import CoroutineType

def test1(
    coro: Coroutine
) -> None:
    assert isinstance(coro, CoroutineType)
    reveal_type(coro.cr_code)  # N: Revealed type is "types.CodeType"

def test2(
    coro: Coroutine
) -> None:
    assert hasattr(coro, "cr_code")
    reveal_type(coro.cr_code)  # N: Revealed type is "Any"

gabrielcocenza added a commit to gabrielcocenza/charmed-openstack-upgrader-1 that referenced this issue Feb 10, 2025
Since the new release of the new mypy version (1.15.0), our lint
started failing. The bug discription can be found here:
- python/mypy#18634

Until mypy start returning CoroutineType for async functions,
we need to ensure that Coroutine has `cr_code`:
- python/mypy#18635
gabrielcocenza added a commit to gabrielcocenza/charmed-openstack-upgrader-1 that referenced this issue Feb 10, 2025
Since the new release of the new mypy version (1.15.0), our lint
started failing. The bug discription can be found here:
- python/mypy#18634

Until mypy start returning CoroutineType for async functions,
we need to ensure that Coroutine has `cr_code`:
- python/mypy#18635
samuelallan72 pushed a commit to canonical/charmed-openstack-upgrader that referenced this issue Feb 10, 2025
Since the new release of the new mypy version (1.15.0), our lint
started failing. The bug discription can be found here:
- python/mypy#18634

Until mypy start returning CoroutineType for async functions,
we need to ensure that Coroutine has `cr_code`:
- python/mypy#18635
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug mypy got something wrong
Projects
None yet
Development

No branches or pull requests

2 participants