-
Notifications
You must be signed in to change notification settings - Fork 2k
[WIP] support for OpenAI Responses API and image gen #8331
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -41,10 +41,26 @@ def pretty_print_history(history, n: int = 1): | |
else: | ||
image_str = f"<image_url: {c['image_url']['url']}>" | ||
print(_blue(image_str.strip())) | ||
elif c["type"] == "input_audio": | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. this got lost in an earlier PR, adding back in |
||
audio_format = c["input_audio"]["format"] | ||
len_audio = len(c["input_audio"]["data"]) | ||
audio_str = f"<audio format='{audio_format}' base64-encoded, length={len_audio}>" | ||
print(_blue(audio_str.strip())) | ||
print("\n") | ||
|
||
print(_red("Response:")) | ||
print(_green(outputs[0].strip())) | ||
out = outputs[0] | ||
if isinstance(out, str): | ||
print(_green(out.strip())) | ||
elif hasattr(out, "result") and isinstance(out.result, str): | ||
b64 = out.result | ||
if b64.startswith("data:"): | ||
head, b64data = b64.split(",", 1) | ||
print(_green(f"<Image output: {head}base64,<IMAGE_BASE_64_ENCODED({len(b64data)})>>")) | ||
else: | ||
print(_green(f"<Image output: base64,<IMAGE_BASE_64_ENCODED({len(b64)})>>")) | ||
else: | ||
print(_green(f"<Non-string output: {repr(out)}>")) | ||
|
||
if len(outputs) > 1: | ||
choices_text = f" \t (and {len(outputs) - 1} other completions)" | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -219,7 +219,7 @@ class MySignature(dspy.Signature): | |
assert user_message_content[2]["type"] == "text" | ||
|
||
# Assert that the image is formatted correctly | ||
expected_image_content = {"type": "image_url", "image_url": {"url": "https://example.com/image.jpg"}} | ||
expected_image_content = {"type": "input_image", "image_url": "https://example.com/image.jpg"} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. all test related changes are for the refactoring of dspy.Image to handle the Responses Image format (the API strictly requires |
||
assert expected_image_content in user_message_content | ||
|
||
|
||
|
@@ -245,9 +245,10 @@ class MySignature(dspy.Signature): | |
# 1 system message, 2 few shot examples (1 user and assistant message for each example), 1 user message | ||
assert len(messages) == 6 | ||
|
||
assert {"type": "image_url", "image_url": {"url": "https://example.com/image1.jpg"}} in messages[1]["content"] | ||
assert {"type": "image_url", "image_url": {"url": "https://example.com/image2.jpg"}} in messages[3]["content"] | ||
assert {"type": "image_url", "image_url": {"url": "https://example.com/image3.jpg"}} in messages[5]["content"] | ||
assert {"type": "input_image", "image_url": "https://example.com/image1.jpg"} in messages[1]["content"] | ||
assert {"type": "input_image", "image_url": "https://example.com/image2.jpg"} in messages[3]["content"] | ||
assert {"type": "input_image", "image_url": "https://example.com/image3.jpg"} in messages[5]["content"] | ||
|
||
|
||
|
||
def test_chat_adapter_formats_image_with_nested_images(): | ||
|
@@ -268,9 +269,11 @@ class MySignature(dspy.Signature): | |
adapter = dspy.ChatAdapter() | ||
messages = adapter.format(MySignature, [], {"image": image_wrapper}) | ||
|
||
expected_image1_content = {"type": "image_url", "image_url": {"url": "https://example.com/image1.jpg"}} | ||
expected_image2_content = {"type": "image_url", "image_url": {"url": "https://example.com/image2.jpg"}} | ||
expected_image3_content = {"type": "image_url", "image_url": {"url": "https://example.com/image3.jpg"}} | ||
expected_image1_content = {"type": "input_image", "image_url": "https://example.com/image1.jpg"} | ||
expected_image2_content = {"type": "input_image", "image_url": "https://example.com/image2.jpg"} | ||
expected_image3_content = {"type": "input_image", "image_url": "https://example.com/image3.jpg"} | ||
|
||
|
||
|
||
assert expected_image1_content in messages[1]["content"] | ||
assert expected_image2_content in messages[1]["content"] | ||
|
@@ -305,12 +308,14 @@ class MySignature(dspy.Signature): | |
assert len(messages) == 4 | ||
|
||
# Image information in the few-shot example's user message | ||
expected_image1_content = {"type": "image_url", "image_url": {"url": "https://example.com/image1.jpg"}} | ||
expected_image2_content = {"type": "image_url", "image_url": {"url": "https://example.com/image2.jpg"}} | ||
expected_image3_content = {"type": "image_url", "image_url": {"url": "https://example.com/image3.jpg"}} | ||
expected_image1_content = {"type": "input_image", "image_url": "https://example.com/image1.jpg"} | ||
expected_image2_content = {"type": "input_image", "image_url": "https://example.com/image2.jpg"} | ||
expected_image3_content = {"type": "input_image", "image_url": "https://example.com/image3.jpg"} | ||
|
||
|
||
assert expected_image1_content in messages[1]["content"] | ||
assert expected_image2_content in messages[1]["content"] | ||
assert expected_image3_content in messages[1]["content"] | ||
|
||
# The query image is formatted in the last user message | ||
assert {"type": "image_url", "image_url": {"url": "https://example.com/image4.jpg"}} in messages[-1]["content"] | ||
assert {"type": "input_image", "image_url": "https://example.com/image4.jpg"} in messages[-1]["content"] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is related to the implicit warning that certain custom fields must be the only OutputField (aka can't have 2 Image OutputFields or 1 Image, 1 ToolCall OutputField) but maybe we can express this better? @chenmoneygithub @TomeHirata