@writepanda/mcp 1.267.0 → 1.271.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/bin/server.mjs +287 -9
- package/package.json +1 -1
package/bin/server.mjs
CHANGED
|
@@ -1739,7 +1739,7 @@ const TOOLS = [
|
|
|
1739
1739
|
{
|
|
1740
1740
|
name: "project_edit_summary",
|
|
1741
1741
|
description:
|
|
1742
|
-
"What the edit contains now: lengths (editedDurationMs, sourceDurationMs, removedMs cut or sped up), counts (cuts, zooms, motionElements, graphics, transitions, brollBeats, mediaOverlays, captions { on, template }, audio { narration, music, soundEffects }, ...) and highlights[] (plain lines). Cheap; use it to report an editing pass instead of project_read.",
|
|
1742
|
+
"What the edit contains now: lengths (editedDurationMs, sourceDurationMs, removedMs cut or sped up), counts (cuts, zooms, motionElements, graphics, transitions, brollBeats, mediaOverlays, captions { on, template }, audio { narration, music, soundEffects }, voiceEnhancedClips vs loudnessNormalizedClips, ...) and highlights[] (plain lines). Each recording counts once, so splits change neither source length nor cuts. Cheap; use it to report an editing pass instead of project_read.",
|
|
1743
1743
|
inputSchema: {
|
|
1744
1744
|
type: "object",
|
|
1745
1745
|
properties: {
|
|
@@ -2020,11 +2020,11 @@ const TOOLS = [
|
|
|
2020
2020
|
...[
|
|
2021
2021
|
[
|
|
2022
2022
|
"status",
|
|
2023
|
-
"Read the live podcast session code, guest
|
|
2023
|
+
"Read the live podcast session code, mode (hosting / producing), links (guest, call-in, host, producer), recording and sharing state, the desktop's micMuted / cameraOff / devices, each guest's name, role, state, micMuted, cameraOff and sharing, and people: everyone's role, stage (on / back), upNext, talkingPrivately and (while recording) whether they're recorded. While recording, takeStage is who was on stage when.",
|
|
2024
2024
|
],
|
|
2025
2025
|
[
|
|
2026
2026
|
"start-recording",
|
|
2027
|
-
"Start
|
|
2027
|
+
"Start the take: everyone on stage records now, everyone else from their first time on stage (a producer backstage is never recorded). Returns once recording has really started; fails with the reason otherwise.",
|
|
2028
2028
|
],
|
|
2029
2029
|
[
|
|
2030
2030
|
"stop-recording",
|
|
@@ -2149,19 +2149,67 @@ const TOOLS = [
|
|
|
2149
2149
|
{
|
|
2150
2150
|
name: "podcast_set_stage",
|
|
2151
2151
|
description:
|
|
2152
|
-
"Put
|
|
2152
|
+
"Put someone on stage or backstage (stage on|back, live or recording or before the show), queue them up next (upNext: they hear the show and get a cue), or mute them in the stream only (muted). Only on-stage people are in the stream, the recording and the edit; backstage they're recorded as silence. Ids: host (the show's host), producer (the desktop when a producer runs the show), cohost, guest, guest-2, guest-3, caller-N, producer-web-N (browser producers can't go on stage). See podcast_status.",
|
|
2153
2153
|
inputSchema: {
|
|
2154
2154
|
type: "object",
|
|
2155
2155
|
properties: {
|
|
2156
2156
|
waitSec: PODCAST_WAIT,
|
|
2157
2157
|
participant: { type: "string" },
|
|
2158
|
-
|
|
2158
|
+
stage: { type: "string", enum: ["on", "back"] },
|
|
2159
|
+
onAir: { type: "boolean", description: "Same as stage on (true) / back (false)." },
|
|
2160
|
+
upNext: { type: "boolean" },
|
|
2159
2161
|
muted: { type: "boolean" },
|
|
2160
2162
|
},
|
|
2161
2163
|
required: ["participant"],
|
|
2162
2164
|
},
|
|
2163
2165
|
command: "podcast.set-stage",
|
|
2164
2166
|
},
|
|
2167
|
+
{
|
|
2168
|
+
name: "podcast_talkback",
|
|
2169
|
+
description:
|
|
2170
|
+
'Talk privately from the studio desktop (a producer running the show): its mic reaches only `to` (participant ids, or "stage" for everyone on stage), never the stream or the recording, until you call it with active false.',
|
|
2171
|
+
inputSchema: {
|
|
2172
|
+
type: "object",
|
|
2173
|
+
properties: {
|
|
2174
|
+
to: { type: "array", items: { type: "string" } },
|
|
2175
|
+
active: { type: "boolean", description: "false stops (default true)." },
|
|
2176
|
+
},
|
|
2177
|
+
},
|
|
2178
|
+
command: "podcast.talkback",
|
|
2179
|
+
},
|
|
2180
|
+
{
|
|
2181
|
+
name: "podcast_set_mode",
|
|
2182
|
+
description:
|
|
2183
|
+
"Who runs the show from this desktop: hosting (its operator hosts, on camera; default) or producing (a producer runs the studio backstage, never recorded unless they step on stage; the host joins by the host link from podcast_invite as host). Not while recording.",
|
|
2184
|
+
inputSchema: {
|
|
2185
|
+
type: "object",
|
|
2186
|
+
properties: { mode: { type: "string", enum: ["hosting", "producing"] } },
|
|
2187
|
+
required: ["mode"],
|
|
2188
|
+
},
|
|
2189
|
+
command: "podcast.set-mode",
|
|
2190
|
+
},
|
|
2191
|
+
{
|
|
2192
|
+
name: "podcast_host_control",
|
|
2193
|
+
description:
|
|
2194
|
+
"Give the host (host link) control on their page, or take it back: Record, bring people on or backstage, next segment. Graphics and going live stay with the producer. Off by default.",
|
|
2195
|
+
inputSchema: {
|
|
2196
|
+
type: "object",
|
|
2197
|
+
properties: { on: { type: "boolean" } },
|
|
2198
|
+
required: ["on"],
|
|
2199
|
+
},
|
|
2200
|
+
command: "podcast.host-control",
|
|
2201
|
+
},
|
|
2202
|
+
{
|
|
2203
|
+
name: "podcast_cue_host",
|
|
2204
|
+
description:
|
|
2205
|
+
'Show the host a cue card on their page ("Wrap up in 2", "Ask about pricing"). Never on air. Needs the host connected by the host link.',
|
|
2206
|
+
inputSchema: {
|
|
2207
|
+
type: "object",
|
|
2208
|
+
properties: { text: { type: "string", description: "Up to 280 characters." } },
|
|
2209
|
+
required: ["text"],
|
|
2210
|
+
},
|
|
2211
|
+
command: "podcast.cue-host",
|
|
2212
|
+
},
|
|
2165
2213
|
{
|
|
2166
2214
|
name: "podcast_show_overlay",
|
|
2167
2215
|
description:
|
|
@@ -2290,10 +2338,214 @@ const TOOLS = [
|
|
|
2290
2338
|
"YouTube title when it should differ from the episode title; empty = follow it.",
|
|
2291
2339
|
},
|
|
2292
2340
|
draftRundown: { type: "boolean" },
|
|
2341
|
+
mode: {
|
|
2342
|
+
type: "string",
|
|
2343
|
+
enum: ["hosting", "producing"],
|
|
2344
|
+
description:
|
|
2345
|
+
"producing: a producer runs the studio, the host joins by the host link (podcast_invite as host).",
|
|
2346
|
+
},
|
|
2347
|
+
host: {
|
|
2348
|
+
type: "object",
|
|
2349
|
+
description: "Producing: the show's host (their lower third).",
|
|
2350
|
+
properties: {
|
|
2351
|
+
name: { type: "string" },
|
|
2352
|
+
email: { type: "string" },
|
|
2353
|
+
role: { type: "string" },
|
|
2354
|
+
},
|
|
2355
|
+
required: ["name"],
|
|
2356
|
+
},
|
|
2357
|
+
crew: {
|
|
2358
|
+
type: "array",
|
|
2359
|
+
description: "The production side: producers, editor, client.",
|
|
2360
|
+
items: {
|
|
2361
|
+
type: "object",
|
|
2362
|
+
properties: {
|
|
2363
|
+
name: { type: "string" },
|
|
2364
|
+
email: { type: "string" },
|
|
2365
|
+
role: { type: "string" },
|
|
2366
|
+
},
|
|
2367
|
+
required: ["name"],
|
|
2368
|
+
},
|
|
2369
|
+
},
|
|
2370
|
+
hostControl: {
|
|
2371
|
+
type: "boolean",
|
|
2372
|
+
description: "Producing: the host gets Record, stage and next segment on their page.",
|
|
2373
|
+
},
|
|
2374
|
+
showId: { type: "string", description: "The show (series) it belongs to." },
|
|
2293
2375
|
},
|
|
2294
2376
|
},
|
|
2295
2377
|
command: "podcast.schedule",
|
|
2296
2378
|
},
|
|
2379
|
+
{
|
|
2380
|
+
name: "show_list",
|
|
2381
|
+
description:
|
|
2382
|
+
"Podcast shows (series) in the current workspace. A workspace is the client; a show is one of its series, with defaults for new episodes and a delivery after each recording.",
|
|
2383
|
+
inputSchema: { type: "object", properties: {} },
|
|
2384
|
+
command: "show.list",
|
|
2385
|
+
},
|
|
2386
|
+
{
|
|
2387
|
+
name: "show_create",
|
|
2388
|
+
description:
|
|
2389
|
+
"Create a podcast show in the current workspace. Episodes scheduled with its showId (podcast_schedule) start from its mode (hosting / producing), host, crew, host control, run-of-show template, recipe and destinations. A delivery with edit / MP3 / Shorts / upload proposes a delivery routine the user turns on.",
|
|
2390
|
+
inputSchema: {
|
|
2391
|
+
type: "object",
|
|
2392
|
+
properties: {
|
|
2393
|
+
name: { type: "string" },
|
|
2394
|
+
description: { type: "string" },
|
|
2395
|
+
mode: { type: "string", enum: ["hosting", "producing"] },
|
|
2396
|
+
host: {
|
|
2397
|
+
type: "object",
|
|
2398
|
+
properties: {
|
|
2399
|
+
name: { type: "string" },
|
|
2400
|
+
email: { type: "string" },
|
|
2401
|
+
role: { type: "string" },
|
|
2402
|
+
},
|
|
2403
|
+
required: ["name"],
|
|
2404
|
+
},
|
|
2405
|
+
crew: {
|
|
2406
|
+
type: "array",
|
|
2407
|
+
items: {
|
|
2408
|
+
type: "object",
|
|
2409
|
+
properties: {
|
|
2410
|
+
name: { type: "string" },
|
|
2411
|
+
email: { type: "string" },
|
|
2412
|
+
role: { type: "string" },
|
|
2413
|
+
},
|
|
2414
|
+
required: ["name"],
|
|
2415
|
+
},
|
|
2416
|
+
},
|
|
2417
|
+
hostControl: { type: "boolean" },
|
|
2418
|
+
recipeId: { type: "string", description: "The edit's recipe (recipe_list); empty clears." },
|
|
2419
|
+
rundownTemplate: { type: "object", description: "Run of show new episodes start from." },
|
|
2420
|
+
destinationIds: { type: "array", items: { type: "string" } },
|
|
2421
|
+
delivery: {
|
|
2422
|
+
type: "object",
|
|
2423
|
+
description:
|
|
2424
|
+
"After each recorded episode: folder (absolute) gets rawFiles (each person's own recording + the live program); edit, audioMaster (MP3), shorts (0-10) and youtube {accountId, privacy} run as a delivery routine the user turns on. null clears.",
|
|
2425
|
+
properties: {
|
|
2426
|
+
folder: { type: "string" },
|
|
2427
|
+
rawFiles: { type: "boolean" },
|
|
2428
|
+
edit: { type: "boolean" },
|
|
2429
|
+
audioMaster: { type: "boolean" },
|
|
2430
|
+
shorts: { type: "number" },
|
|
2431
|
+
youtube: {
|
|
2432
|
+
type: "object",
|
|
2433
|
+
properties: {
|
|
2434
|
+
accountId: { type: "string" },
|
|
2435
|
+
privacy: { type: "string", enum: ["private", "unlisted", "public"] },
|
|
2436
|
+
},
|
|
2437
|
+
required: ["accountId"],
|
|
2438
|
+
},
|
|
2439
|
+
notes: { type: "string" },
|
|
2440
|
+
},
|
|
2441
|
+
},
|
|
2442
|
+
},
|
|
2443
|
+
required: ["name"],
|
|
2444
|
+
},
|
|
2445
|
+
command: "show.create",
|
|
2446
|
+
},
|
|
2447
|
+
{
|
|
2448
|
+
name: "show_update",
|
|
2449
|
+
description: "Change a show's name, defaults or delivery (only the fields given).",
|
|
2450
|
+
inputSchema: {
|
|
2451
|
+
type: "object",
|
|
2452
|
+
properties: {
|
|
2453
|
+
id: { type: "string" },
|
|
2454
|
+
name: { type: "string" },
|
|
2455
|
+
description: { type: "string" },
|
|
2456
|
+
mode: { type: "string", enum: ["hosting", "producing"] },
|
|
2457
|
+
host: {
|
|
2458
|
+
type: "object",
|
|
2459
|
+
properties: {
|
|
2460
|
+
name: { type: "string" },
|
|
2461
|
+
email: { type: "string" },
|
|
2462
|
+
role: { type: "string" },
|
|
2463
|
+
},
|
|
2464
|
+
required: ["name"],
|
|
2465
|
+
},
|
|
2466
|
+
crew: {
|
|
2467
|
+
type: "array",
|
|
2468
|
+
items: {
|
|
2469
|
+
type: "object",
|
|
2470
|
+
properties: {
|
|
2471
|
+
name: { type: "string" },
|
|
2472
|
+
email: { type: "string" },
|
|
2473
|
+
role: { type: "string" },
|
|
2474
|
+
},
|
|
2475
|
+
required: ["name"],
|
|
2476
|
+
},
|
|
2477
|
+
},
|
|
2478
|
+
hostControl: { type: "boolean" },
|
|
2479
|
+
recipeId: { type: "string", description: "The edit's recipe (recipe_list); empty clears." },
|
|
2480
|
+
rundownTemplate: { type: "object", description: "Run of show new episodes start from." },
|
|
2481
|
+
destinationIds: { type: "array", items: { type: "string" } },
|
|
2482
|
+
delivery: {
|
|
2483
|
+
type: "object",
|
|
2484
|
+
description:
|
|
2485
|
+
"After each recorded episode: folder (absolute) gets rawFiles (each person's own recording + the live program); edit, audioMaster (MP3), shorts (0-10) and youtube {accountId, privacy} run as a delivery routine the user turns on. null clears.",
|
|
2486
|
+
properties: {
|
|
2487
|
+
folder: { type: "string" },
|
|
2488
|
+
rawFiles: { type: "boolean" },
|
|
2489
|
+
edit: { type: "boolean" },
|
|
2490
|
+
audioMaster: { type: "boolean" },
|
|
2491
|
+
shorts: { type: "number" },
|
|
2492
|
+
youtube: {
|
|
2493
|
+
type: "object",
|
|
2494
|
+
properties: {
|
|
2495
|
+
accountId: { type: "string" },
|
|
2496
|
+
privacy: { type: "string", enum: ["private", "unlisted", "public"] },
|
|
2497
|
+
},
|
|
2498
|
+
required: ["accountId"],
|
|
2499
|
+
},
|
|
2500
|
+
notes: { type: "string" },
|
|
2501
|
+
},
|
|
2502
|
+
},
|
|
2503
|
+
},
|
|
2504
|
+
required: ["id"],
|
|
2505
|
+
},
|
|
2506
|
+
command: "show.update",
|
|
2507
|
+
},
|
|
2508
|
+
{
|
|
2509
|
+
name: "show_set_delivery",
|
|
2510
|
+
description:
|
|
2511
|
+
"What to hand over after each recorded episode of a show: raw files to a folder (copied right after recording), plus the edit, MP3, Shorts and YouTube upload as a delivery routine the user turns on.",
|
|
2512
|
+
inputSchema: {
|
|
2513
|
+
type: "object",
|
|
2514
|
+
properties: {
|
|
2515
|
+
id: { type: "string" },
|
|
2516
|
+
delivery: {
|
|
2517
|
+
type: "object",
|
|
2518
|
+
description:
|
|
2519
|
+
"After each recorded episode: folder (absolute) gets rawFiles (each person's own recording + the live program); edit, audioMaster (MP3), shorts (0-10) and youtube {accountId, privacy} run as a delivery routine the user turns on. null clears.",
|
|
2520
|
+
properties: {
|
|
2521
|
+
folder: { type: "string" },
|
|
2522
|
+
rawFiles: { type: "boolean" },
|
|
2523
|
+
edit: { type: "boolean" },
|
|
2524
|
+
audioMaster: { type: "boolean" },
|
|
2525
|
+
shorts: { type: "number" },
|
|
2526
|
+
youtube: {
|
|
2527
|
+
type: "object",
|
|
2528
|
+
properties: {
|
|
2529
|
+
accountId: { type: "string" },
|
|
2530
|
+
privacy: { type: "string", enum: ["private", "unlisted", "public"] },
|
|
2531
|
+
},
|
|
2532
|
+
required: ["accountId"],
|
|
2533
|
+
},
|
|
2534
|
+
notes: { type: "string" },
|
|
2535
|
+
},
|
|
2536
|
+
},
|
|
2537
|
+
},
|
|
2538
|
+
required: ["id", "delivery"],
|
|
2539
|
+
},
|
|
2540
|
+
command: "show.set-delivery",
|
|
2541
|
+
},
|
|
2542
|
+
{
|
|
2543
|
+
name: "show_delete",
|
|
2544
|
+
description:
|
|
2545
|
+
"Delete a show (ask the user first). Its episodes and files stay; its delivery routine is removed.",
|
|
2546
|
+
inputSchema: { type: "object", properties: { id: { type: "string" } }, required: ["id"] },
|
|
2547
|
+
command: "show.delete",
|
|
2548
|
+
},
|
|
2297
2549
|
{
|
|
2298
2550
|
name: "podcast_list_upcoming",
|
|
2299
2551
|
description:
|
|
@@ -2324,13 +2576,14 @@ const TOOLS = [
|
|
|
2324
2576
|
{
|
|
2325
2577
|
name: "podcast_invite",
|
|
2326
2578
|
description:
|
|
2327
|
-
"An episode's
|
|
2579
|
+
"An episode's invite: the link, invite text and a calendar invite (.ics, needs a date). as: guest (default), host (the host link, when a producer runs the studio) or producer (a browser producer link: watch, talk privately, approve the AI producer). out writes the .ics there. Don't send it yourself unless the user asks.",
|
|
2328
2580
|
inputSchema: {
|
|
2329
2581
|
type: "object",
|
|
2330
2582
|
properties: {
|
|
2331
2583
|
path: { type: "string" },
|
|
2332
2584
|
id: { type: "string" },
|
|
2333
2585
|
sessionCode: { type: "string" },
|
|
2586
|
+
as: { type: "string", enum: ["guest", "host", "producer"] },
|
|
2334
2587
|
out: { type: "string", description: "Absolute path ending in .ics." },
|
|
2335
2588
|
hostName: { type: "string" },
|
|
2336
2589
|
},
|
|
@@ -4504,7 +4757,7 @@ const TOOLS = [
|
|
|
4504
4757
|
{
|
|
4505
4758
|
name: "project_center_camera_on_face",
|
|
4506
4759
|
description:
|
|
4507
|
-
"Keep the presenter's face centred in
|
|
4760
|
+
"Keep the presenter's face centred in a SEPARATE camera card by tracking it (can take a minute). Not for the main video: face-tracked zooms on the main video are project_auto_reframe. On a podcast clip it tracks every participant's camera so their tiles (pair, grid, screen-share strip) centre on each face (the editor also does this in the background when a podcast opens; a set-podcast-source-crop framing wins). clear: true turns it off. Concurrent saves are merged and retried (three attempts). Exhausted conflicts report code revision_conflict / status 409 (job.errorDetails for async jobs).",
|
|
4508
4761
|
inputSchema: {
|
|
4509
4762
|
type: "object",
|
|
4510
4763
|
properties: {
|
|
@@ -4743,7 +4996,7 @@ const TOOLS = [
|
|
|
4743
4996
|
{
|
|
4744
4997
|
name: "project_auto_reframe",
|
|
4745
4998
|
description:
|
|
4746
|
-
"Active-speaker auto-reframe
|
|
4999
|
+
"Active-speaker auto-reframe: frames whoever talks, shot by shot (face tracking, no speaker IDs needed). Landscape footage on a vertical / square canvas gets a crop that follows the speaker; footage that already has the canvas shape (a 16:9 wide of two hosts in a 16:9 video) gets a punch-in on the speaker inside the frame, which is also how to get face-tracked zooms on the main video. zoom = fixed punch-in. split=true stacks two people (podcast / interview wide) one above the other on a 9:16 canvas. Slow (minutes). clear reverts. Concurrent saves are merged and retried (three attempts). Exhausted conflicts report code revision_conflict / status 409 (job.errorDetails for async jobs).",
|
|
4747
5000
|
inputSchema: {
|
|
4748
5001
|
type: "object",
|
|
4749
5002
|
properties: {
|
|
@@ -5140,6 +5393,24 @@ const TOOLS = [
|
|
|
5140
5393
|
},
|
|
5141
5394
|
command: "project.set-clip-chroma-key",
|
|
5142
5395
|
},
|
|
5396
|
+
{
|
|
5397
|
+
name: "project_set_clip_flip",
|
|
5398
|
+
description:
|
|
5399
|
+
"Flip a main-track clip's picture: fixes a recording that came out upside down (horizontal + vertical = turned 180 degrees, e.g. a monitor mounted upside down) or mirrored (horizontal). Corrects the source: crops, cursor and zoom focus read the flipped picture. Omitted axes keep their value; both false removes it. Check with project_render_frame.",
|
|
5400
|
+
inputSchema: {
|
|
5401
|
+
type: "object",
|
|
5402
|
+
properties: {
|
|
5403
|
+
id: { type: "string" },
|
|
5404
|
+
path: { type: "string" },
|
|
5405
|
+
clipId: { type: "string" },
|
|
5406
|
+
horizontal: { type: "boolean", description: "Mirror left to right." },
|
|
5407
|
+
vertical: { type: "boolean", description: "Mirror top to bottom." },
|
|
5408
|
+
expectedRevision: { type: "number" },
|
|
5409
|
+
},
|
|
5410
|
+
required: ["clipId"],
|
|
5411
|
+
},
|
|
5412
|
+
command: "project.set-clip-flip",
|
|
5413
|
+
},
|
|
5143
5414
|
{
|
|
5144
5415
|
name: "project_set_clip_kind",
|
|
5145
5416
|
description:
|
|
@@ -5459,7 +5730,7 @@ const TOOLS = [
|
|
|
5459
5730
|
{
|
|
5460
5731
|
name: "transcript_transcribe",
|
|
5461
5732
|
description:
|
|
5462
|
-
"Transcribe clips with word timestamps (default: only clips without words). Engine: language auto/english = Parakeet; any other named language = local Whisper LOCKED to it (engine override). Returns { jobId, plan } (plan = engine + reason, ranges, totalAudioMs: the audio that will be processed, estimate/estimatedMs: how long on this computer, advice: faster options for a long Whisper run; tell the user for long jobs). Long Whisper runs are saved chunk by chunk: stalls restart from the last chunk automatically; after job_cancel, a crash or an app restart, transcribing again resumes there. Progress is real (audio decoded); time left in progress.message and progress.data.etaMs. To REDO a transcript (wrong language, bad run) confirm language, pass per-run language and provider overrides, then force: true (all clips) or clipId. Word fixes are re-applied; tell the user about result droppedWordEdits[] (fixes that may need redoing). Each clip is transcribed only over the part it plays (head trim to tail trim, e.g. one half of a split; only the kept parts when cuts hide most of a long recording; result transcribedRanges[]). ASYNC: { jobId }, job_wait. Concurrent saves are merged and retried (three attempts). Exhausted conflicts report code revision_conflict / status 409 (job.errorDetails for async jobs).",
|
|
5733
|
+
"Transcribe clips with word timestamps (default: only clips without words). Engine: language auto/english = Parakeet; any other named language = local Whisper LOCKED to it (engine override). Returns { jobId, plan } (plan = engine + reason, ranges, totalAudioMs: the audio that will be processed, estimate/estimatedMs: how long on this computer, advice: faster options for a long Whisper run; tell the user for long jobs). Long Whisper runs are saved chunk by chunk: stalls restart from the last chunk automatically; after job_cancel, a crash or an app restart, transcribing again resumes there. Progress is real (audio decoded); time left in progress.message and progress.data.etaMs. To REDO a transcript (wrong language, bad run) confirm language, pass per-run language and provider overrides, then force: true (all clips) or clipId. Word fixes are re-applied; tell the user about result droppedWordEdits[] (fixes that may need redoing). Each clip is transcribed only over the part it plays (head trim to tail trim, e.g. one half of a split; only the kept parts when cuts hide most of a long recording; result transcribedRanges[]). Clips with no audio track are skipped (result noAudioClips), not failed. ASYNC: { jobId }, job_wait. Concurrent saves are merged and retried (three attempts). Exhausted conflicts report code revision_conflict / status 409 (job.errorDetails for async jobs).",
|
|
5463
5734
|
inputSchema: {
|
|
5464
5735
|
type: "object",
|
|
5465
5736
|
properties: {
|
|
@@ -7531,6 +7802,13 @@ const TOOLS = [
|
|
|
7531
7802
|
description:
|
|
7532
7803
|
"{ id?, title, description, category, footage?, aspectRatio?, fields: [{ key, label, type: text|longtext|select|color|images, default?, options?, required?, help?, minCount?, maxCount?, optional? }], prompt, lookFrames?: [{ src: absolute image path, shows: what it shows (position, size, colours), atMs? }] (up to 8 stills of the target look; copied into the recipe), style?: { aspectRatio?, colorCorrection?, lut?: { preset, intensity? }, speakerBackground?: { mode: none|blur|remove|image, image?, strength?, outline?: { enabled, width?, color?, shadow? } }, framing?: { shortsLayout: full|camera-corner }, cameraLayout?, captions?: { enabled, templateId?, wordsPerLine?, positionY?, style?: caption_set_look's style }, broll?: { use: none|ask|generate|user-images, layout?: full|split|card, notes? }, graphics?: { family?, titleFont?, bodyFont?, accentColor?, textColor?, surfaceColor?, notes? }, wallpaper? }, checklist: string[] }. Put the WHOLE look in style (every caption value, the background, framing, B-roll rule, title fonts and colours): it is applied exactly, the prompt only covers what depends on the footage.",
|
|
7533
7804
|
},
|
|
7805
|
+
id: {
|
|
7806
|
+
type: "string",
|
|
7807
|
+
description:
|
|
7808
|
+
"Project the edit was made in (default: the one open in the editor). Without lookFrames, three stills of it become the recipe's cover on Home and the look the next run matches.",
|
|
7809
|
+
},
|
|
7810
|
+
path: { type: "string", description: "Same as id, by project file path." },
|
|
7811
|
+
stills: { type: "boolean", description: "false = save without stills of the edit." },
|
|
7534
7812
|
},
|
|
7535
7813
|
required: ["recipe"],
|
|
7536
7814
|
},
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@writepanda/mcp",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.271.0",
|
|
4
4
|
"description": "Model Context Protocol server for PandaStudio. Exposes the desktop video editor's automation surface to Cursor, Continue, Cline, Claude Desktop, and any MCP-compliant client.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"pandastudio",
|