Intermittently, when using OpenAI::Client.new(...).responses.stream(...) we will receive a keepalive event: e.g.,{"sequence_number":3,"type":"keepalive"}. We are using Azure OpenAI, so my guess is that these keepalive events are sent to keep the connection open when there's a gap between received events or a larger time-to-first-token (although there is no mention of these events in the Azure documentation of this).
In our code, we have a case statement branching on different types of ResponseStreamEvent:
# Translates events from the OpenAI::Models::Responses::ResponseStreamEvent to StreamResponseEvent
def parse_stream_event(event:)
case event
when OpenAI::Models::Responses::ResponseCreatedEvent
parse_created_event(event:)
when OpenAI::Models::Responses::ResponseTextDeltaEvent
parse_output_text_delta_event(event:)
when OpenAI::Models::Responses::ResponseCompletedEvent
parse_completed_event(event:)
when OpenAI::Models::Responses::ResponseFailedEvent
parse_failed_event(event:)
when OpenAI::Models::Responses::ResponseIncompleteEvent
report_token_usage(response: event.response)
parse_incomplete_event(event:)
when OpenAI::Models::Responses::ResponseErrorEvent
parse_error(event:)
end
end
We are seeing these keepalive events being classified as a ResponseErrorEvent, resulting in our code treating these keepalive events as errors. Looking at the OpenAI::Internal::Type::Union#coerce method, it seems as though it tries to match the best-fit variant but does not enforce type matching the expected value for the variant.
We've since added logic to skip these events if type == 'keepalive' but I wanted to share this in case this is not expected behavior and the logic for Union#coerce should be altered to be more strict
Intermittently, when using
OpenAI::Client.new(...).responses.stream(...)we will receive akeepaliveevent: e.g.,{"sequence_number":3,"type":"keepalive"}. We are using Azure OpenAI, so my guess is that thesekeepaliveevents are sent to keep the connection open when there's a gap between received events or a larger time-to-first-token (although there is no mention of these events in the Azure documentation of this).In our code, we have a
casestatement branching on different types ofResponseStreamEvent:We are seeing these
keepaliveevents being classified as aResponseErrorEvent, resulting in our code treating thesekeepaliveevents as errors. Looking at theOpenAI::Internal::Type::Union#coercemethod, it seems as though it tries to match the best-fit variant but does not enforcetypematching the expected value for the variant.We've since added logic to skip these events if
type == 'keepalive'but I wanted to share this in case this is not expected behavior and the logic forUnion#coerceshould be altered to be more strict