@mindstone/mcp-server-elevenlabs 0.3.0 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (41) hide show
  1. package/README.md +30 -7
  2. package/dist/bridge.d.ts +1 -0
  3. package/dist/client.d.ts +34 -3
  4. package/dist/client.js +68 -14
  5. package/dist/endpoints.d.ts +34 -0
  6. package/dist/endpoints.js +37 -0
  7. package/dist/error-detail.d.ts +5 -0
  8. package/dist/error-detail.js +20 -0
  9. package/dist/server.js +9 -1
  10. package/dist/tools/account.d.ts +3 -0
  11. package/dist/tools/account.js +105 -0
  12. package/dist/tools/alignment.d.ts +3 -0
  13. package/dist/tools/alignment.js +55 -0
  14. package/dist/tools/audio-isolation.d.ts +3 -0
  15. package/dist/tools/audio-isolation.js +51 -0
  16. package/dist/tools/configure.js +18 -6
  17. package/dist/tools/dialogue.d.ts +3 -0
  18. package/dist/tools/dialogue.js +70 -0
  19. package/dist/tools/dubbing.d.ts +3 -0
  20. package/dist/tools/dubbing.js +234 -0
  21. package/dist/tools/file-input.d.ts +28 -0
  22. package/dist/tools/file-input.js +77 -0
  23. package/dist/tools/index.d.ts +8 -0
  24. package/dist/tools/index.js +8 -0
  25. package/dist/tools/music.js +85 -25
  26. package/dist/tools/path-safety.d.ts +1 -0
  27. package/dist/tools/path-safety.js +4 -1
  28. package/dist/tools/speech.js +57 -24
  29. package/dist/tools/transcription.js +27 -61
  30. package/dist/tools/voice-changer.d.ts +3 -0
  31. package/dist/tools/voice-changer.js +62 -0
  32. package/dist/tools/voice-clone.d.ts +3 -0
  33. package/dist/tools/voice-clone.js +104 -0
  34. package/dist/tools/voice-design.d.ts +3 -0
  35. package/dist/tools/voice-design.js +153 -0
  36. package/dist/tools/voices.js +167 -13
  37. package/dist/types.d.ts +91 -0
  38. package/dist/types.js +20 -4
  39. package/dist/untrusted-content.d.ts +45 -0
  40. package/dist/untrusted-content.js +104 -0
  41. package/package.json +2 -2
@@ -0,0 +1,104 @@
1
+ /**
2
+ * AGENTS.md security invariant #6 — content fetched from an external system
3
+ * MUST be wrapped in an `<untrusted-content source="…">…</untrusted-content>`
4
+ * envelope (with close-tag breakout escaping) before it is returned to the
5
+ * LLM, so the model treats third-party / attacker-controllable text as DATA,
6
+ * not as instructions.
7
+ *
8
+ * This is the canonical implementation a new connector ships with. It is a
9
+ * VENDORED copy of the shared reference in `test-harness/src/untrusted-content.ts`
10
+ * — connectors cannot `import` the test-harness at runtime (it is a
11
+ * test/dev-only `file:` dependency that is never published into a connector's
12
+ * `dist/`), so the helper lives in the connector's own runtime source. Keep
13
+ * this byte-for-byte in sync with the shared reference; do NOT weaken the
14
+ * escaping back to a simple `replaceAll` (that family misses whitespace / case
15
+ * close-tag variants like `</untrusted-content >` / `</UNTRUSTED-CONTENT>`).
16
+ *
17
+ * `scripts/check-untrusted-coverage.mjs` greps for a reference to
18
+ * `untrusted-content` in any connector that talks to an external system; this
19
+ * file (and the call sites that import from it) is what satisfies that gate.
20
+ */
21
+ const UNTRUSTED_CLOSE_TAG_VARIANT = /<\/untrusted-content\s*>/gi;
22
+ const ESCAPED_UNTRUSTED_CLOSE_TAG = '<\\/untrusted-content>';
23
+ const UNTRUSTED_ENVELOPE = /^<untrusted-content source="[^"]*">([\s\S]*)<\/untrusted-content>$/;
24
+ function escapeAttr(s) {
25
+ return s.replaceAll('&', '&amp;').replaceAll('"', '&quot;').replaceAll('<', '&lt;').replaceAll('>', '&gt;');
26
+ }
27
+ function escapeCloseTagSentinels(s) {
28
+ return s.replace(UNTRUSTED_CLOSE_TAG_VARIANT, ESCAPED_UNTRUSTED_CLOSE_TAG);
29
+ }
30
+ function unescapeCloseTagSentinels(s) {
31
+ return s.replaceAll(ESCAPED_UNTRUSTED_CLOSE_TAG, '</untrusted-content>');
32
+ }
33
+ /**
34
+ * Wrap a single untrusted string in an `<untrusted-content source="…">`
35
+ * envelope, escaping any embedded close-tag variant so the envelope cannot be
36
+ * broken out of. `undefined` passes through untouched. Idempotent for the same
37
+ * `source`.
38
+ */
39
+ export function wrapUntrusted(text, source) {
40
+ if (text === undefined)
41
+ return undefined;
42
+ const open = `<untrusted-content source="${escapeAttr(source)}">`;
43
+ const close = '</untrusted-content>';
44
+ if (text.startsWith(open) && text.endsWith(close) && text.length >= open.length + close.length) {
45
+ const inner = text.slice(open.length, text.length - close.length);
46
+ if (!UNTRUSTED_CLOSE_TAG_VARIANT.test(inner)) {
47
+ UNTRUSTED_CLOSE_TAG_VARIANT.lastIndex = 0;
48
+ return text;
49
+ }
50
+ UNTRUSTED_CLOSE_TAG_VARIANT.lastIndex = 0;
51
+ }
52
+ return `${open}${escapeCloseTagSentinels(text)}${close}`;
53
+ }
54
+ /**
55
+ * Strip one `<untrusted-content>` envelope from `text` if present, returning raw
56
+ * strings unchanged. This is intentionally one-layer and idempotent for already
57
+ * raw input so callers can accept either displayed wrapped content or manually
58
+ * authored content.
59
+ */
60
+ export function unwrapUntrusted(text) {
61
+ const match = UNTRUSTED_ENVELOPE.exec(text);
62
+ if (!match)
63
+ return text;
64
+ return unescapeCloseTagSentinels(match[1]);
65
+ }
66
+ /**
67
+ * Recursively wrap every string key and value reachable inside `value`.
68
+ * Non-string leaves pass through unchanged.
69
+ */
70
+ export function wrapUntrustedJsonStrings(value, source) {
71
+ if (typeof value === 'string') {
72
+ return wrapUntrusted(value, source);
73
+ }
74
+ if (Array.isArray(value)) {
75
+ return value.map((item) => wrapUntrustedJsonStrings(item, source));
76
+ }
77
+ if (value && typeof value === 'object') {
78
+ return Object.fromEntries(Object.entries(value).map(([key, item]) => [
79
+ wrapUntrusted(key, source) ?? key,
80
+ wrapUntrustedJsonStrings(item, source),
81
+ ]));
82
+ }
83
+ return value;
84
+ }
85
+ /**
86
+ * Recursively unwrap every string key and value reachable inside `value`.
87
+ * Non-string leaves pass through unchanged.
88
+ */
89
+ export function unwrapUntrustedJsonStrings(value) {
90
+ if (typeof value === 'string') {
91
+ return unwrapUntrusted(value);
92
+ }
93
+ if (Array.isArray(value)) {
94
+ return value.map((item) => unwrapUntrustedJsonStrings(item));
95
+ }
96
+ if (value && typeof value === 'object') {
97
+ return Object.fromEntries(Object.entries(value).map(([key, item]) => [
98
+ unwrapUntrusted(key),
99
+ unwrapUntrustedJsonStrings(item),
100
+ ]));
101
+ }
102
+ return value;
103
+ }
104
+ //# sourceMappingURL=untrusted-content.js.map
package/package.json CHANGED
@@ -1,8 +1,8 @@
1
1
  {
2
2
  "name": "@mindstone/mcp-server-elevenlabs",
3
- "version": "0.3.0",
3
+ "version": "0.4.0",
4
4
  "mcpName": "io.github.mindstone/mcp-server-elevenlabs",
5
- "description": "ElevenLabs MCP server for Model Context Protocol hosts \u2014 music, TTS, sound effects, voices, transcription",
5
+ "description": "ElevenLabs MCP server for Model Context Protocol hosts music, TTS, sound effects, voices, transcription",
6
6
  "license": "FSL-1.1-MIT",
7
7
  "type": "module",
8
8
  "bin": {