Fix the frame reader for a closed socket

Review the AI's codeEasy10 min

Your task

Your client reads length-prefixed messages from a socket. When the peer closed mid-stream, recv kept returning empty results and the loop spun at 100% CPU. The fix stops at end of stream and keeps only the messages that arrived whole.

An assistant wrote drain_framed_stream(chunks). It is in the editor. It has a bug. Find it and fix it.

Input and output:

  • chunks: the strings successive recv calls returned, in order. An empty string means the peer closed the connection.
  • Return the bodies of the complete messages, in order.

Rules the tests check:

  • Join the chunks in order up to the first empty string. Ignore that chunk and everything after it.
  • A message is a 4-character header, then a body. The header is the body's length in decimal, padded with zeros, such as 0005.
  • Read messages from the start of the joined text. Stop when fewer than 4 characters remain for a header, or the header is not 4 ASCII digits.
  • Also stop when fewer characters remain than the header says. A message cut short by the close is truncated data, not a message, so it is not returned.
  • A header of 0000 is a complete message with an empty body.

Examples

drain_framed_stream(chunks: list[str]) -> list[str]
Example 1
Inputdrain_framed_stream(["0003abc0003def"])
Output["abc", "def"]
Example 2
Inputdrain_framed_stream(["0005hello", "", "0005world"])
Output["hello"]
Example 3
Inputdrain_framed_stream(["00"])
Output[]