Commit ·
0da76bb
1
Parent(s): 433bff2
tentative tool call support
Browse files- app/openai_handler.py +49 -18
app/openai_handler.py
CHANGED
|
@@ -245,30 +245,61 @@ class OpenAIDirectHandler:
|
|
| 245 |
# print(f"DEBUG: Chunk {chunk_count} - Processed content: '{processed_content}', Reasoning: '{current_reasoning[:50]}...' if len(current_reasoning) > 50 else '{current_reasoning}'")
|
| 246 |
|
| 247 |
# Send chunks for both reasoning and content as they arrive
|
| 248 |
-
|
| 249 |
-
|
| 250 |
-
|
|
|
|
|
|
|
| 251 |
if current_reasoning:
|
| 252 |
-
|
| 253 |
-
|
| 254 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 255 |
|
| 256 |
-
# If we have regular content, send it
|
| 257 |
if processed_content:
|
| 258 |
-
|
| 259 |
-
|
| 260 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 261 |
has_sent_content = True
|
| 262 |
|
| 263 |
-
#
|
| 264 |
-
|
| 265 |
-
|
| 266 |
-
|
| 267 |
-
|
| 268 |
-
|
| 269 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
| 270 |
yielded_data_str = f"data: {json.dumps(chunk_as_dict)}\n\n"
|
| 271 |
-
print(f"DEBUG_OPENAI_STREAM: Chunk {chunk_count} - Yielding (original delta
|
| 272 |
yield yielded_data_str
|
| 273 |
else:
|
| 274 |
# Yield chunks without choices too (they might contain metadata)
|
|
|
|
| 245 |
# print(f"DEBUG: Chunk {chunk_count} - Processed content: '{processed_content}', Reasoning: '{current_reasoning[:50]}...' if len(current_reasoning) > 50 else '{current_reasoning}'")
|
| 246 |
|
| 247 |
# Send chunks for both reasoning and content as they arrive
|
| 248 |
+
# Kilo Code: Revised payload construction
|
| 249 |
+
original_choice = chunk_as_dict['choices'][0]
|
| 250 |
+
original_finish_reason = original_choice.get('finish_reason')
|
| 251 |
+
original_usage = original_choice.get('usage')
|
| 252 |
+
|
| 253 |
if current_reasoning:
|
| 254 |
+
reasoning_delta = {'reasoning_content': current_reasoning}
|
| 255 |
+
reasoning_payload = {
|
| 256 |
+
"id": chunk_as_dict["id"], "object": chunk_as_dict["object"],
|
| 257 |
+
"created": chunk_as_dict["created"], "model": chunk_as_dict["model"],
|
| 258 |
+
"choices": [{"index": 0, "delta": reasoning_delta, "finish_reason": None}]
|
| 259 |
+
}
|
| 260 |
+
yielded_data_str = f"data: {json.dumps(reasoning_payload)}\n\n"
|
| 261 |
+
print(f"DEBUG_OPENAI_STREAM: Chunk {chunk_count} - Yielding REASONING: {yielded_data_str.strip()}")
|
| 262 |
+
yield yielded_data_str
|
| 263 |
|
|
|
|
| 264 |
if processed_content:
|
| 265 |
+
content_delta = {'content': processed_content}
|
| 266 |
+
# Determine if this processed_content chunk should carry the original finish_reason and usage.
|
| 267 |
+
# It should if the reasoning processor is NOT inside a tag after this,
|
| 268 |
+
# meaning this processed_content is the final part of any tagged content from original_content_from_delta.
|
| 269 |
+
finish_reason_for_this_content_delta = None
|
| 270 |
+
usage_for_this_content_delta = None
|
| 271 |
+
|
| 272 |
+
if original_finish_reason and not reasoning_processor.inside_tag:
|
| 273 |
+
finish_reason_for_this_content_delta = original_finish_reason
|
| 274 |
+
if original_usage:
|
| 275 |
+
usage_for_this_content_delta = original_usage
|
| 276 |
+
|
| 277 |
+
content_payload = {
|
| 278 |
+
"id": chunk_as_dict["id"], "object": chunk_as_dict["object"],
|
| 279 |
+
"created": chunk_as_dict["created"], "model": chunk_as_dict["model"],
|
| 280 |
+
"choices": [{"index": 0, "delta": content_delta, "finish_reason": finish_reason_for_this_content_delta}]
|
| 281 |
+
}
|
| 282 |
+
if usage_for_this_content_delta:
|
| 283 |
+
content_payload['choices'][0]['usage'] = usage_for_this_content_delta
|
| 284 |
+
|
| 285 |
+
yielded_data_str = f"data: {json.dumps(content_payload)}\n\n"
|
| 286 |
+
print(f"DEBUG_OPENAI_STREAM: Chunk {chunk_count} - Yielding CONTENT: {yielded_data_str.strip()}")
|
| 287 |
+
yield yielded_data_str
|
| 288 |
has_sent_content = True
|
| 289 |
|
| 290 |
+
# If neither reasoning nor processed_content was generated from a non-empty original content,
|
| 291 |
+
# it implies the original content might have been just a tag or something consumed entirely.
|
| 292 |
+
# In this case, do nothing more for this path; the original chunk's other properties (like finish_reason if content was empty) are handled below.
|
| 293 |
+
|
| 294 |
+
elif original_finish_reason: # Original delta had no content, but had a finish_reason
|
| 295 |
+
# This case handles chunks that are purely for signaling stream end or other non-content states.
|
| 296 |
+
yielded_data_str = f"data: {json.dumps(chunk_as_dict)}\n\n" # Yield original chunk as is
|
| 297 |
+
print(f"DEBUG_OPENAI_STREAM: Chunk {chunk_count} - Yielding (original delta no content, but has finish_reason): {yielded_data_str.strip()}")
|
| 298 |
+
yield yielded_data_str
|
| 299 |
+
# If original delta had no content and no finish_reason, it's an empty delta, yield as is.
|
| 300 |
+
elif not content and not original_finish_reason : # Kilo Code: Added this condition
|
| 301 |
yielded_data_str = f"data: {json.dumps(chunk_as_dict)}\n\n"
|
| 302 |
+
print(f"DEBUG_OPENAI_STREAM: Chunk {chunk_count} - Yielding (original delta empty): {yielded_data_str.strip()}")
|
| 303 |
yield yielded_data_str
|
| 304 |
else:
|
| 305 |
# Yield chunks without choices too (they might contain metadata)
|