Compare commits

...

17 Commits

Author SHA1 Message Date
David Robertson
6554988888 Update mypy-zope commit ID 2023-03-27 12:31:23 +01:00
David Robertson
0c09fccab1 Merge remote-tracking branch 'origin/develop' into dmr/test-mypy-zope-92 2023-03-27 12:26:38 +01:00
David Robertson
f031e406d7 Include mypy-zope test file verbatim 2023-03-27 12:23:05 +01:00
David Robertson
af0145bf27 wip 10 2023-03-23 15:09:11 +00:00
David Robertson
baca8eb43e wip 9 2023-03-23 15:04:21 +00:00
David Robertson
d4a608e8bb wip 8 2023-03-23 15:03:47 +00:00
David Robertson
c3aa80ca9d wip 7 2023-03-23 15:02:32 +00:00
David Robertson
9b985cf8a8 wip 6 2023-03-23 14:58:38 +00:00
David Robertson
ecc1084654 WIP 5 2023-03-23 14:55:32 +00:00
David Robertson
af2f251ace WIP 4 2023-03-23 14:47:46 +00:00
David Robertson
b306fa579d MWE WIP 3 2023-03-23 14:45:12 +00:00
David Robertson
a7636881cc MWE WIP 2 2023-03-23 14:42:13 +00:00
David Robertson
31b5b619c9 MWE WIP 2023-03-23 14:38:08 +00:00
David Robertson
df8e0b9dbc Try to reproduce MWE 2023-03-23 14:35:57 +00:00
David Robertson
0df5d132e7 Changelog 2023-03-23 13:54:19 +00:00
David Robertson
024c8df013 Revert checked_cast changes 2023-03-23 13:54:19 +00:00
David Robertson
5830b7a986 Try the mypy-zope branch 2023-03-23 13:19:27 +00:00
9 changed files with 102 additions and 29 deletions

1
changelog.d/15313.misc Normal file
View File

@@ -0,0 +1 @@
Dummy changelog.

18
poetry.lock generated
View File

@@ -1520,24 +1520,28 @@ files = [
[[package]]
name = "mypy-zope"
version = "0.9.1"
version = "0.9.1.dev0"
description = "Plugin for mypy to support zope interfaces"
category = "dev"
optional = false
python-versions = "*"
files = [
{file = "mypy-zope-0.9.1.tar.gz", hash = "sha256:4c87dbc71fec35f6533746ecdf9d400cd9281338d71c16b5676bb5ed00a97ca2"},
{file = "mypy_zope-0.9.1-py3-none-any.whl", hash = "sha256:733d4399affe9e61e332ce9c4049418d6775c39b473e4b9f409d51c207c1b71a"},
]
files = []
develop = false
[package.dependencies]
mypy = ">=1.0.0,<1.1.0"
mypy = "1.0.0"
"zope.interface" = "*"
"zope.schema" = "*"
[package.extras]
test = ["lxml", "pytest (>=4.6)", "pytest-cov"]
[package.source]
type = "git"
url = "https://github.com/Shoobx/mypy-zope.git"
reference = "fix-unreachable"
resolved_reference = "282269e484cdece7aa024639f763927015cfdac5"
[[package]]
name = "myst-parser"
version = "1.0.0"
@@ -3426,4 +3430,4 @@ user-search = ["pyicu"]
[metadata]
lock-version = "2.0"
python-versions = "^3.7.1"
content-hash = "0a1dd4be3dff3c8cc71bd57a4eb48e1d92f155db7230e61fbb54f8af03619509"
content-hash = "6991931764c913db1be84bc4c684bcf8b9d1855d49a297f21c1a56a5119dc68a"

View File

@@ -315,7 +315,8 @@ ruff = "0.0.252"
# Typechecking
mypy = "*"
mypy-zope = "*"
mypy-zope = {git = "https://github.com/Shoobx/mypy-zope.git", rev = "fix-unreachable"}
types-bleach = ">=4.1.0"
types-commonmark = ">=0.9.2"
types-jsonschema = ">=3.2.0"
@@ -350,7 +351,6 @@ towncrier = ">=18.6.0rc1"
# Used for checking the Poetry lockfile
tomli = ">=1.2.3"
# Dependencies for building the development documentation
[tool.poetry.group.dev-docs]
optional = true

View File

@@ -0,0 +1,27 @@
from typing import Optional
from zope.interface import Interface, implementer
class IFoo(Interface):
pass
@implementer(IFoo)
class BaseFoo:
pass
class ChildFoo(BaseFoo):
pass
class IFooFactory(Interface):
def build() -> Optional[IFoo]:
pass
def build_and_use_foo(client_factory: IFooFactory) -> None:
client_protocol = client_factory.build()
assert isinstance(client_protocol, ChildFoo)
print("Hello")

View File

@@ -63,7 +63,7 @@ from tests.http import (
get_test_ca_cert_file,
)
from tests.server import FakeTransport, ThreadedMemoryReactorClock
from tests.utils import checked_cast, default_config
from tests.utils import default_config
logger = logging.getLogger(__name__)
@@ -147,9 +147,8 @@ class MatrixFederationAgentTests(unittest.TestCase):
# Normally this would be done by the TCP socket code in Twisted, but we are
# stubbing that out here.
# NB: we use a checked_cast here to workaround https://github.com/Shoobx/mypy-zope/issues/91)
client_protocol = checked_cast(
_WrappingProtocol, client_factory.buildProtocol(dummy_address)
)
client_protocol = client_factory.buildProtocol(dummy_address)
assert isinstance(client_protocol, _WrappingProtocol)
client_protocol.makeConnection(
FakeTransport(server_protocol, self.reactor, client_protocol)
)
@@ -467,7 +466,8 @@ class MatrixFederationAgentTests(unittest.TestCase):
assert isinstance(proxy_server_transport, FakeTransport)
client_protocol = proxy_server_transport.other
assert isinstance(client_protocol, Protocol)
c2s_transport = checked_cast(FakeTransport, client_protocol.transport)
c2s_transport = client_protocol.transport
assert isinstance(c2s_transport, FakeTransport)
c2s_transport.other = server_ssl_protocol
self.reactor.advance(0)

View File

@@ -43,7 +43,6 @@ from tests.http import (
)
from tests.server import FakeTransport, ThreadedMemoryReactorClock
from tests.unittest import TestCase
from tests.utils import checked_cast
logger = logging.getLogger(__name__)
@@ -645,7 +644,8 @@ class MatrixFederationAgentTests(TestCase):
assert isinstance(proxy_server_transport, FakeTransport)
client_protocol = proxy_server_transport.other
assert isinstance(client_protocol, Protocol)
c2s_transport = checked_cast(FakeTransport, client_protocol.transport)
c2s_transport = client_protocol.transport
assert isinstance(c2s_transport, FakeTransport)
c2s_transport.other = server_ssl_protocol
self.reactor.advance(0)
@@ -763,9 +763,12 @@ class MatrixFederationAgentTests(TestCase):
# https://github.com/Shoobx/mypy-zope/issues/91 .
# We also double-checked these casts at runtime (test-time) because I found it
# quite confusing to deduce these types in the first place!
s2c_transport = checked_cast(FakeTransport, proxy_server.transport)
client_protocol = checked_cast(_WrappingProtocol, s2c_transport.other)
c2s_transport = checked_cast(FakeTransport, client_protocol.transport)
s2c_transport = proxy_server.transport
assert isinstance(s2c_transport, FakeTransport)
client_protocol = s2c_transport.other
assert isinstance(client_protocol, _WrappingProtocol)
c2s_transport = client_protocol.transport
assert isinstance(c2s_transport, FakeTransport)
# the FakeTransport is async, so we need to pump the reactor
self.reactor.advance(0)
@@ -825,7 +828,8 @@ class MatrixFederationAgentTests(TestCase):
@patch.dict(os.environ, {"http_proxy": "proxy.com:8888"})
def test_proxy_with_no_scheme(self) -> None:
http_proxy_agent = ProxyAgent(self.reactor, use_proxy=True)
proxy_ep = checked_cast(HostnameEndpoint, http_proxy_agent.http_proxy_endpoint)
proxy_ep = http_proxy_agent.http_proxy_endpoint
assert isinstance(proxy_ep, HostnameEndpoint)
self.assertEqual(proxy_ep._hostStr, "proxy.com")
self.assertEqual(proxy_ep._port, 8888)
@@ -837,14 +841,16 @@ class MatrixFederationAgentTests(TestCase):
@patch.dict(os.environ, {"http_proxy": "http://proxy.com:8888"})
def test_proxy_with_http_scheme(self) -> None:
http_proxy_agent = ProxyAgent(self.reactor, use_proxy=True)
proxy_ep = checked_cast(HostnameEndpoint, http_proxy_agent.http_proxy_endpoint)
proxy_ep = http_proxy_agent.http_proxy_endpoint
assert isinstance(proxy_ep, HostnameEndpoint)
self.assertEqual(proxy_ep._hostStr, "proxy.com")
self.assertEqual(proxy_ep._port, 8888)
@patch.dict(os.environ, {"http_proxy": "https://proxy.com:8888"})
def test_proxy_with_https_scheme(self) -> None:
https_proxy_agent = ProxyAgent(self.reactor, use_proxy=True)
proxy_ep = checked_cast(_WrapperEndpoint, https_proxy_agent.http_proxy_endpoint)
proxy_ep = https_proxy_agent.http_proxy_endpoint
assert isinstance(proxy_ep, _WrapperEndpoint)
self.assertEqual(proxy_ep._wrappedEndpoint._hostStr, "proxy.com")
self.assertEqual(proxy_ep._wrappedEndpoint._port, 8888)

30
tests/isinstance_impl.py Normal file
View File

@@ -0,0 +1,30 @@
# Per https://github.com/Shoobx/mypy-zope/pull/92#issuecomment-1483266683
from typing import Optional
from zope.interface import implementer, Interface
class IFoo(Interface):
...
@implementer(IFoo)
class MyFoo:
...
def make_foo() -> Optional[IFoo]:
return MyFoo()
x = make_foo()
reveal_type(x)
assert isinstance(x, MyFoo)
# The code below should not be considered unreachable
print("hello")
"""
<output>
isinstance_impl.py:19: note: Revealed type is "Union[__main__.IFoo, None]"
</output>
"""

View File

@@ -21,7 +21,6 @@ from synapse.logging import RemoteHandler
from tests.logging import LoggerCleanupMixin
from tests.server import FakeTransport, get_clock
from tests.unittest import TestCase
from tests.utils import checked_cast
def connect_logging_client(
@@ -57,7 +56,8 @@ class RemoteHandlerTestCase(LoggerCleanupMixin, TestCase):
client, server = connect_logging_client(self.reactor, 0)
# Trigger data being sent
client_transport = checked_cast(FakeTransport, client.transport)
client_transport = client.transport
assert isinstance(client_transport, FakeTransport)
client_transport.flush()
# One log message, with a single trailing newline
@@ -90,7 +90,8 @@ class RemoteHandlerTestCase(LoggerCleanupMixin, TestCase):
# Allow the reconnection
client, server = connect_logging_client(self.reactor, 0)
client_transport = checked_cast(FakeTransport, client.transport)
client_transport = client.transport
assert isinstance(client_transport, FakeTransport)
client_transport.flush()
# Only the 7 infos made it through, the debugs were elided
@@ -124,7 +125,8 @@ class RemoteHandlerTestCase(LoggerCleanupMixin, TestCase):
# Allow the reconnection
client, server = connect_logging_client(self.reactor, 0)
client_transport = checked_cast(FakeTransport, client.transport)
client_transport = client.transport
assert isinstance(client_transport, FakeTransport)
client_transport.flush()
# The 10 warnings made it through, the debugs and infos were elided
@@ -149,7 +151,8 @@ class RemoteHandlerTestCase(LoggerCleanupMixin, TestCase):
# Allow the reconnection
client, server = connect_logging_client(self.reactor, 0)
client_transport = checked_cast(FakeTransport, client.transport)
client_transport = client.transport
assert isinstance(client_transport, FakeTransport)
client_transport.flush()
# The first five and last five warnings made it through, the debugs and

View File

@@ -82,7 +82,7 @@ from tests.server import (
)
from tests.test_utils import event_injection, setup_awaitable_errors
from tests.test_utils.logging_setup import setup_logging
from tests.utils import checked_cast, default_config, setupdb
from tests.utils import default_config, setupdb
setupdb()
setup_logging()
@@ -296,9 +296,11 @@ class HomeserverTestCase(TestCase):
from tests.rest.client.utils import RestHelper
reactor = self.hs.get_reactor()
assert isinstance(reactor, MemoryReactorClock)
self.helper = RestHelper(
self.hs,
checked_cast(MemoryReactorClock, self.hs.get_reactor()),
reactor,
self.site,
getattr(self, "user_id", None),
)