Files
openclaw-zero-token/media/parse.test.ts
sjhu 571e14a236 feat: upgrade to upstream v2026.3.28
Major upgrade from e26988a38 to upstream v2026.3.28 (f9b107928).
Key changes:
- Upstream src/, ui/, extensions/ (89 bundled extensions)
- Zero-token web providers preserved in src/zero-token/
- AskOnce plugin restored and registered as CLI command
- Added missing packages: @anthropic-ai/vertex-sdk, @modelcontextprotocol/sdk
- Fixed tsconfig rootDir, skipLibCheck for plugin-sdk DTS build
- Added askonce to bundled plugin metadata and package.json exports
- Fixed AskOnce CLI command registration (missing commands metadata)
- Restored AskOnce adapter imports (correct 5-level relative paths)
- Removed stale migration artifacts from root directory
2026-03-30 17:58:12 +08:00

95 lines
3.2 KiB
TypeScript

import { describe, expect, it } from "vitest";
import { splitMediaFromOutput } from "./parse.js";
describe("splitMediaFromOutput", () => {
function expectParsedMediaOutputCase(
input: string,
expected: {
mediaUrls?: string[];
text?: string;
audioAsVoice?: boolean;
},
) {
const result = splitMediaFromOutput(input);
expect(result.text).toBe(expected.text ?? "");
if ("audioAsVoice" in expected) {
expect(result.audioAsVoice).toBe(expected.audioAsVoice);
} else {
expect(result.audioAsVoice).toBeUndefined();
}
if ("mediaUrls" in expected) {
expect(result.mediaUrls).toEqual(expected.mediaUrls);
expect(result.mediaUrl).toBe(expected.mediaUrls?.[0]);
} else {
expect(result.mediaUrls).toBeUndefined();
expect(result.mediaUrl).toBeUndefined();
}
}
function expectStableAudioAsVoiceDetectionCase(input: string) {
for (const output of [splitMediaFromOutput(input), splitMediaFromOutput(input)]) {
expect(output.audioAsVoice).toBe(true);
}
}
function expectAcceptedMediaPathCase(expectedPath: string, input: string) {
expectParsedMediaOutputCase(input, { mediaUrls: [expectedPath] });
}
function expectRejectedMediaPathCase(input: string) {
expectParsedMediaOutputCase(input, { mediaUrls: undefined });
}
it.each([
["/Users/pete/My File.png", "MEDIA:/Users/pete/My File.png"],
["/Users/pete/My File.png", 'MEDIA:"/Users/pete/My File.png"'],
["./screenshots/image.png", "MEDIA:./screenshots/image.png"],
["media/inbound/image.png", "MEDIA:media/inbound/image.png"],
["./screenshot.png", " MEDIA:./screenshot.png"],
["C:\\Users\\pete\\Pictures\\snap.png", "MEDIA:C:\\Users\\pete\\Pictures\\snap.png"],
["/tmp/tts-fAJy8C/voice-1770246885083.opus", "MEDIA:/tmp/tts-fAJy8C/voice-1770246885083.opus"],
["image.png", "MEDIA:image.png"],
] as const)("accepts supported media path variant: %s", (expectedPath, input) => {
expectAcceptedMediaPathCase(expectedPath, input);
});
it.each([
"MEDIA:../../../etc/passwd",
"MEDIA:../../.env",
"MEDIA:~/.ssh/id_rsa",
"MEDIA:~/Pictures/My File.png",
"MEDIA:./foo/../../../etc/shadow",
] as const)("rejects traversal and home-dir path: %s", (input) => {
expectRejectedMediaPathCase(input);
});
it.each([
{
name: "detects audio_as_voice tag and strips it",
input: "Hello [[audio_as_voice]] world",
expected: { audioAsVoice: true, text: "Hello world" },
},
{
name: "keeps MEDIA mentions in prose",
input: "The MEDIA: tag fails to deliver",
expected: { mediaUrls: undefined, text: "The MEDIA: tag fails to deliver" },
},
{
name: "rejects bare words without file extensions",
input: "MEDIA:screenshot",
expected: { mediaUrls: undefined, text: "MEDIA:screenshot" },
},
{
name: "keeps audio_as_voice detection stable across calls",
input: "Hello [[audio_as_voice]]",
expected: { audioAsVoice: true, text: "Hello" },
assertStable: true,
},
] as const)("$name", ({ input, expected, assertStable }) => {
expectParsedMediaOutputCase(input, expected);
if (assertStable) {
expectStableAudioAsVoiceDetectionCase(input);
}
});
});