Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 17 additions & 8 deletions ipykernel/kernelbase.py
Original file line number Diff line number Diff line change
Expand Up @@ -883,7 +883,7 @@ async def comm_info_request(self, stream, ident, parent):
msg = self.session.send(stream, "comm_info_reply", reply_content, parent, ident)
self.log.debug("%s", msg)

def _send_interupt_children(self):
def _send_interrupt_children(self):
if os.name == "nt":
self.log.error("Interrupt message not supported on Windows")
else:
Expand All @@ -894,18 +894,27 @@ def _send_interupt_children(self):
if pgid and pgid == pid and hasattr(os, "killpg"):
try:
os.killpg(pgid, SIGINT)
return
except OSError:
pass
try:
os.kill(pid, SIGINT)
raise
else:
os.kill(pid, SIGINT)
except OSError:
pass

async def interrupt_request(self, stream, ident, parent):
"""Handle an interrupt request."""
self._send_interupt_children()
content = parent["content"]
content: t.Dict[str, t.Any] = {"status": "ok"}
try:
self._send_interrupt_children()
except OSError as err:
import traceback

content = {
"status": "error",
"traceback": traceback.format_stack(),
"ename": str(type(err).__name__),
"evalue": str(err),
}

self.session.send(stream, "interrupt_reply", content, parent, ident=ident)
return

Expand Down
2 changes: 1 addition & 1 deletion ipykernel/tests/conftest.py
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,7 @@ async def _wait_for_msg(self):
_, msg = self.session.feed_identities(self._reply)
return self.session.deserialize(msg)

def _send_interupt_children(self):
def _send_interrupt_children(self):
# override to prevent deadlock
pass

Expand Down
15 changes: 14 additions & 1 deletion ipykernel/tests/test_ipkernel_direct.py
Original file line number Diff line number Diff line change
Expand Up @@ -90,8 +90,21 @@ async def test_comm_info_request(ipkernel):


async def test_direct_interrupt_request(ipkernel):
reply = await ipkernel.test_shell_message("interrupt_request", {})
reply = await ipkernel.test_control_message("interrupt_request", {})
assert reply["header"]["msg_type"] == "interrupt_reply"
assert reply["content"] == {"status": "ok"}

# test failure on interrupt request
def raiseOSError():
raise OSError("evalue")

ipkernel._send_interrupt_children = raiseOSError
reply = await ipkernel.test_control_message("interrupt_request", {})
assert reply["header"]["msg_type"] == "interrupt_reply"
assert reply["content"]["status"] == "error"
assert reply["content"]["ename"] == "OSError"
assert reply["content"]["evalue"] == "evalue"
assert len(reply["content"]["traceback"]) > 0


# TODO: this causes deadlock
Expand Down
19 changes: 16 additions & 3 deletions ipykernel/tests/test_kernel_direct.py
Original file line number Diff line number Diff line change
Expand Up @@ -69,8 +69,21 @@ async def test_comm_info_request(kernel):


async def test_direct_interrupt_request(kernel):
reply = await kernel.test_shell_message("interrupt_request", {})
reply = await kernel.test_control_message("interrupt_request", {})
assert reply["header"]["msg_type"] == "interrupt_reply"
assert reply["content"] == {"status": "ok"}

# test failure on interrupt request
def raiseOSError():
raise OSError("evalue")

kernel._send_interrupt_children = raiseOSError
reply = await kernel.test_control_message("interrupt_request", {})
assert reply["header"]["msg_type"] == "interrupt_reply"
assert reply["content"]["status"] == "error"
assert reply["content"]["ename"] == "OSError"
assert reply["content"]["evalue"] == "evalue"
assert len(reply["content"]["traceback"]) > 0


async def test_direct_shutdown_request(kernel):
Expand Down Expand Up @@ -145,8 +158,8 @@ async def test_connect_request(kernel):
await kernel.connect_request(kernel.shell_stream, "foo", {})


async def test_send_interupt_children(kernel):
kernel._send_interupt_children()
async def test_send_interrupt_children(kernel):
kernel._send_interrupt_children()


# TODO: this causes deadlock
Expand Down