@contenthero/mcp 0.1.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.
- package/README.md +62 -0
- package/dist/client.d.ts +11 -0
- package/dist/client.d.ts.map +1 -0
- package/dist/client.js +21 -0
- package/dist/client.js.map +1 -0
- package/dist/format.d.ts +41 -0
- package/dist/format.d.ts.map +1 -0
- package/dist/format.js +156 -0
- package/dist/format.js.map +1 -0
- package/dist/index.d.ts +9 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +20 -0
- package/dist/index.js.map +1 -0
- package/dist/models.d.ts +56 -0
- package/dist/models.d.ts.map +1 -0
- package/dist/models.js +114 -0
- package/dist/models.js.map +1 -0
- package/dist/server.d.ts +30 -0
- package/dist/server.d.ts.map +1 -0
- package/dist/server.js +451 -0
- package/dist/server.js.map +1 -0
- package/package.json +52 -0
package/README.md
ADDED
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
# @contenthero/mcp
|
|
2
|
+
|
|
3
|
+
Official [ContentHero](https://contenthero.ai) MCP server. Generate images, video, and audio from any MCP client (Claude Code, Claude Desktop, ...) using your ContentHero API key.
|
|
4
|
+
|
|
5
|
+
## Tools
|
|
6
|
+
|
|
7
|
+
| Tool | What it does |
|
|
8
|
+
| --- | --- |
|
|
9
|
+
| `generate_image` | Generate images from a prompt (or image-to-image). Waits for the result and returns the URLs. |
|
|
10
|
+
| `generate_video` | Generate video from a prompt (or start/end frame, references). Waits up to ~75s, then returns an `outputId` to poll if the render is still running. |
|
|
11
|
+
| `generate_audio` | ElevenLabs speech (TTS), music, or sound effects. Synchronous: returns the audio URL directly. |
|
|
12
|
+
| `check_generation` | Poll an image/video `outputId` to its final URLs. |
|
|
13
|
+
| `get_balance` | Current credit balance, tier, and auto-top-up state. |
|
|
14
|
+
|
|
15
|
+
Three intent-shaped generate tools (not one `generate_media`): image and video share the async smart-wait lifecycle, audio shares almost nothing and runs synchronously, and per-tool `modelId` enums keep each schema clean.
|
|
16
|
+
|
|
17
|
+
## Setup
|
|
18
|
+
|
|
19
|
+
Requires Node 20+. You need a ContentHero API key (`ch_live_...`).
|
|
20
|
+
|
|
21
|
+
### Claude Code
|
|
22
|
+
|
|
23
|
+
```bash
|
|
24
|
+
claude mcp add contenthero --env CONTENTHERO_API_KEY=ch_live_xxx -- npx -y @contenthero/mcp
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
### Claude Desktop / generic MCP config
|
|
28
|
+
|
|
29
|
+
```json
|
|
30
|
+
{
|
|
31
|
+
"mcpServers": {
|
|
32
|
+
"contenthero": {
|
|
33
|
+
"command": "npx",
|
|
34
|
+
"args": ["-y", "@contenthero/mcp"],
|
|
35
|
+
"env": { "CONTENTHERO_API_KEY": "ch_live_xxx" }
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
```
|
|
40
|
+
|
|
41
|
+
### Environment
|
|
42
|
+
|
|
43
|
+
| Variable | Required | Default |
|
|
44
|
+
| --- | --- | --- |
|
|
45
|
+
| `CONTENTHERO_API_KEY` | yes | - |
|
|
46
|
+
| `CONTENTHERO_BASE_URL` | no | `https://app.contenthero.ai` |
|
|
47
|
+
|
|
48
|
+
## Usage
|
|
49
|
+
|
|
50
|
+
Once connected, just ask in natural language. The agent picks the tool and model:
|
|
51
|
+
|
|
52
|
+
> "Generate a 16:9 image of a golden retriever astronaut with nano-banana-2."
|
|
53
|
+
|
|
54
|
+
> "Make an 8 second video of a city at dusk with audio using veo-3.1-fast."
|
|
55
|
+
|
|
56
|
+
> "Read this script aloud with ElevenLabs voice `<id>`."
|
|
57
|
+
|
|
58
|
+
Images return in one turn (~15s). Video either returns inline or hands back an `outputId`; the agent then calls `check_generation` to fetch the final URLs. Insufficient credits, invalid parameters, and unknown models come back as readable tool errors.
|
|
59
|
+
|
|
60
|
+
## How it works
|
|
61
|
+
|
|
62
|
+
This server is a thin wrapper over [`@contenthero/sdk`](https://www.npmjs.com/package/@contenthero/sdk), which talks to the ContentHero `/api/v1` surface. Your API key resolves your account server-side; the server never sends a user id. Pricing is computed server-side.
|
package/dist/client.d.ts
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Lazy ContentHero SDK client, configured from the environment.
|
|
3
|
+
*
|
|
4
|
+
* Reads CONTENTHERO_API_KEY (required) and CONTENTHERO_BASE_URL (optional) from
|
|
5
|
+
* the MCP server's env config. Resolution is deferred to first use so the
|
|
6
|
+
* server can start and advertise its tools even before a key is present; the
|
|
7
|
+
* missing-key error then surfaces as a tool-call result rather than a crash.
|
|
8
|
+
*/
|
|
9
|
+
import { ContentHero } from '@contenthero/sdk';
|
|
10
|
+
export declare function getClient(): ContentHero;
|
|
11
|
+
//# sourceMappingURL=client.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA;AAI9C,wBAAgB,SAAS,IAAI,WAAW,CAUvC"}
|
package/dist/client.js
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Lazy ContentHero SDK client, configured from the environment.
|
|
3
|
+
*
|
|
4
|
+
* Reads CONTENTHERO_API_KEY (required) and CONTENTHERO_BASE_URL (optional) from
|
|
5
|
+
* the MCP server's env config. Resolution is deferred to first use so the
|
|
6
|
+
* server can start and advertise its tools even before a key is present; the
|
|
7
|
+
* missing-key error then surfaces as a tool-call result rather than a crash.
|
|
8
|
+
*/
|
|
9
|
+
import { ContentHero } from '@contenthero/sdk';
|
|
10
|
+
let cached;
|
|
11
|
+
export function getClient() {
|
|
12
|
+
if (cached)
|
|
13
|
+
return cached;
|
|
14
|
+
const apiKey = process.env.CONTENTHERO_API_KEY;
|
|
15
|
+
if (!apiKey) {
|
|
16
|
+
throw new Error('CONTENTHERO_API_KEY is not set. Add it to the env of your ContentHero MCP server config.');
|
|
17
|
+
}
|
|
18
|
+
cached = new ContentHero({ apiKey, baseUrl: process.env.CONTENTHERO_BASE_URL });
|
|
19
|
+
return cached;
|
|
20
|
+
}
|
|
21
|
+
//# sourceMappingURL=client.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"client.js","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA;AAE9C,IAAI,MAA+B,CAAA;AAEnC,MAAM,UAAU,SAAS;IACvB,IAAI,MAAM;QAAE,OAAO,MAAM,CAAA;IACzB,MAAM,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC,mBAAmB,CAAA;IAC9C,IAAI,CAAC,MAAM,EAAE,CAAC;QACZ,MAAM,IAAI,KAAK,CACb,0FAA0F,CAC3F,CAAA;IACH,CAAC;IACD,MAAM,GAAG,IAAI,WAAW,CAAC,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,CAAC,GAAG,CAAC,oBAAoB,EAAE,CAAC,CAAA;IAC/E,OAAO,MAAM,CAAA;AACf,CAAC"}
|
package/dist/format.d.ts
ADDED
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Helpers that turn SDK results and errors into MCP CallToolResult content.
|
|
3
|
+
* Tool errors are returned as `isError` results (not thrown) so the agent sees
|
|
4
|
+
* a readable message instead of a transport failure.
|
|
5
|
+
*/
|
|
6
|
+
import type { CallToolResult } from '@modelcontextprotocol/sdk/types.js';
|
|
7
|
+
import type { Avatar, AvatarSummary, Balance, BrandKit, BrandKitSummary, Generation, GenerateResult, MediaItem, MediaSummary, Transcription, Voice, VoiceSummary } from '@contenthero/sdk';
|
|
8
|
+
/** A finished image/video generation: list the asset URLs. */
|
|
9
|
+
export declare function completedResult(gen: Generation): CallToolResult;
|
|
10
|
+
/** A slow job that did not finish within the smart-wait window. */
|
|
11
|
+
export declare function pendingResult(outputId: string): CallToolResult;
|
|
12
|
+
/** Synchronous audio result (already complete on submit). */
|
|
13
|
+
export declare function audioResult(result: GenerateResult): CallToolResult;
|
|
14
|
+
/** Result of polling a generation via check_generation. */
|
|
15
|
+
export declare function generationStatusResult(gen: Generation): CallToolResult;
|
|
16
|
+
/** A finished transcription: header line plus the transcript body. */
|
|
17
|
+
export declare function transcriptResult(t: Transcription): CallToolResult;
|
|
18
|
+
/** List of avatars, each with the fields an agent needs to drive lip-sync. */
|
|
19
|
+
export declare function avatarListResult(avatars: AvatarSummary[]): CallToolResult;
|
|
20
|
+
/** One avatar's full detail, including its looks. */
|
|
21
|
+
export declare function avatarResult(a: Avatar): CallToolResult;
|
|
22
|
+
/** List of saved voices. */
|
|
23
|
+
export declare function voiceListResult(voices: VoiceSummary[]): CallToolResult;
|
|
24
|
+
/** One voice's full detail. */
|
|
25
|
+
export declare function voiceResult(v: Voice): CallToolResult;
|
|
26
|
+
/** List of brand kits. */
|
|
27
|
+
export declare function brandKitListResult(kits: BrandKitSummary[]): CallToolResult;
|
|
28
|
+
/**
|
|
29
|
+
* One brand kit in full. The kit is deeply structured (visual identity, voice,
|
|
30
|
+
* curated sections, linked accounts, knowledge), so return a short header plus
|
|
31
|
+
* the whole object as JSON: faithful and complete, and an agent reads it cleanly.
|
|
32
|
+
*/
|
|
33
|
+
export declare function brandKitResult(kit: BrandKit): CallToolResult;
|
|
34
|
+
/** List of studio outputs (media). */
|
|
35
|
+
export declare function mediaListResult(items: MediaSummary[]): CallToolResult;
|
|
36
|
+
/** One studio output's detail, with its variations. */
|
|
37
|
+
export declare function mediaResult(m: MediaItem): CallToolResult;
|
|
38
|
+
export declare function balanceResult(b: Balance): CallToolResult;
|
|
39
|
+
/** Map any thrown error onto a readable isError result. */
|
|
40
|
+
export declare function errorResult(err: unknown): CallToolResult;
|
|
41
|
+
//# sourceMappingURL=format.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"format.d.ts","sourceRoot":"","sources":["../src/format.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,oCAAoC,CAAA;AACxE,OAAO,KAAK,EACV,MAAM,EACN,aAAa,EACb,OAAO,EACP,QAAQ,EACR,eAAe,EACf,UAAU,EACV,cAAc,EACd,SAAS,EACT,YAAY,EACZ,aAAa,EACb,KAAK,EACL,YAAY,EACb,MAAM,kBAAkB,CAAA;AAOzB,8DAA8D;AAC9D,wBAAgB,eAAe,CAAC,GAAG,EAAE,UAAU,GAAG,cAAc,CAK/D;AAED,mEAAmE;AACnE,wBAAgB,aAAa,CAAC,QAAQ,EAAE,MAAM,GAAG,cAAc,CAI9D;AAED,6DAA6D;AAC7D,wBAAgB,WAAW,CAAC,MAAM,EAAE,cAAc,GAAG,cAAc,CAIlE;AAED,2DAA2D;AAC3D,wBAAgB,sBAAsB,CAAC,GAAG,EAAE,UAAU,GAAG,cAAc,CAMtE;AAED,sEAAsE;AACtE,wBAAgB,gBAAgB,CAAC,CAAC,EAAE,aAAa,GAAG,cAAc,CAIjE;AAOD,8EAA8E;AAC9E,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,aAAa,EAAE,GAAG,cAAc,CASzE;AAED,qDAAqD;AACrD,wBAAgB,YAAY,CAAC,CAAC,EAAE,MAAM,GAAG,cAAc,CAiBtD;AAED,4BAA4B;AAC5B,wBAAgB,eAAe,CAAC,MAAM,EAAE,YAAY,EAAE,GAAG,cAAc,CAOtE;AAED,+BAA+B;AAC/B,wBAAgB,WAAW,CAAC,CAAC,EAAE,KAAK,GAAG,cAAc,CAYpD;AAED,0BAA0B;AAC1B,wBAAgB,kBAAkB,CAAC,IAAI,EAAE,eAAe,EAAE,GAAG,cAAc,CAO1E;AAED;;;;GAIG;AACH,wBAAgB,cAAc,CAAC,GAAG,EAAE,QAAQ,GAAG,cAAc,CAG5D;AAED,sCAAsC;AACtC,wBAAgB,eAAe,CAAC,KAAK,EAAE,YAAY,EAAE,GAAG,cAAc,CAQrE;AAED,uDAAuD;AACvD,wBAAgB,WAAW,CAAC,CAAC,EAAE,SAAS,GAAG,cAAc,CAqBxD;AAED,wBAAgB,aAAa,CAAC,CAAC,EAAE,OAAO,GAAG,cAAc,CAIxD;AAED,2DAA2D;AAC3D,wBAAgB,WAAW,CAAC,GAAG,EAAE,OAAO,GAAG,cAAc,CAgBxD"}
|
package/dist/format.js
ADDED
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Helpers that turn SDK results and errors into MCP CallToolResult content.
|
|
3
|
+
* Tool errors are returned as `isError` results (not thrown) so the agent sees
|
|
4
|
+
* a readable message instead of a transport failure.
|
|
5
|
+
*/
|
|
6
|
+
import { ContentHeroError, InsufficientCreditsError, RateLimitError } from '@contenthero/sdk';
|
|
7
|
+
function text(body, isError = false) {
|
|
8
|
+
return { content: [{ type: 'text', text: body }], isError };
|
|
9
|
+
}
|
|
10
|
+
/** A finished image/video generation: list the asset URLs. */
|
|
11
|
+
export function completedResult(gen) {
|
|
12
|
+
const urls = gen.outputUrls ?? [];
|
|
13
|
+
const noun = urls.length === 1 ? gen.contentType : `${gen.contentType}s`;
|
|
14
|
+
const header = `Done. ${urls.length} ${noun} from ${gen.modelId} (outputId ${gen.outputId}):`;
|
|
15
|
+
return text([header, ...urls.map((u, i) => `${i + 1}. ${u}`)].join('\n'));
|
|
16
|
+
}
|
|
17
|
+
/** A slow job that did not finish within the smart-wait window. */
|
|
18
|
+
export function pendingResult(outputId) {
|
|
19
|
+
return text(`Still rendering (outputId ${outputId}). This is normal for video. Call check_generation with this outputId in ~30-60s to get the final URLs.`);
|
|
20
|
+
}
|
|
21
|
+
/** Synchronous audio result (already complete on submit). */
|
|
22
|
+
export function audioResult(result) {
|
|
23
|
+
const urls = result.outputUrls ?? [];
|
|
24
|
+
const header = `Done. Audio generated (outputId ${result.outputId}):`;
|
|
25
|
+
return text([header, ...urls.map((u, i) => `${i + 1}. ${u}`)].join('\n'));
|
|
26
|
+
}
|
|
27
|
+
/** Result of polling a generation via check_generation. */
|
|
28
|
+
export function generationStatusResult(gen) {
|
|
29
|
+
if (gen.status === 'completed')
|
|
30
|
+
return completedResult(gen);
|
|
31
|
+
if (gen.status === 'failed') {
|
|
32
|
+
return text(`Generation ${gen.outputId} failed: ${gen.error ?? 'unknown error'}`, true);
|
|
33
|
+
}
|
|
34
|
+
return text(`Generation ${gen.outputId} is still ${gen.status}. Check again in a moment.`);
|
|
35
|
+
}
|
|
36
|
+
/** A finished transcription: header line plus the transcript body. */
|
|
37
|
+
export function transcriptResult(t) {
|
|
38
|
+
const lang = t.language ? ` (${t.language})` : '';
|
|
39
|
+
const header = `Transcript${lang}, ${t.wordCount} words (outputId ${t.outputId}):`;
|
|
40
|
+
return text([header, '', t.transcript].join('\n'));
|
|
41
|
+
}
|
|
42
|
+
/** Join the non-empty lines (drops null/empty entries). */
|
|
43
|
+
function lines(parts) {
|
|
44
|
+
return parts.filter((p) => !!p).join('\n');
|
|
45
|
+
}
|
|
46
|
+
/** List of avatars, each with the fields an agent needs to drive lip-sync. */
|
|
47
|
+
export function avatarListResult(avatars) {
|
|
48
|
+
if (!avatars.length) {
|
|
49
|
+
return text('No avatars found. Create one in the ContentHero app first.');
|
|
50
|
+
}
|
|
51
|
+
const rows = avatars.map((a) => `- ${a.name} (id ${a.id})${a.isDefault ? ' [default]' : ''} | image: ${a.imageUrl ?? 'none'} | voice: ${a.defaultVoiceId ?? 'none'}`);
|
|
52
|
+
return text([`${avatars.length} avatar(s):`, ...rows].join('\n'));
|
|
53
|
+
}
|
|
54
|
+
/** One avatar's full detail, including its looks. */
|
|
55
|
+
export function avatarResult(a) {
|
|
56
|
+
const traits = [a.gender, a.age, a.ethnicity].filter(Boolean).join(', ');
|
|
57
|
+
return text(lines([
|
|
58
|
+
`${a.name} (id ${a.id})${a.isDefault ? ' [default]' : ''}`,
|
|
59
|
+
`image (base look, use as imageUrl for generate_lip_sync): ${a.imageUrl ?? 'none'}`,
|
|
60
|
+
`default voice (use as voiceId): ${a.defaultVoiceId ?? 'none'}`,
|
|
61
|
+
a.description ? `description: ${a.description}` : null,
|
|
62
|
+
traits ? `traits: ${traits}` : null,
|
|
63
|
+
a.niche.length ? `niche: ${a.niche.join(', ')}` : null,
|
|
64
|
+
a.looks.length ? `looks (${a.looks.length}):` : 'looks: none',
|
|
65
|
+
...a.looks.map((l) => ` - ${l.name ?? l.lookType ?? 'look'} (id ${l.id})${l.isDefault ? ' [default]' : ''}: ${l.imageUrl ?? 'none'}`),
|
|
66
|
+
]));
|
|
67
|
+
}
|
|
68
|
+
/** List of saved voices. */
|
|
69
|
+
export function voiceListResult(voices) {
|
|
70
|
+
if (!voices.length)
|
|
71
|
+
return text('No saved voices found.');
|
|
72
|
+
const rows = voices.map((v) => `- ${v.name ?? '(unnamed)'} (voiceId ${v.voiceId})${v.isFavorited ? ' [favorite]' : ''}${v.previewUrl ? ` | preview: ${v.previewUrl}` : ''}`);
|
|
73
|
+
return text([`${voices.length} voice(s):`, ...rows].join('\n'));
|
|
74
|
+
}
|
|
75
|
+
/** One voice's full detail. */
|
|
76
|
+
export function voiceResult(v) {
|
|
77
|
+
const traits = [v.gender, v.age, v.accent, v.language].filter(Boolean).join(', ');
|
|
78
|
+
return text(lines([
|
|
79
|
+
`${v.name ?? '(unnamed)'} (voiceId ${v.voiceId})${v.isFavorited ? ' [favorite]' : ''}`,
|
|
80
|
+
v.provider ? `provider: ${v.provider}` : null,
|
|
81
|
+
traits ? `traits: ${traits}` : null,
|
|
82
|
+
v.description ? `description: ${v.description}` : null,
|
|
83
|
+
v.useCase ? `use case: ${v.useCase}` : null,
|
|
84
|
+
v.previewUrl ? `preview: ${v.previewUrl}` : null,
|
|
85
|
+
]));
|
|
86
|
+
}
|
|
87
|
+
/** List of brand kits. */
|
|
88
|
+
export function brandKitListResult(kits) {
|
|
89
|
+
if (!kits.length)
|
|
90
|
+
return text('No brand kits found. Create one in the ContentHero app first.');
|
|
91
|
+
const rows = kits.map((k) => `- ${k.name}${k.businessName && k.businessName !== k.name ? ` (${k.businessName})` : ''} (id ${k.id})${k.isDefault ? ' [default]' : ''}${k.nicheDefinition ? ` | niche: ${k.nicheDefinition}` : ''}`);
|
|
92
|
+
return text([`${kits.length} brand kit(s):`, ...rows].join('\n'));
|
|
93
|
+
}
|
|
94
|
+
/**
|
|
95
|
+
* One brand kit in full. The kit is deeply structured (visual identity, voice,
|
|
96
|
+
* curated sections, linked accounts, knowledge), so return a short header plus
|
|
97
|
+
* the whole object as JSON: faithful and complete, and an agent reads it cleanly.
|
|
98
|
+
*/
|
|
99
|
+
export function brandKitResult(kit) {
|
|
100
|
+
const header = `Brand kit "${kit.name}"${kit.isDefault ? ' [default]' : ''} (id ${kit.id}):`;
|
|
101
|
+
return text([header, '', JSON.stringify(kit, null, 2)].join('\n'));
|
|
102
|
+
}
|
|
103
|
+
/** List of studio outputs (media). */
|
|
104
|
+
export function mediaListResult(items) {
|
|
105
|
+
if (!items.length)
|
|
106
|
+
return text('No media found.');
|
|
107
|
+
const rows = items.map((m) => {
|
|
108
|
+
const vars = m.variationCount > 1 ? ` | ${m.variationCount} variations` : '';
|
|
109
|
+
const promptStr = m.prompt ? ` | ${m.prompt.slice(0, 80)}${m.prompt.length > 80 ? '...' : ''}` : '';
|
|
110
|
+
return `- [${m.type}] ${m.model ?? ''} (id ${m.id})${vars} | ${m.status}${promptStr}`;
|
|
111
|
+
});
|
|
112
|
+
return text([`${items.length} item(s) (newest first):`, ...rows].join('\n'));
|
|
113
|
+
}
|
|
114
|
+
/** One studio output's detail, with its variations. */
|
|
115
|
+
export function mediaResult(m) {
|
|
116
|
+
const specs = [
|
|
117
|
+
m.aspectRatio ? `aspect ${m.aspectRatio}` : null,
|
|
118
|
+
m.resolution ? `res ${m.resolution}` : null,
|
|
119
|
+
m.duration ? `${m.duration}s` : null,
|
|
120
|
+
]
|
|
121
|
+
.filter(Boolean)
|
|
122
|
+
.join(', ');
|
|
123
|
+
return text(lines([
|
|
124
|
+
`${m.type} from ${m.model ?? 'unknown'} (id ${m.id})${m.selectedVariation ? `, variation ${m.selectedVariation}` : ''}`,
|
|
125
|
+
m.prompt ? `prompt: ${m.prompt}` : null,
|
|
126
|
+
m.script ? `script: ${m.script}` : null,
|
|
127
|
+
specs || null,
|
|
128
|
+
`status: ${m.status}${m.creditsUsed != null ? ` | ${m.creditsUsed} credits` : ''}`,
|
|
129
|
+
`variations (${m.variationCount}):`,
|
|
130
|
+
...m.variations.map((v) => ` ${v.variation}. ${v.url ?? `(no url, ${v.status})`}${v.isFavorited ? ' [favorite]' : ''}`),
|
|
131
|
+
]));
|
|
132
|
+
}
|
|
133
|
+
export function balanceResult(b) {
|
|
134
|
+
return text(`Balance: ${b.balance} credits (tier: ${b.tier}, auto top-up: ${b.autoTopupEnabled ? 'on' : 'off'}).`);
|
|
135
|
+
}
|
|
136
|
+
/** Map any thrown error onto a readable isError result. */
|
|
137
|
+
export function errorResult(err) {
|
|
138
|
+
if (err instanceof InsufficientCreditsError) {
|
|
139
|
+
const parts = [];
|
|
140
|
+
if (err.required != null)
|
|
141
|
+
parts.push(`need ${err.required}`);
|
|
142
|
+
if (err.balance != null)
|
|
143
|
+
parts.push(`have ${err.balance}`);
|
|
144
|
+
const detail = parts.length ? ` (${parts.join(', ')})` : '';
|
|
145
|
+
return text(`Insufficient credits${detail}. Top up to continue.`, true);
|
|
146
|
+
}
|
|
147
|
+
if (err instanceof RateLimitError) {
|
|
148
|
+
const wait = err.retryAfter != null ? ` Retry in ${err.retryAfter}s.` : '';
|
|
149
|
+
return text(`Rate limit exceeded.${wait || ' Wait a moment before retrying.'}`, true);
|
|
150
|
+
}
|
|
151
|
+
if (err instanceof ContentHeroError || err instanceof Error) {
|
|
152
|
+
return text(err.message, true);
|
|
153
|
+
}
|
|
154
|
+
return text('Unknown error', true);
|
|
155
|
+
}
|
|
156
|
+
//# sourceMappingURL=format.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"format.js","sourceRoot":"","sources":["../src/format.ts"],"names":[],"mappings":"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"}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* ContentHero MCP server entry point (stdio transport).
|
|
4
|
+
*
|
|
5
|
+
* Run by an MCP client (Claude Code, Claude Desktop, etc.) as a child process.
|
|
6
|
+
* stdout is the protocol channel, so all logging goes to stderr.
|
|
7
|
+
*/
|
|
8
|
+
export {};
|
|
9
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA;;;;;GAKG"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* ContentHero MCP server entry point (stdio transport).
|
|
4
|
+
*
|
|
5
|
+
* Run by an MCP client (Claude Code, Claude Desktop, etc.) as a child process.
|
|
6
|
+
* stdout is the protocol channel, so all logging goes to stderr.
|
|
7
|
+
*/
|
|
8
|
+
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
|
|
9
|
+
import { buildServer } from './server.js';
|
|
10
|
+
async function main() {
|
|
11
|
+
const server = await buildServer();
|
|
12
|
+
const transport = new StdioServerTransport();
|
|
13
|
+
await server.connect(transport);
|
|
14
|
+
console.error('ContentHero MCP server running on stdio');
|
|
15
|
+
}
|
|
16
|
+
main().catch((err) => {
|
|
17
|
+
console.error('ContentHero MCP server failed to start:', err);
|
|
18
|
+
process.exit(1);
|
|
19
|
+
});
|
|
20
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AACA;;;;;GAKG;AAEH,OAAO,EAAE,oBAAoB,EAAE,MAAM,2CAA2C,CAAA;AAChF,OAAO,EAAE,WAAW,EAAE,MAAM,aAAa,CAAA;AAEzC,KAAK,UAAU,IAAI;IACjB,MAAM,MAAM,GAAG,MAAM,WAAW,EAAE,CAAA;IAClC,MAAM,SAAS,GAAG,IAAI,oBAAoB,EAAE,CAAA;IAC5C,MAAM,MAAM,CAAC,OAAO,CAAC,SAAS,CAAC,CAAA;IAC/B,OAAO,CAAC,KAAK,CAAC,yCAAyC,CAAC,CAAA;AAC1D,CAAC;AAED,IAAI,EAAE,CAAC,KAAK,CAAC,CAAC,GAAG,EAAE,EAAE;IACnB,OAAO,CAAC,KAAK,CAAC,yCAAyC,EAAE,GAAG,CAAC,CAAA;IAC7D,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAA;AACjB,CAAC,CAAC,CAAA"}
|
package/dist/models.d.ts
ADDED
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Per-tool model lists, resolved dynamically from the discovery endpoint.
|
|
3
|
+
*
|
|
4
|
+
* `resolveModelEnums` fetches `GET /api/v1/models` (via the SDK) once at server
|
|
5
|
+
* startup and groups the enabled models into the three generate tools by their
|
|
6
|
+
* registry `kind`. So the model a tool offers always tracks the admin
|
|
7
|
+
* switchboard: enable a model in the app and it appears here on the next restart,
|
|
8
|
+
* with no package change. The hardcoded `*_FALLBACK` lists below are used only
|
|
9
|
+
* when discovery is unreachable (no key yet, or a network error), so the server
|
|
10
|
+
* still starts and advertises a sensible default surface.
|
|
11
|
+
*
|
|
12
|
+
* Grouping (v1 generate-tool scope):
|
|
13
|
+
* - image: contentType=image, kind=generate (upscalers are kind=upscale)
|
|
14
|
+
* - video: contentType=video, kind=generate (excludes upscale + lip-sync)
|
|
15
|
+
* - audio: contentType=audio, kind=generate, outputType=audio (TTS/music/sfx;
|
|
16
|
+
* excludes transcribe, which outputs text, and the voice utilities)
|
|
17
|
+
* - upscale: kind=upscale (image or video), surfaced as the dedicated `upscale`
|
|
18
|
+
* tool rather than mixed into the generate tools
|
|
19
|
+
* - lipSync: kind=lip-sync (Wavespeed talking-head), surfaced as the dedicated
|
|
20
|
+
* `generate_lip_sync` tool (a portrait + audio/script, not prompt-led)
|
|
21
|
+
*/
|
|
22
|
+
import type { ContentHero } from '@contenthero/sdk';
|
|
23
|
+
/** Fallback image-generation models (used only if discovery is unreachable). */
|
|
24
|
+
export declare const IMAGE_MODELS_FALLBACK: readonly ["nano-banana-2", "nano-banana", "nano-banana-pro", "seedream-5-lite", "gpt-image-2", "flux-2-pro", "flux-1-kontext"];
|
|
25
|
+
/** Fallback video-generation models (used only if discovery is unreachable). */
|
|
26
|
+
export declare const VIDEO_MODELS_FALLBACK: readonly ["veo-3.1-fast", "veo-3.1-quality", "seedance-2", "seedance-2-fast", "kling-3.0", "kling-2.6", "kling-3.0-motion-control", "kling-2.6-motion-control", "wan-2.6"];
|
|
27
|
+
/** Fallback audio-generation models (used only if discovery is unreachable). */
|
|
28
|
+
export declare const AUDIO_MODELS_FALLBACK: readonly ["elevenlabs-tts", "elevenlabs-music", "elevenlabs-sound-effects"];
|
|
29
|
+
/** Fallback upscale models (used only if discovery is unreachable). */
|
|
30
|
+
export declare const UPSCALE_MODELS_FALLBACK: readonly ["topaz-image-upscale", "topaz-video-upscale"];
|
|
31
|
+
/** Fallback lip-sync models (used only if discovery is unreachable). */
|
|
32
|
+
export declare const LIP_SYNC_MODELS_FALLBACK: readonly ["infinitalk", "infinitalk-fast", "kling-ai-avatar"];
|
|
33
|
+
/** A non-empty model-id tuple, the shape `z.enum` requires. */
|
|
34
|
+
export type ModelEnum = [string, ...string[]];
|
|
35
|
+
export interface ResolvedModelEnums {
|
|
36
|
+
image: ModelEnum;
|
|
37
|
+
video: ModelEnum;
|
|
38
|
+
audio: ModelEnum;
|
|
39
|
+
upscale: ModelEnum;
|
|
40
|
+
lipSync: ModelEnum;
|
|
41
|
+
/** Maps each upscale modelId to its source media kind (image vs video). */
|
|
42
|
+
upscaleContentType: Record<string, 'image' | 'video'>;
|
|
43
|
+
}
|
|
44
|
+
/**
|
|
45
|
+
* Build the three per-tool model enums from the live discovery catalog, falling
|
|
46
|
+
* back to the static lists on any failure (missing key, network error, empty
|
|
47
|
+
* result). Never throws: the server must always start.
|
|
48
|
+
*/
|
|
49
|
+
export declare function resolveModelEnums(getClient: () => ContentHero): Promise<ResolvedModelEnums>;
|
|
50
|
+
/** Short selection guidance baked into each generate tool's modelId description. */
|
|
51
|
+
export declare const IMAGE_MODEL_GUIDANCE = "nano-banana-2 = strong general default (1K/2K/4K). gpt-image-2 = best text rendering. flux-2-pro / seedream-5-lite / nano-banana-pro = alternatives. Pass referenceImages for image-to-image / editing.";
|
|
52
|
+
export declare const VIDEO_MODEL_GUIDANCE = "veo-3.1-fast / veo-3.1-quality = high quality clips with audio. seedance-2 / seedance-2-fast = multimodal references. kling-3.0 / kling-2.6 = strong motion. wan-2.6 = alternative. The motion-control variants require an input image plus an input video.";
|
|
53
|
+
export declare const AUDIO_MODEL_GUIDANCE = "elevenlabs-tts = text to speech (needs text + voiceId). elevenlabs-music = music from a prompt. elevenlabs-sound-effects = a sound effect from a prompt.";
|
|
54
|
+
export declare const UPSCALE_MODEL_GUIDANCE = "topaz-image-upscale = upscale an image (source must be an image URL). topaz-video-upscale = upscale a video (source must be a video URL; also pass durationSeconds).";
|
|
55
|
+
export declare const LIP_SYNC_MODEL_GUIDANCE = "infinitalk = talking-head lip-sync (480p/720p). infinitalk-fast = faster, cheaper. kling-ai-avatar = Kling avatar (720p/1080p). All take a portrait image plus either an audio clip or a script + voiceId.";
|
|
56
|
+
//# sourceMappingURL=models.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"models.d.ts","sourceRoot":"","sources":["../src/models.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;GAoBG;AAEH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAA;AAEnD,gFAAgF;AAChF,eAAO,MAAM,qBAAqB,gIAQxB,CAAA;AAEV,gFAAgF;AAChF,eAAO,MAAM,qBAAqB,4KAUxB,CAAA;AAEV,gFAAgF;AAChF,eAAO,MAAM,qBAAqB,6EAIxB,CAAA;AAEV,uEAAuE;AACvE,eAAO,MAAM,uBAAuB,yDAA0D,CAAA;AAE9F,wEAAwE;AACxE,eAAO,MAAM,wBAAwB,+DAAgE,CAAA;AAQrG,+DAA+D;AAC/D,MAAM,MAAM,SAAS,GAAG,CAAC,MAAM,EAAE,GAAG,MAAM,EAAE,CAAC,CAAA;AAE7C,MAAM,WAAW,kBAAkB;IACjC,KAAK,EAAE,SAAS,CAAA;IAChB,KAAK,EAAE,SAAS,CAAA;IAChB,KAAK,EAAE,SAAS,CAAA;IAChB,OAAO,EAAE,SAAS,CAAA;IAClB,OAAO,EAAE,SAAS,CAAA;IAClB,2EAA2E;IAC3E,kBAAkB,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,GAAG,OAAO,CAAC,CAAA;CACtD;AAMD;;;;GAIG;AACH,wBAAsB,iBAAiB,CAAC,SAAS,EAAE,MAAM,WAAW,GAAG,OAAO,CAAC,kBAAkB,CAAC,CA2CjG;AAED,oFAAoF;AACpF,eAAO,MAAM,oBAAoB,4MAC0K,CAAA;AAE3M,eAAO,MAAM,oBAAoB,gQAC8N,CAAA;AAE/P,eAAO,MAAM,oBAAoB,6JAC2H,CAAA;AAE5J,eAAO,MAAM,sBAAsB,yKACqI,CAAA;AAExK,eAAO,MAAM,uBAAuB,+MAC0K,CAAA"}
|
package/dist/models.js
ADDED
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Per-tool model lists, resolved dynamically from the discovery endpoint.
|
|
3
|
+
*
|
|
4
|
+
* `resolveModelEnums` fetches `GET /api/v1/models` (via the SDK) once at server
|
|
5
|
+
* startup and groups the enabled models into the three generate tools by their
|
|
6
|
+
* registry `kind`. So the model a tool offers always tracks the admin
|
|
7
|
+
* switchboard: enable a model in the app and it appears here on the next restart,
|
|
8
|
+
* with no package change. The hardcoded `*_FALLBACK` lists below are used only
|
|
9
|
+
* when discovery is unreachable (no key yet, or a network error), so the server
|
|
10
|
+
* still starts and advertises a sensible default surface.
|
|
11
|
+
*
|
|
12
|
+
* Grouping (v1 generate-tool scope):
|
|
13
|
+
* - image: contentType=image, kind=generate (upscalers are kind=upscale)
|
|
14
|
+
* - video: contentType=video, kind=generate (excludes upscale + lip-sync)
|
|
15
|
+
* - audio: contentType=audio, kind=generate, outputType=audio (TTS/music/sfx;
|
|
16
|
+
* excludes transcribe, which outputs text, and the voice utilities)
|
|
17
|
+
* - upscale: kind=upscale (image or video), surfaced as the dedicated `upscale`
|
|
18
|
+
* tool rather than mixed into the generate tools
|
|
19
|
+
* - lipSync: kind=lip-sync (Wavespeed talking-head), surfaced as the dedicated
|
|
20
|
+
* `generate_lip_sync` tool (a portrait + audio/script, not prompt-led)
|
|
21
|
+
*/
|
|
22
|
+
/** Fallback image-generation models (used only if discovery is unreachable). */
|
|
23
|
+
export const IMAGE_MODELS_FALLBACK = [
|
|
24
|
+
'nano-banana-2',
|
|
25
|
+
'nano-banana',
|
|
26
|
+
'nano-banana-pro',
|
|
27
|
+
'seedream-5-lite',
|
|
28
|
+
'gpt-image-2',
|
|
29
|
+
'flux-2-pro',
|
|
30
|
+
'flux-1-kontext',
|
|
31
|
+
];
|
|
32
|
+
/** Fallback video-generation models (used only if discovery is unreachable). */
|
|
33
|
+
export const VIDEO_MODELS_FALLBACK = [
|
|
34
|
+
'veo-3.1-fast',
|
|
35
|
+
'veo-3.1-quality',
|
|
36
|
+
'seedance-2',
|
|
37
|
+
'seedance-2-fast',
|
|
38
|
+
'kling-3.0',
|
|
39
|
+
'kling-2.6',
|
|
40
|
+
'kling-3.0-motion-control',
|
|
41
|
+
'kling-2.6-motion-control',
|
|
42
|
+
'wan-2.6',
|
|
43
|
+
];
|
|
44
|
+
/** Fallback audio-generation models (used only if discovery is unreachable). */
|
|
45
|
+
export const AUDIO_MODELS_FALLBACK = [
|
|
46
|
+
'elevenlabs-tts',
|
|
47
|
+
'elevenlabs-music',
|
|
48
|
+
'elevenlabs-sound-effects',
|
|
49
|
+
];
|
|
50
|
+
/** Fallback upscale models (used only if discovery is unreachable). */
|
|
51
|
+
export const UPSCALE_MODELS_FALLBACK = ['topaz-image-upscale', 'topaz-video-upscale'];
|
|
52
|
+
/** Fallback lip-sync models (used only if discovery is unreachable). */
|
|
53
|
+
export const LIP_SYNC_MODELS_FALLBACK = ['infinitalk', 'infinitalk-fast', 'kling-ai-avatar'];
|
|
54
|
+
/** Source media kind per upscale model (used to route the source URL + duration). */
|
|
55
|
+
const UPSCALE_CONTENT_TYPE_FALLBACK = {
|
|
56
|
+
'topaz-image-upscale': 'image',
|
|
57
|
+
'topaz-video-upscale': 'video',
|
|
58
|
+
};
|
|
59
|
+
function nonEmpty(ids, fallback) {
|
|
60
|
+
return (ids.length > 0 ? ids : [...fallback]);
|
|
61
|
+
}
|
|
62
|
+
/**
|
|
63
|
+
* Build the three per-tool model enums from the live discovery catalog, falling
|
|
64
|
+
* back to the static lists on any failure (missing key, network error, empty
|
|
65
|
+
* result). Never throws: the server must always start.
|
|
66
|
+
*/
|
|
67
|
+
export async function resolveModelEnums(getClient) {
|
|
68
|
+
try {
|
|
69
|
+
const models = await getClient().listModels();
|
|
70
|
+
const image = models
|
|
71
|
+
.filter((m) => m.contentType === 'image' && m.kind === 'generate')
|
|
72
|
+
.map((m) => m.modelId);
|
|
73
|
+
const video = models
|
|
74
|
+
.filter((m) => m.contentType === 'video' && m.kind === 'generate')
|
|
75
|
+
.map((m) => m.modelId);
|
|
76
|
+
const audio = models
|
|
77
|
+
.filter((m) => m.contentType === 'audio' &&
|
|
78
|
+
m.kind === 'generate' &&
|
|
79
|
+
m.capabilities?.outputType === 'audio')
|
|
80
|
+
.map((m) => m.modelId);
|
|
81
|
+
const upscaleModels = models.filter((m) => m.kind === 'upscale');
|
|
82
|
+
const upscale = upscaleModels.map((m) => m.modelId);
|
|
83
|
+
const upscaleContentType = {};
|
|
84
|
+
for (const m of upscaleModels) {
|
|
85
|
+
upscaleContentType[m.modelId] = m.contentType === 'video' ? 'video' : 'image';
|
|
86
|
+
}
|
|
87
|
+
const lipSync = models.filter((m) => m.kind === 'lip-sync').map((m) => m.modelId);
|
|
88
|
+
return {
|
|
89
|
+
image: nonEmpty(image, IMAGE_MODELS_FALLBACK),
|
|
90
|
+
video: nonEmpty(video, VIDEO_MODELS_FALLBACK),
|
|
91
|
+
audio: nonEmpty(audio, AUDIO_MODELS_FALLBACK),
|
|
92
|
+
upscale: nonEmpty(upscale, UPSCALE_MODELS_FALLBACK),
|
|
93
|
+
lipSync: nonEmpty(lipSync, LIP_SYNC_MODELS_FALLBACK),
|
|
94
|
+
upscaleContentType: upscale.length > 0 ? upscaleContentType : { ...UPSCALE_CONTENT_TYPE_FALLBACK },
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
catch {
|
|
98
|
+
return {
|
|
99
|
+
image: [...IMAGE_MODELS_FALLBACK],
|
|
100
|
+
video: [...VIDEO_MODELS_FALLBACK],
|
|
101
|
+
audio: [...AUDIO_MODELS_FALLBACK],
|
|
102
|
+
upscale: [...UPSCALE_MODELS_FALLBACK],
|
|
103
|
+
lipSync: [...LIP_SYNC_MODELS_FALLBACK],
|
|
104
|
+
upscaleContentType: { ...UPSCALE_CONTENT_TYPE_FALLBACK },
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
}
|
|
108
|
+
/** Short selection guidance baked into each generate tool's modelId description. */
|
|
109
|
+
export const IMAGE_MODEL_GUIDANCE = 'nano-banana-2 = strong general default (1K/2K/4K). gpt-image-2 = best text rendering. flux-2-pro / seedream-5-lite / nano-banana-pro = alternatives. Pass referenceImages for image-to-image / editing.';
|
|
110
|
+
export const VIDEO_MODEL_GUIDANCE = 'veo-3.1-fast / veo-3.1-quality = high quality clips with audio. seedance-2 / seedance-2-fast = multimodal references. kling-3.0 / kling-2.6 = strong motion. wan-2.6 = alternative. The motion-control variants require an input image plus an input video.';
|
|
111
|
+
export const AUDIO_MODEL_GUIDANCE = 'elevenlabs-tts = text to speech (needs text + voiceId). elevenlabs-music = music from a prompt. elevenlabs-sound-effects = a sound effect from a prompt.';
|
|
112
|
+
export const UPSCALE_MODEL_GUIDANCE = 'topaz-image-upscale = upscale an image (source must be an image URL). topaz-video-upscale = upscale a video (source must be a video URL; also pass durationSeconds).';
|
|
113
|
+
export const LIP_SYNC_MODEL_GUIDANCE = 'infinitalk = talking-head lip-sync (480p/720p). infinitalk-fast = faster, cheaper. kling-ai-avatar = Kling avatar (720p/1080p). All take a portrait image plus either an audio clip or a script + voiceId.';
|
|
114
|
+
//# sourceMappingURL=models.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"models.js","sourceRoot":"","sources":["../src/models.ts"],"names":[],"mappings":"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"}
|
package/dist/server.d.ts
ADDED
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The ContentHero MCP server: intent-shaped tools over the @contenthero/sdk kernel.
|
|
3
|
+
*
|
|
4
|
+
* generate_image - smart-wait, image models
|
|
5
|
+
* generate_video - smart-wait, video models
|
|
6
|
+
* generate_audio - synchronous (ElevenLabs), no polling
|
|
7
|
+
* upscale - smart-wait, image/video upscalers
|
|
8
|
+
* generate_lip_sync - smart-wait, talking-head lip-sync (portrait + audio/script)
|
|
9
|
+
* transcribe - synchronous speech-to-text (audio URL -> transcript)
|
|
10
|
+
* list_avatars / get_avatar - the account's avatars (base look + default voice)
|
|
11
|
+
* list_voices / get_voice - the account's saved voices
|
|
12
|
+
* list_brand_kits / get_brand_kit - the account's brand kits (full brand context)
|
|
13
|
+
* list_media / get_media - the account's studio outputs (+ per-variation ids)
|
|
14
|
+
* check_generation - poll an image/video outputId to its final URLs
|
|
15
|
+
* get_balance - credit balance + tier
|
|
16
|
+
*
|
|
17
|
+
* Intent-shaped generate tools rather than one generate_media: each operation
|
|
18
|
+
* (generate / upscale / lip-sync) gets a tool whose schema only carries its own
|
|
19
|
+
* fields, and per-tool modelId enums prevent cross-type model misuse. Image and
|
|
20
|
+
* video share the async smart-wait lifecycle; audio shares almost no parameters
|
|
21
|
+
* and runs synchronously.
|
|
22
|
+
*/
|
|
23
|
+
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
24
|
+
import { ContentHero } from '@contenthero/sdk';
|
|
25
|
+
export interface BuildServerOptions {
|
|
26
|
+
/** Override the SDK client (for tests). Defaults to the env-configured client. */
|
|
27
|
+
getClient?: () => ContentHero;
|
|
28
|
+
}
|
|
29
|
+
export declare function buildServer(options?: BuildServerOptions): Promise<McpServer>;
|
|
30
|
+
//# sourceMappingURL=server.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAEH,OAAO,EAAE,SAAS,EAAE,MAAM,yCAAyC,CAAA;AAEnE,OAAO,EACL,WAAW,EAIZ,MAAM,kBAAkB,CAAA;AAsCzB,MAAM,WAAW,kBAAkB;IACjC,kFAAkF;IAClF,SAAS,CAAC,EAAE,MAAM,WAAW,CAAA;CAC9B;AAYD,wBAAsB,WAAW,CAAC,OAAO,GAAE,kBAAuB,GAAG,OAAO,CAAC,SAAS,CAAC,CAietF"}
|
package/dist/server.js
ADDED
|
@@ -0,0 +1,451 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The ContentHero MCP server: intent-shaped tools over the @contenthero/sdk kernel.
|
|
3
|
+
*
|
|
4
|
+
* generate_image - smart-wait, image models
|
|
5
|
+
* generate_video - smart-wait, video models
|
|
6
|
+
* generate_audio - synchronous (ElevenLabs), no polling
|
|
7
|
+
* upscale - smart-wait, image/video upscalers
|
|
8
|
+
* generate_lip_sync - smart-wait, talking-head lip-sync (portrait + audio/script)
|
|
9
|
+
* transcribe - synchronous speech-to-text (audio URL -> transcript)
|
|
10
|
+
* list_avatars / get_avatar - the account's avatars (base look + default voice)
|
|
11
|
+
* list_voices / get_voice - the account's saved voices
|
|
12
|
+
* list_brand_kits / get_brand_kit - the account's brand kits (full brand context)
|
|
13
|
+
* list_media / get_media - the account's studio outputs (+ per-variation ids)
|
|
14
|
+
* check_generation - poll an image/video outputId to its final URLs
|
|
15
|
+
* get_balance - credit balance + tier
|
|
16
|
+
*
|
|
17
|
+
* Intent-shaped generate tools rather than one generate_media: each operation
|
|
18
|
+
* (generate / upscale / lip-sync) gets a tool whose schema only carries its own
|
|
19
|
+
* fields, and per-tool modelId enums prevent cross-type model misuse. Image and
|
|
20
|
+
* video share the async smart-wait lifecycle; audio shares almost no parameters
|
|
21
|
+
* and runs synchronously.
|
|
22
|
+
*/
|
|
23
|
+
import { McpServer } from '@modelcontextprotocol/sdk/server/mcp.js';
|
|
24
|
+
import { z } from 'zod';
|
|
25
|
+
import { GenerationTimeoutError, } from '@contenthero/sdk';
|
|
26
|
+
import { getClient as defaultGetClient } from './client.js';
|
|
27
|
+
import { resolveModelEnums, IMAGE_MODEL_GUIDANCE, VIDEO_MODEL_GUIDANCE, AUDIO_MODEL_GUIDANCE, UPSCALE_MODEL_GUIDANCE, LIP_SYNC_MODEL_GUIDANCE, } from './models.js';
|
|
28
|
+
import { audioResult, avatarListResult, avatarResult, balanceResult, brandKitListResult, brandKitResult, completedResult, mediaListResult, mediaResult, errorResult, generationStatusResult, pendingResult, transcriptResult, voiceListResult, voiceResult, } from './format.js';
|
|
29
|
+
/**
|
|
30
|
+
* How long the smart-wait tools (generate_image / generate_video / upscale /
|
|
31
|
+
* generate_lip_sync) wait inline before handing back the outputId to poll.
|
|
32
|
+
* Kept under the MCP SDK's default 60s client request timeout, so a slow render
|
|
33
|
+
* returns the clean "still rendering, call check_generation" handoff rather than
|
|
34
|
+
* tripping the client's timeout. Comfortably covers images (~15-30s); slower
|
|
35
|
+
* video/lip-sync jobs return the pollable pending result.
|
|
36
|
+
*/
|
|
37
|
+
const SMART_WAIT_MS = 50_000;
|
|
38
|
+
/** Drop undefined values so the request payload stays minimal. */
|
|
39
|
+
function compact(obj) {
|
|
40
|
+
return Object.fromEntries(Object.entries(obj).filter(([, v]) => v !== undefined));
|
|
41
|
+
}
|
|
42
|
+
function buildReferences(parts) {
|
|
43
|
+
const refs = compact(parts);
|
|
44
|
+
return Object.keys(refs).length > 0 ? refs : undefined;
|
|
45
|
+
}
|
|
46
|
+
export async function buildServer(options = {}) {
|
|
47
|
+
const getClient = options.getClient ?? defaultGetClient;
|
|
48
|
+
// Resolve the per-tool model enums from the live discovery catalog (falls back
|
|
49
|
+
// to static lists if discovery is unreachable). Done once at startup, since
|
|
50
|
+
// tool schemas are advertised once; a restart picks up admin-switchboard changes.
|
|
51
|
+
const models = await resolveModelEnums(getClient);
|
|
52
|
+
const server = new McpServer({ name: 'contenthero', version: '0.1.0' });
|
|
53
|
+
// -- generate_image -------------------------------------------------------
|
|
54
|
+
server.registerTool('generate_image', {
|
|
55
|
+
title: 'Generate Image',
|
|
56
|
+
description: 'Generate one or more images from a text prompt (optionally image-to-image with reference images). Waits for the result and returns the image URLs.',
|
|
57
|
+
inputSchema: {
|
|
58
|
+
modelId: z.enum(models.image).describe(IMAGE_MODEL_GUIDANCE),
|
|
59
|
+
prompt: z
|
|
60
|
+
.string()
|
|
61
|
+
.optional()
|
|
62
|
+
.describe('Describe the image to generate. Required for most models; optional for a few that can run from references alone.'),
|
|
63
|
+
aspectRatio: z.string().optional().describe('e.g. 16:9, 1:1, 9:16. Validated per model.'),
|
|
64
|
+
resolution: z.string().optional().describe('e.g. 1K, 2K, 4K. Model-dependent.'),
|
|
65
|
+
quality: z.string().optional().describe('GPT Image models only: high or medium.'),
|
|
66
|
+
numImages: z.number().int().min(1).max(4).optional().describe('Number of variations (1-4).'),
|
|
67
|
+
seed: z.number().int().optional().describe('Seed for reproducibility.'),
|
|
68
|
+
referenceImages: z
|
|
69
|
+
.array(z.string())
|
|
70
|
+
.optional()
|
|
71
|
+
.describe('References for image-to-image / editing. Each may be a URL or a previous output id (e.g. "<id>" or "<id>-2") to chain from an earlier generation.'),
|
|
72
|
+
},
|
|
73
|
+
}, async (args) => {
|
|
74
|
+
try {
|
|
75
|
+
const request = compact({
|
|
76
|
+
contentType: 'image',
|
|
77
|
+
modelId: args.modelId,
|
|
78
|
+
prompt: args.prompt,
|
|
79
|
+
aspectRatio: args.aspectRatio,
|
|
80
|
+
resolution: args.resolution,
|
|
81
|
+
quality: args.quality,
|
|
82
|
+
numImages: args.numImages,
|
|
83
|
+
seed: args.seed,
|
|
84
|
+
references: buildReferences({ images: args.referenceImages }),
|
|
85
|
+
});
|
|
86
|
+
const gen = await getClient().generateAndWait(request, { timeoutMs: SMART_WAIT_MS });
|
|
87
|
+
return completedResult(gen);
|
|
88
|
+
}
|
|
89
|
+
catch (err) {
|
|
90
|
+
if (err instanceof GenerationTimeoutError)
|
|
91
|
+
return pendingResult(err.outputId);
|
|
92
|
+
return errorResult(err);
|
|
93
|
+
}
|
|
94
|
+
});
|
|
95
|
+
// -- generate_video -------------------------------------------------------
|
|
96
|
+
server.registerTool('generate_video', {
|
|
97
|
+
title: 'Generate Video',
|
|
98
|
+
description: 'Generate a video from a text prompt (optionally from a start/end frame or reference images/videos). Waits up to ~50s; if the render is still running it returns an outputId to poll with check_generation.',
|
|
99
|
+
inputSchema: {
|
|
100
|
+
modelId: z.enum(models.video).describe(VIDEO_MODEL_GUIDANCE),
|
|
101
|
+
prompt: z
|
|
102
|
+
.string()
|
|
103
|
+
.optional()
|
|
104
|
+
.describe('Describe the video to generate. Required for most models; optional for some (e.g. motion-control), where it is an auxiliary motion hint.'),
|
|
105
|
+
aspectRatio: z.string().optional().describe('e.g. 16:9, 9:16. Validated per model.'),
|
|
106
|
+
resolution: z.string().optional().describe('e.g. 720p, 1080p, 4K. Model-dependent.'),
|
|
107
|
+
duration: z
|
|
108
|
+
.number()
|
|
109
|
+
.optional()
|
|
110
|
+
.describe('Clip length in seconds. Model-dependent; some models lock it.'),
|
|
111
|
+
audioEnabled: z
|
|
112
|
+
.boolean()
|
|
113
|
+
.optional()
|
|
114
|
+
.describe('Generate audio (only for models that support it).'),
|
|
115
|
+
numGenerations: z.number().int().min(1).max(4).optional().describe('Number of variations (1-4).'),
|
|
116
|
+
negativePrompt: z.string().optional().describe('What to avoid (models that support it).'),
|
|
117
|
+
seed: z.number().int().optional().describe('Seed for reproducibility.'),
|
|
118
|
+
startFrame: z.string().optional().describe('First frame: an image URL or a previous output id (e.g. "<id>-2") to chain (e.g. animate an image you just generated).'),
|
|
119
|
+
endFrame: z.string().optional().describe('Last frame: an image URL or a previous output id.'),
|
|
120
|
+
referenceImages: z.array(z.string()).optional().describe('Reference images: each a URL or a previous output id to chain.'),
|
|
121
|
+
referenceVideos: z.array(z.string()).optional().describe('Reference videos: each a URL or a previous output id to chain.'),
|
|
122
|
+
},
|
|
123
|
+
}, async (args) => {
|
|
124
|
+
try {
|
|
125
|
+
const request = compact({
|
|
126
|
+
contentType: 'video',
|
|
127
|
+
modelId: args.modelId,
|
|
128
|
+
prompt: args.prompt,
|
|
129
|
+
aspectRatio: args.aspectRatio,
|
|
130
|
+
resolution: args.resolution,
|
|
131
|
+
duration: args.duration,
|
|
132
|
+
audioEnabled: args.audioEnabled,
|
|
133
|
+
numGenerations: args.numGenerations,
|
|
134
|
+
negativePrompt: args.negativePrompt,
|
|
135
|
+
seed: args.seed,
|
|
136
|
+
references: buildReferences({
|
|
137
|
+
startFrame: args.startFrame,
|
|
138
|
+
endFrame: args.endFrame,
|
|
139
|
+
images: args.referenceImages,
|
|
140
|
+
videos: args.referenceVideos,
|
|
141
|
+
}),
|
|
142
|
+
});
|
|
143
|
+
const gen = await getClient().generateAndWait(request, { timeoutMs: SMART_WAIT_MS });
|
|
144
|
+
return completedResult(gen);
|
|
145
|
+
}
|
|
146
|
+
catch (err) {
|
|
147
|
+
if (err instanceof GenerationTimeoutError)
|
|
148
|
+
return pendingResult(err.outputId);
|
|
149
|
+
return errorResult(err);
|
|
150
|
+
}
|
|
151
|
+
});
|
|
152
|
+
// -- generate_audio (synchronous) -----------------------------------------
|
|
153
|
+
server.registerTool('generate_audio', {
|
|
154
|
+
title: 'Generate Audio',
|
|
155
|
+
description: 'Generate audio with ElevenLabs: speech (TTS), music, or a sound effect. Returns the audio URL directly (synchronous, no polling).',
|
|
156
|
+
inputSchema: {
|
|
157
|
+
modelId: z.enum(models.audio).describe(AUDIO_MODEL_GUIDANCE),
|
|
158
|
+
prompt: z.string().optional().describe('For music / sfx: what to generate.'),
|
|
159
|
+
text: z.string().optional().describe('For TTS (elevenlabs-tts): the words to speak.'),
|
|
160
|
+
voiceId: z.string().optional().describe('For TTS: the ElevenLabs voice id.'),
|
|
161
|
+
voiceName: z.string().optional().describe('For TTS: human-readable voice name (display only).'),
|
|
162
|
+
durationSeconds: z.number().optional().describe('For music / sfx: length in seconds.'),
|
|
163
|
+
promptInfluence: z
|
|
164
|
+
.number()
|
|
165
|
+
.min(0)
|
|
166
|
+
.max(1)
|
|
167
|
+
.optional()
|
|
168
|
+
.describe('For sfx: how literally to follow the prompt (0 to 1).'),
|
|
169
|
+
},
|
|
170
|
+
}, async (args) => {
|
|
171
|
+
try {
|
|
172
|
+
const request = compact({
|
|
173
|
+
contentType: 'audio',
|
|
174
|
+
modelId: args.modelId,
|
|
175
|
+
prompt: args.prompt,
|
|
176
|
+
text: args.text,
|
|
177
|
+
voiceId: args.voiceId,
|
|
178
|
+
voiceName: args.voiceName,
|
|
179
|
+
durationSeconds: args.durationSeconds,
|
|
180
|
+
promptInfluence: args.promptInfluence,
|
|
181
|
+
});
|
|
182
|
+
const result = await getClient().generate(request);
|
|
183
|
+
return audioResult(result);
|
|
184
|
+
}
|
|
185
|
+
catch (err) {
|
|
186
|
+
return errorResult(err);
|
|
187
|
+
}
|
|
188
|
+
});
|
|
189
|
+
// -- upscale --------------------------------------------------------------
|
|
190
|
+
server.registerTool('upscale', {
|
|
191
|
+
title: 'Upscale',
|
|
192
|
+
description: 'Upscale an existing image or video to a higher resolution. Provide the source media URL and a model-supported factor. Waits for the result; if the job is still running it returns an outputId to poll with check_generation.',
|
|
193
|
+
inputSchema: {
|
|
194
|
+
modelId: z.enum(models.upscale).describe(UPSCALE_MODEL_GUIDANCE),
|
|
195
|
+
sourceUrl: z.string().describe('The source image (image upscalers) or video (video upscalers): a URL or a previous output id (e.g. "<id>-1") to upscale an earlier generation.'),
|
|
196
|
+
factor: z.string().describe('Upscale factor, e.g. 2x, 4x. Model-dependent; validated per model.'),
|
|
197
|
+
durationSeconds: z
|
|
198
|
+
.number()
|
|
199
|
+
.optional()
|
|
200
|
+
.describe('Required for video upscalers: the source video length in seconds (used for pricing).'),
|
|
201
|
+
},
|
|
202
|
+
}, async (args) => {
|
|
203
|
+
try {
|
|
204
|
+
const isVideo = models.upscaleContentType[args.modelId] === 'video';
|
|
205
|
+
const request = compact({
|
|
206
|
+
contentType: isVideo ? 'video' : 'image',
|
|
207
|
+
modelId: args.modelId,
|
|
208
|
+
upscaleFactor: args.factor,
|
|
209
|
+
duration: isVideo ? args.durationSeconds : undefined,
|
|
210
|
+
references: isVideo ? { videos: [args.sourceUrl] } : { images: [args.sourceUrl] },
|
|
211
|
+
});
|
|
212
|
+
const gen = await getClient().generateAndWait(request, { timeoutMs: SMART_WAIT_MS });
|
|
213
|
+
return completedResult(gen);
|
|
214
|
+
}
|
|
215
|
+
catch (err) {
|
|
216
|
+
if (err instanceof GenerationTimeoutError)
|
|
217
|
+
return pendingResult(err.outputId);
|
|
218
|
+
return errorResult(err);
|
|
219
|
+
}
|
|
220
|
+
});
|
|
221
|
+
// -- generate_lip_sync ----------------------------------------------------
|
|
222
|
+
server.registerTool('generate_lip_sync', {
|
|
223
|
+
title: 'Generate Lip Sync',
|
|
224
|
+
description: 'Animate a portrait image so the subject speaks. Provide imageUrl (the face) plus a voice source: either audioUrl (an existing speech clip) or script + voiceId (we synthesize the speech). Optional motionPrompt nudges expression/motion. Waits up to ~50s; if still rendering it returns an outputId to poll with check_generation.',
|
|
225
|
+
inputSchema: {
|
|
226
|
+
modelId: z.enum(models.lipSync).describe(LIP_SYNC_MODEL_GUIDANCE),
|
|
227
|
+
imageUrl: z.string().describe('The portrait to animate (the speaking subject): an image URL or a previous output id (e.g. "<id>-1") to chain.'),
|
|
228
|
+
audioUrl: z
|
|
229
|
+
.string()
|
|
230
|
+
.optional()
|
|
231
|
+
.describe('An existing speech clip: an audio URL or a previous output id. Use this OR script + voiceId.'),
|
|
232
|
+
script: z
|
|
233
|
+
.string()
|
|
234
|
+
.optional()
|
|
235
|
+
.describe('Text for the subject to speak. Requires voiceId; synthesized to speech. Use this OR audioUrl.'),
|
|
236
|
+
voiceId: z.string().optional().describe('ElevenLabs voice id to speak the script (required with script).'),
|
|
237
|
+
voiceName: z.string().optional().describe('Human-readable voice name (display only).'),
|
|
238
|
+
motionPrompt: z
|
|
239
|
+
.string()
|
|
240
|
+
.optional()
|
|
241
|
+
.describe('Optional motion / expression hint for the animation.'),
|
|
242
|
+
resolution: z.string().optional().describe('e.g. 480p, 720p, 1080p. Model-dependent.'),
|
|
243
|
+
audioDurationSeconds: z
|
|
244
|
+
.number()
|
|
245
|
+
.optional()
|
|
246
|
+
.describe('Length of audioUrl in seconds (audio mode only; improves cost accuracy).'),
|
|
247
|
+
},
|
|
248
|
+
}, async (args) => {
|
|
249
|
+
try {
|
|
250
|
+
const request = compact({
|
|
251
|
+
contentType: 'video',
|
|
252
|
+
modelId: args.modelId,
|
|
253
|
+
prompt: args.motionPrompt,
|
|
254
|
+
text: args.script,
|
|
255
|
+
voiceId: args.voiceId,
|
|
256
|
+
voiceName: args.voiceName,
|
|
257
|
+
resolution: args.resolution,
|
|
258
|
+
durationSeconds: args.audioDurationSeconds,
|
|
259
|
+
references: buildReferences({
|
|
260
|
+
images: [args.imageUrl],
|
|
261
|
+
audio: args.audioUrl ? [args.audioUrl] : undefined,
|
|
262
|
+
}),
|
|
263
|
+
});
|
|
264
|
+
const gen = await getClient().generateAndWait(request, { timeoutMs: SMART_WAIT_MS });
|
|
265
|
+
return completedResult(gen);
|
|
266
|
+
}
|
|
267
|
+
catch (err) {
|
|
268
|
+
if (err instanceof GenerationTimeoutError)
|
|
269
|
+
return pendingResult(err.outputId);
|
|
270
|
+
return errorResult(err);
|
|
271
|
+
}
|
|
272
|
+
});
|
|
273
|
+
// -- transcribe -----------------------------------------------------------
|
|
274
|
+
server.registerTool('transcribe', {
|
|
275
|
+
title: 'Transcribe Audio',
|
|
276
|
+
description: 'Transcribe an audio URL to text (speech-to-text). Returns the transcript directly (synchronous, free, no polling).',
|
|
277
|
+
inputSchema: {
|
|
278
|
+
audioUrl: z.string().describe('Public URL of the audio file to transcribe.'),
|
|
279
|
+
languageCode: z
|
|
280
|
+
.string()
|
|
281
|
+
.optional()
|
|
282
|
+
.describe('ISO language hint, e.g. "en". Auto-detected when omitted.'),
|
|
283
|
+
diarize: z.boolean().optional().describe('Label each speaker (diarization).'),
|
|
284
|
+
},
|
|
285
|
+
}, async (args) => {
|
|
286
|
+
try {
|
|
287
|
+
const t = await getClient().transcribe({
|
|
288
|
+
audioUrl: args.audioUrl,
|
|
289
|
+
languageCode: args.languageCode,
|
|
290
|
+
diarize: args.diarize,
|
|
291
|
+
});
|
|
292
|
+
return transcriptResult(t);
|
|
293
|
+
}
|
|
294
|
+
catch (err) {
|
|
295
|
+
return errorResult(err);
|
|
296
|
+
}
|
|
297
|
+
});
|
|
298
|
+
// -- list_avatars ---------------------------------------------------------
|
|
299
|
+
server.registerTool('list_avatars', {
|
|
300
|
+
title: 'List Avatars',
|
|
301
|
+
description: "List the account's avatars. Each avatar has an imageUrl (its base look) and a defaultVoiceId, which feed generate_lip_sync. Call get_avatar for full detail and the avatar's looks.",
|
|
302
|
+
}, async () => {
|
|
303
|
+
try {
|
|
304
|
+
return avatarListResult(await getClient().listAvatars());
|
|
305
|
+
}
|
|
306
|
+
catch (err) {
|
|
307
|
+
return errorResult(err);
|
|
308
|
+
}
|
|
309
|
+
});
|
|
310
|
+
// -- get_avatar -----------------------------------------------------------
|
|
311
|
+
server.registerTool('get_avatar', {
|
|
312
|
+
title: 'Get Avatar',
|
|
313
|
+
description: 'Get one avatar by id: its base image (use as generate_lip_sync imageUrl), default voice, traits, and its looks (outfit variations).',
|
|
314
|
+
inputSchema: {
|
|
315
|
+
avatarId: z.string().describe('The avatar id from list_avatars.'),
|
|
316
|
+
},
|
|
317
|
+
}, async (args) => {
|
|
318
|
+
try {
|
|
319
|
+
return avatarResult(await getClient().getAvatar(args.avatarId));
|
|
320
|
+
}
|
|
321
|
+
catch (err) {
|
|
322
|
+
return errorResult(err);
|
|
323
|
+
}
|
|
324
|
+
});
|
|
325
|
+
// -- list_voices ----------------------------------------------------------
|
|
326
|
+
server.registerTool('list_voices', {
|
|
327
|
+
title: 'List Voices',
|
|
328
|
+
description: "List the account's saved voices (favorites first). Each has a voiceId for generate_lip_sync / generate_audio (TTS). Call get_voice for full detail.",
|
|
329
|
+
}, async () => {
|
|
330
|
+
try {
|
|
331
|
+
return voiceListResult(await getClient().listVoices());
|
|
332
|
+
}
|
|
333
|
+
catch (err) {
|
|
334
|
+
return errorResult(err);
|
|
335
|
+
}
|
|
336
|
+
});
|
|
337
|
+
// -- get_voice ------------------------------------------------------------
|
|
338
|
+
server.registerTool('get_voice', {
|
|
339
|
+
title: 'Get Voice',
|
|
340
|
+
description: 'Get one voice by its voiceId: provider, traits (accent/language/gender/age), description, and a preview URL.',
|
|
341
|
+
inputSchema: {
|
|
342
|
+
voiceId: z.string().describe('The voice id from list_voices.'),
|
|
343
|
+
},
|
|
344
|
+
}, async (args) => {
|
|
345
|
+
try {
|
|
346
|
+
return voiceResult(await getClient().getVoice(args.voiceId));
|
|
347
|
+
}
|
|
348
|
+
catch (err) {
|
|
349
|
+
return errorResult(err);
|
|
350
|
+
}
|
|
351
|
+
});
|
|
352
|
+
// -- list_brand_kits ------------------------------------------------------
|
|
353
|
+
server.registerTool('list_brand_kits', {
|
|
354
|
+
title: 'List Brand Kits',
|
|
355
|
+
description: "List the account's brand kits (default first). Call get_brand_kit for one kit's full brand context (voice, visual identity, audience, sections, accounts, knowledge) to write on-brand content.",
|
|
356
|
+
}, async () => {
|
|
357
|
+
try {
|
|
358
|
+
return brandKitListResult(await getClient().listBrandKits());
|
|
359
|
+
}
|
|
360
|
+
catch (err) {
|
|
361
|
+
return errorResult(err);
|
|
362
|
+
}
|
|
363
|
+
});
|
|
364
|
+
// -- get_brand_kit --------------------------------------------------------
|
|
365
|
+
server.registerTool('get_brand_kit', {
|
|
366
|
+
title: 'Get Brand Kit',
|
|
367
|
+
description: 'Get one brand kit in full: business overview, positioning, audience, voice profile, visual identity (logos/colors/typography), curated sections, linked brand + inspiration accounts, and a knowledge-base summary. Use it to ground on-brand generation.',
|
|
368
|
+
inputSchema: {
|
|
369
|
+
brandKitId: z.string().describe('The brand kit id from list_brand_kits.'),
|
|
370
|
+
},
|
|
371
|
+
}, async (args) => {
|
|
372
|
+
try {
|
|
373
|
+
return brandKitResult(await getClient().getBrandKit(args.brandKitId));
|
|
374
|
+
}
|
|
375
|
+
catch (err) {
|
|
376
|
+
return errorResult(err);
|
|
377
|
+
}
|
|
378
|
+
});
|
|
379
|
+
// -- list_media -----------------------------------------------------------
|
|
380
|
+
server.registerTool('list_media', {
|
|
381
|
+
title: 'List Media',
|
|
382
|
+
description: "List the account's recent studio outputs (generated images, videos, audio, transcripts), newest first. Each item has an id and its variation URLs. Call get_media for one output's full detail and individual variations.",
|
|
383
|
+
inputSchema: {
|
|
384
|
+
contentType: z
|
|
385
|
+
.enum(['image', 'video', 'audio', 'transcript'])
|
|
386
|
+
.optional()
|
|
387
|
+
.describe('Filter to one media type.'),
|
|
388
|
+
status: z.string().optional().describe("Status filter; defaults to 'completed'."),
|
|
389
|
+
limit: z.number().int().min(1).max(100).optional().describe('How many to return (default 20).'),
|
|
390
|
+
},
|
|
391
|
+
}, async (args) => {
|
|
392
|
+
try {
|
|
393
|
+
return mediaListResult(await getClient().listMedia({
|
|
394
|
+
contentType: args.contentType,
|
|
395
|
+
status: args.status,
|
|
396
|
+
limit: args.limit,
|
|
397
|
+
}));
|
|
398
|
+
}
|
|
399
|
+
catch (err) {
|
|
400
|
+
return errorResult(err);
|
|
401
|
+
}
|
|
402
|
+
});
|
|
403
|
+
// -- get_media ------------------------------------------------------------
|
|
404
|
+
server.registerTool('get_media', {
|
|
405
|
+
title: 'Get Media',
|
|
406
|
+
description: 'Get one studio output by id: its variations (URLs), prompt/script, model, and specs. The id may be the full output id, its first 8 characters, or either with a "-N" suffix to address one variation (1-based, e.g. "...abcd-2"). A whole-output id returns all variations.',
|
|
407
|
+
inputSchema: {
|
|
408
|
+
id: z
|
|
409
|
+
.string()
|
|
410
|
+
.describe('The output id (full or first-8), optionally with a "-N" variation suffix.'),
|
|
411
|
+
},
|
|
412
|
+
}, async (args) => {
|
|
413
|
+
try {
|
|
414
|
+
return mediaResult(await getClient().getMedia(args.id));
|
|
415
|
+
}
|
|
416
|
+
catch (err) {
|
|
417
|
+
return errorResult(err);
|
|
418
|
+
}
|
|
419
|
+
});
|
|
420
|
+
// -- check_generation -----------------------------------------------------
|
|
421
|
+
server.registerTool('check_generation', {
|
|
422
|
+
title: 'Check Generation',
|
|
423
|
+
description: 'Poll an image or video generation by its outputId (returned by generate_image / generate_video when a render is still in progress). Returns the final URLs once complete.',
|
|
424
|
+
inputSchema: {
|
|
425
|
+
outputId: z.string().describe('The outputId from generate_image or generate_video.'),
|
|
426
|
+
},
|
|
427
|
+
}, async (args) => {
|
|
428
|
+
try {
|
|
429
|
+
const gen = await getClient().getGeneration(args.outputId);
|
|
430
|
+
return generationStatusResult(gen);
|
|
431
|
+
}
|
|
432
|
+
catch (err) {
|
|
433
|
+
return errorResult(err);
|
|
434
|
+
}
|
|
435
|
+
});
|
|
436
|
+
// -- get_balance ----------------------------------------------------------
|
|
437
|
+
server.registerTool('get_balance', {
|
|
438
|
+
title: 'Get Balance',
|
|
439
|
+
description: 'Get the current ContentHero credit balance, subscription tier, and auto-top-up state.',
|
|
440
|
+
}, async () => {
|
|
441
|
+
try {
|
|
442
|
+
const balance = await getClient().getBalance();
|
|
443
|
+
return balanceResult(balance);
|
|
444
|
+
}
|
|
445
|
+
catch (err) {
|
|
446
|
+
return errorResult(err);
|
|
447
|
+
}
|
|
448
|
+
});
|
|
449
|
+
return server;
|
|
450
|
+
}
|
|
451
|
+
//# sourceMappingURL=server.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"server.js","sourceRoot":"","sources":["../src/server.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@contenthero/mcp",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "Official ContentHero MCP server. Generate images, video, and audio from any MCP client (Claude Code, Claude Desktop, etc.) using your ContentHero API key.",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"bin": {
|
|
7
|
+
"contenthero-mcp": "./dist/index.js"
|
|
8
|
+
},
|
|
9
|
+
"main": "./dist/index.js",
|
|
10
|
+
"types": "./dist/index.d.ts",
|
|
11
|
+
"files": [
|
|
12
|
+
"dist",
|
|
13
|
+
"README.md"
|
|
14
|
+
],
|
|
15
|
+
"scripts": {
|
|
16
|
+
"build": "tsc",
|
|
17
|
+
"clean": "rm -rf dist",
|
|
18
|
+
"test": "tsx --test \"src/**/*.test.ts\"",
|
|
19
|
+
"prepublishOnly": "npm run clean && npm run build"
|
|
20
|
+
},
|
|
21
|
+
"publishConfig": {
|
|
22
|
+
"access": "public"
|
|
23
|
+
},
|
|
24
|
+
"repository": {
|
|
25
|
+
"type": "git",
|
|
26
|
+
"url": "git+https://github.com/contenthero-ai/contenthero-packages.git",
|
|
27
|
+
"directory": "packages/mcp"
|
|
28
|
+
},
|
|
29
|
+
"keywords": [
|
|
30
|
+
"contenthero",
|
|
31
|
+
"mcp",
|
|
32
|
+
"model-context-protocol",
|
|
33
|
+
"ai",
|
|
34
|
+
"image-generation",
|
|
35
|
+
"video-generation",
|
|
36
|
+
"text-to-speech"
|
|
37
|
+
],
|
|
38
|
+
"engines": {
|
|
39
|
+
"node": ">=20"
|
|
40
|
+
},
|
|
41
|
+
"license": "MIT",
|
|
42
|
+
"private": false,
|
|
43
|
+
"dependencies": {
|
|
44
|
+
"@contenthero/sdk": "^0.1.0",
|
|
45
|
+
"@modelcontextprotocol/sdk": "^1.29.0",
|
|
46
|
+
"zod": "^3.25.76"
|
|
47
|
+
},
|
|
48
|
+
"devDependencies": {
|
|
49
|
+
"@types/node": "^22.19.19",
|
|
50
|
+
"tsx": "^4.22.3"
|
|
51
|
+
}
|
|
52
|
+
}
|