Skip to content

Commit 4210819

Browse files
committed
Add tests, remove unused code
1 parent bf1aa4c commit 4210819

File tree

3 files changed

+342
-108
lines changed

3 files changed

+342
-108
lines changed
Lines changed: 338 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,338 @@
1+
// npx jest src/api/transform/__tests__/gemini-format.test.ts
2+
3+
import { Anthropic } from "@anthropic-ai/sdk"
4+
5+
import { convertAnthropicMessageToGemini } from "../gemini-format"
6+
7+
describe("convertAnthropicMessageToGemini", () => {
8+
it("should convert a simple text message", () => {
9+
const anthropicMessage: Anthropic.Messages.MessageParam = {
10+
role: "user",
11+
content: "Hello, world!",
12+
}
13+
14+
const result = convertAnthropicMessageToGemini(anthropicMessage)
15+
16+
expect(result).toEqual({
17+
role: "user",
18+
parts: [{ text: "Hello, world!" }],
19+
})
20+
})
21+
22+
it("should convert assistant role to model role", () => {
23+
const anthropicMessage: Anthropic.Messages.MessageParam = {
24+
role: "assistant",
25+
content: "I'm an assistant",
26+
}
27+
28+
const result = convertAnthropicMessageToGemini(anthropicMessage)
29+
30+
expect(result).toEqual({
31+
role: "model",
32+
parts: [{ text: "I'm an assistant" }],
33+
})
34+
})
35+
36+
it("should convert a message with text blocks", () => {
37+
const anthropicMessage: Anthropic.Messages.MessageParam = {
38+
role: "user",
39+
content: [
40+
{ type: "text", text: "First paragraph" },
41+
{ type: "text", text: "Second paragraph" },
42+
],
43+
}
44+
45+
const result = convertAnthropicMessageToGemini(anthropicMessage)
46+
47+
expect(result).toEqual({
48+
role: "user",
49+
parts: [{ text: "First paragraph" }, { text: "Second paragraph" }],
50+
})
51+
})
52+
53+
it("should convert a message with an image", () => {
54+
const anthropicMessage: Anthropic.Messages.MessageParam = {
55+
role: "user",
56+
content: [
57+
{ type: "text", text: "Check out this image:" },
58+
{
59+
type: "image",
60+
source: {
61+
type: "base64",
62+
media_type: "image/jpeg",
63+
data: "base64encodeddata",
64+
},
65+
},
66+
],
67+
}
68+
69+
const result = convertAnthropicMessageToGemini(anthropicMessage)
70+
71+
expect(result).toEqual({
72+
role: "user",
73+
parts: [
74+
{ text: "Check out this image:" },
75+
{
76+
inlineData: {
77+
data: "base64encodeddata",
78+
mimeType: "image/jpeg",
79+
},
80+
},
81+
],
82+
})
83+
})
84+
85+
it("should throw an error for unsupported image source type", () => {
86+
const anthropicMessage: Anthropic.Messages.MessageParam = {
87+
role: "user",
88+
content: [
89+
{
90+
type: "image",
91+
source: {
92+
type: "url", // Not supported
93+
url: "https://example.com/image.jpg",
94+
} as any,
95+
},
96+
],
97+
}
98+
99+
expect(() => convertAnthropicMessageToGemini(anthropicMessage)).toThrow("Unsupported image source type")
100+
})
101+
102+
it("should convert a message with tool use", () => {
103+
const anthropicMessage: Anthropic.Messages.MessageParam = {
104+
role: "assistant",
105+
content: [
106+
{ type: "text", text: "Let me calculate that for you." },
107+
{
108+
type: "tool_use",
109+
id: "calc-123",
110+
name: "calculator",
111+
input: { operation: "add", numbers: [2, 3] },
112+
},
113+
],
114+
}
115+
116+
const result = convertAnthropicMessageToGemini(anthropicMessage)
117+
118+
expect(result).toEqual({
119+
role: "model",
120+
parts: [
121+
{ text: "Let me calculate that for you." },
122+
{
123+
functionCall: {
124+
name: "calculator",
125+
args: { operation: "add", numbers: [2, 3] },
126+
},
127+
},
128+
],
129+
})
130+
})
131+
132+
it("should convert a message with tool result as string", () => {
133+
const anthropicMessage: Anthropic.Messages.MessageParam = {
134+
role: "user",
135+
content: [
136+
{ type: "text", text: "Here's the result:" },
137+
{
138+
type: "tool_result",
139+
tool_use_id: "calculator-123",
140+
content: "The result is 5",
141+
},
142+
],
143+
}
144+
145+
const result = convertAnthropicMessageToGemini(anthropicMessage)
146+
147+
expect(result).toEqual({
148+
role: "user",
149+
parts: [
150+
{ text: "Here's the result:" },
151+
{
152+
functionResponse: {
153+
name: "calculator",
154+
response: {
155+
name: "calculator",
156+
content: "The result is 5",
157+
},
158+
},
159+
},
160+
],
161+
})
162+
})
163+
164+
it("should handle empty tool result content", () => {
165+
const anthropicMessage: Anthropic.Messages.MessageParam = {
166+
role: "user",
167+
content: [
168+
{
169+
type: "tool_result",
170+
tool_use_id: "calculator-123",
171+
content: null as any, // Empty content
172+
},
173+
],
174+
}
175+
176+
const result = convertAnthropicMessageToGemini(anthropicMessage)
177+
178+
// Should skip the empty tool result
179+
expect(result).toEqual({
180+
role: "user",
181+
parts: [],
182+
})
183+
})
184+
185+
it("should convert a message with tool result as array with text only", () => {
186+
const anthropicMessage: Anthropic.Messages.MessageParam = {
187+
role: "user",
188+
content: [
189+
{
190+
type: "tool_result",
191+
tool_use_id: "search-123",
192+
content: [
193+
{ type: "text", text: "First result" },
194+
{ type: "text", text: "Second result" },
195+
],
196+
},
197+
],
198+
}
199+
200+
const result = convertAnthropicMessageToGemini(anthropicMessage)
201+
202+
expect(result).toEqual({
203+
role: "user",
204+
parts: [
205+
{
206+
functionResponse: {
207+
name: "search",
208+
response: {
209+
name: "search",
210+
content: "First result\n\nSecond result",
211+
},
212+
},
213+
},
214+
],
215+
})
216+
})
217+
218+
it("should convert a message with tool result as array with text and images", () => {
219+
const anthropicMessage: Anthropic.Messages.MessageParam = {
220+
role: "user",
221+
content: [
222+
{
223+
type: "tool_result",
224+
tool_use_id: "search-123",
225+
content: [
226+
{ type: "text", text: "Search results:" },
227+
{
228+
type: "image",
229+
source: {
230+
type: "base64",
231+
media_type: "image/png",
232+
data: "image1data",
233+
},
234+
},
235+
{
236+
type: "image",
237+
source: {
238+
type: "base64",
239+
media_type: "image/jpeg",
240+
data: "image2data",
241+
},
242+
},
243+
],
244+
},
245+
],
246+
}
247+
248+
const result = convertAnthropicMessageToGemini(anthropicMessage)
249+
250+
expect(result).toEqual({
251+
role: "user",
252+
parts: [
253+
{
254+
functionResponse: {
255+
name: "search",
256+
response: {
257+
name: "search",
258+
content: "Search results:\n\n(See next part for image)",
259+
},
260+
},
261+
},
262+
{
263+
inlineData: {
264+
data: "image1data",
265+
mimeType: "image/png",
266+
},
267+
},
268+
{
269+
inlineData: {
270+
data: "image2data",
271+
mimeType: "image/jpeg",
272+
},
273+
},
274+
],
275+
})
276+
})
277+
278+
it("should convert a message with tool result containing only images", () => {
279+
const anthropicMessage: Anthropic.Messages.MessageParam = {
280+
role: "user",
281+
content: [
282+
{
283+
type: "tool_result",
284+
tool_use_id: "imagesearch-123",
285+
content: [
286+
{
287+
type: "image",
288+
source: {
289+
type: "base64",
290+
media_type: "image/png",
291+
data: "onlyimagedata",
292+
},
293+
},
294+
],
295+
},
296+
],
297+
}
298+
299+
const result = convertAnthropicMessageToGemini(anthropicMessage)
300+
301+
expect(result).toEqual({
302+
role: "user",
303+
parts: [
304+
{
305+
functionResponse: {
306+
name: "imagesearch",
307+
response: {
308+
name: "imagesearch",
309+
content: "\n\n(See next part for image)",
310+
},
311+
},
312+
},
313+
{
314+
inlineData: {
315+
data: "onlyimagedata",
316+
mimeType: "image/png",
317+
},
318+
},
319+
],
320+
})
321+
})
322+
323+
it("should throw an error for unsupported content block type", () => {
324+
const anthropicMessage: Anthropic.Messages.MessageParam = {
325+
role: "user",
326+
content: [
327+
{
328+
type: "unknown_type", // Unsupported type
329+
data: "some data",
330+
} as any,
331+
],
332+
}
333+
334+
expect(() => convertAnthropicMessageToGemini(anthropicMessage)).toThrow(
335+
"Unsupported content block type: unknown_type",
336+
)
337+
})
338+
})

0 commit comments

Comments
 (0)