Skip to content

Commit 6aeb2b2

Browse files
Suggest to make implementations of some function always return awaitable (#1295)
Co-authored-by: David Brochart <[email protected]>
1 parent 779874f commit 6aeb2b2

File tree

2 files changed

+56
-0
lines changed

2 files changed

+56
-0
lines changed

ipykernel/kernelbase.py

+52
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,14 @@
5858
from ._version import kernel_protocol_version
5959
from .iostream import OutStream
6060

61+
_AWAITABLE_MESSAGE: str = (
62+
"For consistency across implementations, it is recommended that `{func_name}`"
63+
" either be a coroutine function (`async def`) or return an awaitable object"
64+
" (like an `asyncio.Future`). It might become a requirement in the future."
65+
" Coroutine functions and awaitables have been supported since"
66+
" ipykernel 6.0 (2021). {target} does not seem to return an awaitable"
67+
)
68+
6169

6270
def _accepts_parameters(meth, param_names):
6371
parameters = inspect.signature(meth).parameters
@@ -745,6 +753,12 @@ async def execute_request(self, socket, ident, parent):
745753

746754
if inspect.isawaitable(reply_content):
747755
reply_content = await reply_content
756+
else:
757+
warnings.warn(
758+
_AWAITABLE_MESSAGE.format(func_name="do_execute", target=self.do_execute),
759+
PendingDeprecationWarning,
760+
stacklevel=1,
761+
)
748762

749763
# Flush output before sending the reply.
750764
if sys.stdout is not None:
@@ -805,6 +819,12 @@ async def complete_request(self, socket, ident, parent):
805819
matches = self.do_complete(code, cursor_pos)
806820
if inspect.isawaitable(matches):
807821
matches = await matches
822+
else:
823+
warnings.warn(
824+
_AWAITABLE_MESSAGE.format(func_name="do_complete", target=self.do_complete),
825+
PendingDeprecationWarning,
826+
stacklevel=1,
827+
)
808828

809829
matches = json_clean(matches)
810830
self.session.send(socket, "complete_reply", matches, parent, ident)
@@ -833,6 +853,12 @@ async def inspect_request(self, socket, ident, parent):
833853
)
834854
if inspect.isawaitable(reply_content):
835855
reply_content = await reply_content
856+
else:
857+
warnings.warn(
858+
_AWAITABLE_MESSAGE.format(func_name="do_inspect", target=self.do_inspect),
859+
PendingDeprecationWarning,
860+
stacklevel=1,
861+
)
836862

837863
# Before we send this object over, we scrub it for JSON usage
838864
reply_content = json_clean(reply_content)
@@ -852,6 +878,12 @@ async def history_request(self, socket, ident, parent):
852878
reply_content = self.do_history(**content)
853879
if inspect.isawaitable(reply_content):
854880
reply_content = await reply_content
881+
else:
882+
warnings.warn(
883+
_AWAITABLE_MESSAGE.format(func_name="do_history", target=self.do_history),
884+
PendingDeprecationWarning,
885+
stacklevel=1,
886+
)
855887

856888
reply_content = json_clean(reply_content)
857889
msg = self.session.send(socket, "history_reply", reply_content, parent, ident)
@@ -974,6 +1006,12 @@ async def shutdown_request(self, socket, ident, parent):
9741006
content = self.do_shutdown(parent["content"]["restart"])
9751007
if inspect.isawaitable(content):
9761008
content = await content
1009+
else:
1010+
warnings.warn(
1011+
_AWAITABLE_MESSAGE.format(func_name="do_shutdown", target=self.do_shutdown),
1012+
PendingDeprecationWarning,
1013+
stacklevel=1,
1014+
)
9771015
self.session.send(socket, "shutdown_reply", content, parent, ident=ident)
9781016
# same content, but different msg_id for broadcasting on IOPub
9791017
self._shutdown_message = self.session.msg("shutdown_reply", content, parent)
@@ -998,6 +1036,12 @@ async def is_complete_request(self, socket, ident, parent):
9981036
reply_content = self.do_is_complete(code)
9991037
if inspect.isawaitable(reply_content):
10001038
reply_content = await reply_content
1039+
else:
1040+
warnings.warn(
1041+
_AWAITABLE_MESSAGE.format(func_name="do_is_complete", target=self.do_is_complete),
1042+
PendingDeprecationWarning,
1043+
stacklevel=1,
1044+
)
10011045
reply_content = json_clean(reply_content)
10021046
reply_msg = self.session.send(socket, "is_complete_reply", reply_content, parent, ident)
10031047
self.log.debug("%s", reply_msg)
@@ -1014,6 +1058,14 @@ async def debug_request(self, socket, ident, parent):
10141058
reply_content = self.do_debug_request(content)
10151059
if inspect.isawaitable(reply_content):
10161060
reply_content = await reply_content
1061+
else:
1062+
warnings.warn(
1063+
_AWAITABLE_MESSAGE.format(
1064+
func_name="do_debug_request", target=self.do_debug_request
1065+
),
1066+
PendingDeprecationWarning,
1067+
stacklevel=1,
1068+
)
10171069
reply_content = json_clean(reply_content)
10181070
reply_msg = self.session.send(socket, "debug_reply", reply_content, parent, ident)
10191071
self.log.debug("%s", reply_msg)

pyproject.toml

+4
Original file line numberDiff line numberDiff line change
@@ -190,6 +190,10 @@ filterwarnings= [
190190

191191
# ignore unclosed sqlite in traits
192192
"ignore:unclosed database in <sqlite3.Connection:ResourceWarning",
193+
194+
# ignore deprecated non async during tests:
195+
"always:For consistency across implementations, it is recommended that:PendingDeprecationWarning",
196+
193197
]
194198

195199
[tool.coverage.report]

0 commit comments

Comments
 (0)