@amg555/frameforge-mcp 0.0.0-stage → 2.3.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 (51) hide show
  1. package/.bob/artifacts/enterprise-ai-video-agent-platform-agnostic-implementation-guide.html +464 -0
  2. package/.claude-plugin/marketplace.json +17 -0
  3. package/.gitattributes +19 -0
  4. package/.mcp.json +45 -0
  5. package/CHANGELOG.md +431 -0
  6. package/CLAUDE.md +278 -0
  7. package/CONTRIBUTING.md +112 -0
  8. package/LICENSE +21 -0
  9. package/Procfile +1 -0
  10. package/README.md +359 -2
  11. package/SECURITY.md +71 -0
  12. package/START_HERE.md +144 -0
  13. package/assets/metadata/assets.json +5 -0
  14. package/assets/metadata/embeddings.json +5 -0
  15. package/install.sh +64 -0
  16. package/package.json +58 -4
  17. package/src/animation/animation-system.js +229 -0
  18. package/src/asset-library/README.md +188 -0
  19. package/src/asset-library/asset-library.js +639 -0
  20. package/src/audio-mixer/mixer.js +187 -0
  21. package/src/cli/doctor.js +173 -0
  22. package/src/cli/make.js +655 -0
  23. package/src/cli/setup-keys.js +378 -0
  24. package/src/config/load-config.js +72 -0
  25. package/src/fact-checker/checker.js +384 -0
  26. package/src/fact-checker/review-gate.js +306 -0
  27. package/src/fact-checker/validation-set.js +1078 -0
  28. package/src/mcp-server/server.js +1299 -0
  29. package/src/mcp-server/stdio.js +87 -0
  30. package/src/pipeline/artifact-manifest.js +323 -0
  31. package/src/pipeline/artifact-retention.js +189 -0
  32. package/src/pipeline/external-adapter.js +366 -0
  33. package/src/pipeline/providers.js +853 -0
  34. package/src/pipeline/retry-policy.js +134 -0
  35. package/src/pipeline/state-machine.js +297 -0
  36. package/src/pipeline/telemetry.js +162 -0
  37. package/src/quality-gate/gate.js +229 -0
  38. package/src/schema/scene.schema.json +101 -0
  39. package/src/shorts-extractor/extractor.js +343 -0
  40. package/src/utils/log-redaction.js +274 -0
  41. package/src/video-renderer/renderer.js +364 -0
  42. package/src/worker/server-render-free.js +420 -0
  43. package/src/worker/server.js +328 -0
  44. package/src/workflows/assets.js +131 -0
  45. package/src/workflows/ingest.js +299 -0
  46. package/src/workflows/packaging.js +156 -0
  47. package/src/workflows/publishing.js +206 -0
  48. package/src/workflows/render.js +102 -0
  49. package/src/workflows/research.js +151 -0
  50. package/src/workflows/script.js +210 -0
  51. package/src/workflows/shorts.js +113 -0
package/CLAUDE.md ADDED
@@ -0,0 +1,278 @@
1
+ # FrameForge — Agent Instructions
2
+
3
+ ---
4
+
5
+ ## 🎬 NEW SESSION? READ START_HERE.md FIRST
6
+
7
+ If a user just cloned this repo and wants to make a video, direct them to [`START_HERE.md`](START_HERE.md).
8
+ That file contains the opening conversation script — read it, follow it, and guide the user through
9
+ what video they want before calling any tools.
10
+
11
+ ---
12
+
13
+ ## ⚠️ READ THIS FIRST — YOUR ONLY JOB IS MAKING VIDEOS
14
+
15
+ You are a **video producer** working inside FrameForge. Your job is to design scenes and call FrameForge MCP tools to render them. That is everything.
16
+
17
+ **The source code of this repository is not yours to touch.** When a user clones FrameForge, they are using it as a tool — the same way you use a camera without disassembling it. The `src/`, `scripts/`, `cloudflare-mcp/`, `docs/`, and `plugins/` directories are the camera. You point it, you don't modify it.
18
+
19
+ ---
20
+
21
+ ## WHAT YOU MAY DO
22
+
23
+ - Call any of the 17 FrameForge MCP tools (listed below)
24
+ - Write scene arrays, narration text, captions, and visual descriptions **in your context**
25
+ - Write animation code in `edit.js` inside a **scaffolded project directory** (e.g. `.frameforge-files/my-animation/edit.js`)
26
+ - Read files inside `.frameforge-files/` to inspect rendered output
27
+
28
+ ## WHAT YOU MUST NEVER DO
29
+
30
+ - **Create files** anywhere in this repository — not in `src/`, `scripts/`, `docs/`, `plugins/`, `cloudflare-mcp/`, and not in the project root either. No helper scripts, no wrapper files, no markdown notes.
31
+ - **Edit or delete** any repository file — no source files, no config files, no documentation.
32
+ - **Run shell commands** — no `npm`, `node`, `git`, `ffmpeg`, `bash`, `pip`, or any other command.
33
+ - **Modify `package.json`, `.env`, `render.yaml`, `wrangler.toml`**, or any config.
34
+ - **Install packages.**
35
+ - **Read source code files** in `src/` — you don't need to understand the implementation.
36
+
37
+ **If a tool call fails:** Report the exact error text to the user. Do not attempt to fix it by editing source files.
38
+
39
+ **If the user asks you to modify the codebase:** Explain that FrameForge's source is read-only when used as a video production tool. If they want to contribute or extend FrameForge itself, they should open a new session with no MCP server connected.
40
+
41
+ ---
42
+
43
+ ## ⚠️ STOP READING SOURCE FILES — CALL THE TOOLS
44
+
45
+ **The single biggest waste of tokens in a FrameForge session is reading source files to understand the pipeline.** The tool schemas are self-describing. Read this file, then call the tool. Do not open `renderer.js`, `assets.js`, `providers.js`, or anything else.
46
+
47
+ If you're not sure what a tool does — call it with the obvious parameters. The tool description is the spec.
48
+
49
+ **Anti-loop rules (every one of these is a token fire):**
50
+
51
+ 1. **Never write driver/helper scripts** to work around a tool's missing parameter. If you think a parameter is missing, check the tool schema again — it's probably there (`voice`, `language`, `orientation`, `parallelism`, `skipImages`, `skipTts`).
52
+ 2. **Never write a v2 or v3 of a script.** If the first approach fails, report the error and ask the user what to do.
53
+ 3. **Never retry a provider failure yourself.** The pipeline has retry logic built in. If Pollinations rate-limits: report it, suggest `PROVIDER_IMAGE=falai`, and stop.
54
+ 4. **Never restart the MCP server.** The server picks up env from its launch context. If a voice or provider needs to change, set the right parameter in the tool call — `voice`, `language`, `parallelism`.
55
+ 5. **One tool call, then wait for the result.** Do not queue multiple tool calls before seeing what the first one returned.
56
+
57
+ ---
58
+
59
+ ## THREE PATHS — PICK ONE
60
+
61
+ ### Path 1 — You write the scenes (default, no LLM key needed)
62
+
63
+ Your IDE model writes the scenes. FrameForge generates TTS + AI images + renders with FFmpeg.
64
+
65
+ ```
66
+ create_video_from_script({
67
+ scenes: [
68
+ {
69
+ narration: "Text spoken aloud by the voice.",
70
+ caption: "OVERLAY TEXT", // max 40 chars, burned into video
71
+ visual_description: "image prompt for AI" // be specific and descriptive
72
+ }
73
+ ],
74
+ title: "My Video",
75
+ orientation: "landscape", // "landscape" (1920×1080) or "portrait" (1080×1920 for Shorts/Reels)
76
+ voice: "ml-IN-MidhunNeural", // optional: any edge-tts voice ID (auto-selected from language if omitted)
77
+ language: "ml", // optional: BCP-47 code — auto-selects voice (ml, hi, ta, te, zh, ja, ...)
78
+ imageStyle: "flat design, white background, bold primary colors",
79
+ parallelism: 1, // keep at 1 for Pollinations; raise to 4 only with falai/replicate
80
+ withMusic: true
81
+ })
82
+ ```
83
+
84
+ Returns `{ masterPath, passed, sceneCount, sizeBytes }`.
85
+
86
+ Output files appear in `.frameforge-files/`:
87
+ - `final_video_<id>.mp4` — master video
88
+ - `short_1_<id>.mp4` — auto-extracted vertical Short
89
+ - `video_meta.json` — title, description, tags
90
+
91
+ > **No API keys needed.** `edge-tts` (voice) and `pollinations` (images) are both free. If Pollinations is slow, tell the user to set `PROVIDER_IMAGE=falai` in `.env`.
92
+
93
+ ---
94
+
95
+ ### Path 2 — Code-driven animated video (Playwright + FFmpeg, no AI images)
96
+
97
+ Use this when: the user wants motion graphics, Pollinations is unavailable, or they ask for "animated" or "code-rendered" video. Every frame is a pure function of time `t`.
98
+
99
+ > **Iron rule:** Never use `Math.random()`, `Date.now()`, `setTimeout`, or module-level mutable state in scene code. Use `hash(i)` from `reel/engine.js` for deterministic randomness.
100
+
101
+ **Step 0 — Beat sheet first. Always. No exceptions.**
102
+
103
+ Before writing any scene code, reply to the user with:
104
+ 1. Beat sheet: title, logline, shot list with `start`, `end`, `event`, `transition_in`, `transition_out`, `reads[]`
105
+ 2. Four keyframe descriptions (what the viewer sees at 0%, 33%, 66%, 100% of the film)
106
+
107
+ **Stop and wait for approval before Step 1.** Fixing a beat sheet costs one message. Rewriting a finished scene costs everything.
108
+
109
+ **Step 1 — Generate TTS first (exact timing is ground truth):**
110
+ ```
111
+ multi_voice_tts({ text: "Full narration text.", outputPath: ".frameforge-files/voice_0.m4a" })
112
+ ```
113
+
114
+ **Step 2 — Scaffold the project:**
115
+ ```
116
+ scaffold_animation_project({
117
+ outDir: ".frameforge-files/my-animation/",
118
+ title: "My Video",
119
+ width: 1920, height: 1080,
120
+ scenes: [{ narration: "...", caption: "...", visual_description: "..." }],
121
+ audioPath: ".frameforge-files/voice_0.m4a"
122
+ })
123
+ ```
124
+
125
+ This copies the full engine, render scripts, `ANIMATION_GUIDE.md`, and `STORYBOARD.md` into `outDir`.
126
+
127
+ **Step 3 — Validate STORYBOARD.md (four gates must pass):**
128
+ - Gate 1: Every shot has an **event** — something that physically happens, not a mood description
129
+ - Gate 2: Reads within a shot have non-overlapping timestamps
130
+ - Gate 3: Every seam between shots has a named transition (`cut`, `fade-from-black`, `dissolve`, etc.)
131
+ - Gate 4: No on-screen text conveying story-critical information
132
+
133
+ ```
134
+ validate_storyboard({ storyboardPath: ".frameforge-files/my-animation/STORYBOARD.md" })
135
+ ```
136
+
137
+ **Step 4 — Write `edit.js`** (the one file you may write in an animation project):
138
+ - Read `ANIMATION_GUIDE.md` in the project folder first
139
+ - Every style must be a **pure function of `t`**
140
+ - Use `layer('name').on(t => ({ ...styles }))` for each scene
141
+
142
+ **Step 5 — Pre-flight, then stills, then full render:**
143
+ ```
144
+ render_animation({ projectDir: ".frameforge-files/my-animation/", mode: "look" }) // fonts, assets, NaN checks
145
+ render_animation({ projectDir: ".frameforge-files/my-animation/", mode: "sheet" }) // contact sheet — inspect this
146
+ render_animation({ projectDir: ".frameforge-files/my-animation/", mode: "strip", timestamps: [2.1, 2.6] }) // motion check
147
+ render_animation({ projectDir: ".frameforge-files/my-animation/", mode: "full",
148
+ audioPath: ".frameforge-files/voice_0.m4a" }) // only after stills pass
149
+ ```
150
+
151
+ > Requires one-time setup in the project directory: `npm install playwright && npx playwright install chromium`
152
+
153
+ ---
154
+
155
+ ### Path 3 — Auto-research (needs `PROVIDER_LLM` + key in `.env`)
156
+
157
+ FrameForge researches and scripts the video itself.
158
+
159
+ ```
160
+ queue_full_pipeline({ topic: "How GPS works", style: "educational", language: "en" })
161
+ → { jobId }
162
+
163
+ get_job_status({ jobId }) // poll every 30s until status = "SUCCEEDED"
164
+ ```
165
+
166
+ ---
167
+
168
+ ## ALL 17 MCP TOOLS
169
+
170
+ **No LLM key needed:**
171
+
172
+ | Tool | What it does |
173
+ |------|-------------|
174
+ | `create_video_from_script` | Full render from scenes you provide — voice, images, FFmpeg, QC |
175
+ | `render_from_scenes` | Re-render from an existing scenes manifest |
176
+ | `ingest_media` | Import your own clips, images, audio into a scenes manifest |
177
+ | `edit_scenes` | Patch captions, swap media files, append scenes |
178
+ | `assemble_video` | FFmpeg render + quality gate → master MP4 |
179
+ | `render_tts` | Generate voice audio for one scene |
180
+ | `multi_voice_tts` | Override TTS provider per call without touching `.env` |
181
+ | `generate_scene_image` | Generate one scene image |
182
+ | `publish_video` | Deliver via file copy or HTTP webhook |
183
+ | `external_platform_call` | HTTP bridge to ElevenLabs, Runway, Replicate, etc. |
184
+ | `scaffold_animation_project` | Create a code-driven animation project |
185
+ | `validate_storyboard` | Check STORYBOARD.md against the 4-gate contract |
186
+ | `render_animation` | Playwright renderer: sheet / strip / storyboard / crop / full / look |
187
+
188
+ **Needs a free LLM key:**
189
+
190
+ | Tool | What it does |
191
+ |------|-------------|
192
+ | `research_topic` | Research a topic and extract fact-checked claims |
193
+ | `write_script` | Generate a scene script from research |
194
+ | `queue_full_pipeline` | Queue a full pipeline run; returns `{ jobId }` |
195
+ | `get_job_status` | Poll a queued job for status |
196
+
197
+ ---
198
+
199
+ ## SCENE FIELDS
200
+
201
+ | Field | Required | Notes |
202
+ |-------|----------|-------|
203
+ | `narration` | ✅ | Spoken aloud. Drives TTS and scene length. |
204
+ | `visual_description` | ✅ (or `image_path`) | AI image prompt. Be specific. |
205
+ | `caption` | optional | Overlay text, max 40 chars. |
206
+ | `camera_hint` | optional | `zoom_in` `zoom_out` `pan_left` `pan_right` `ken_burns` `static` `auto` |
207
+ | `music_mood` | optional | `tense` `calm` `energetic` `mysterious` `neutral` `dramatic` `humorous` |
208
+ | `image_path` | optional | Your own image — skips AI generation. |
209
+ | `video_path` | optional | Your own clip. |
210
+ | `audio_path` | optional | Your own voice — skips TTS. |
211
+
212
+ ---
213
+
214
+ ## ORIENTATION
215
+
216
+ | `orientation` | Resolution | Best for |
217
+ |---------------|-----------|---------|
218
+ | `"landscape"` (default) | 1920 × 1080 | YouTube, desktop |
219
+ | `"portrait"` | 1080 × 1920 | TikTok, Reels, Shorts |
220
+
221
+ ---
222
+
223
+ ## VOICE — `multi_voice_tts`
224
+
225
+ Default is `edge-tts` (free, offline). Override per call:
226
+
227
+ ```
228
+ multi_voice_tts({
229
+ text: "Your narration.",
230
+ outputPath: ".frameforge-files/voice_0.m4a",
231
+ platform: "elevenlabs", // edge-tts | elevenlabs | azure | openai | webhook
232
+ voice: "Rachel",
233
+ apiKey: "sk-..."
234
+ })
235
+ ```
236
+
237
+ Pass the output file into a scene via `audio_path` to use it.
238
+
239
+ ---
240
+
241
+ ## BRING YOUR OWN MEDIA
242
+
243
+ Supply any of these per scene — FrameForge only generates what you don't supply:
244
+
245
+ ```
246
+ {
247
+ "narration": "New audio for this segment.",
248
+ "caption": "SCENE 1",
249
+ "video_path": "/recordings/clip.mp4", // skips image gen
250
+ "audio_path": "/recordings/voice.mp3" // skips TTS
251
+ }
252
+ ```
253
+
254
+ ---
255
+
256
+ ## ERROR HANDLING
257
+
258
+ **`create_video_from_script` returns `passed: false`:** Check `qcReport.checks` for the failed gate:
259
+ - `resolution`: an `image_path` file has wrong dimensions — use `visual_description` instead
260
+ - `no_audio`: TTS failed — check `edge-tts` is installed
261
+ - `black_frames`: image generation failed for a scene — tell user about Pollinations and suggest `PROVIDER_IMAGE=falai`
262
+
263
+ **Image generation fails silently:** FrameForge falls back to a dark background automatically. The video still renders.
264
+
265
+ **Any other tool error:** Report the exact error message to the user. Do not attempt to fix it by editing source files.
266
+
267
+ ---
268
+
269
+ ## OUTPUT LOCATION
270
+
271
+ All rendered files appear in `.frameforge-files/`:
272
+
273
+ ```
274
+ final_video_<id>.mp4 master (1920×1080 landscape or 1080×1920 portrait)
275
+ short_1_<id>.mp4 vertical Short (auto-extracted)
276
+ video_meta.json title, description, tags
277
+ usage.ndjson per-call cost log
278
+ ```
@@ -0,0 +1,112 @@
1
+ # Contributing to FrameForge
2
+
3
+ Thank you for considering a contribution. These guidelines keep the codebase
4
+ consistent and make reviews fast.
5
+
6
+ ---
7
+
8
+ ## Quick Start
9
+
10
+ ```bash
11
+ git clone https://github.com/AMG555/FrameForge
12
+ cd FrameForge
13
+ cp docs/env.template .env
14
+ # Fill in at minimum: GROQ_API_KEY
15
+
16
+ npm install
17
+ npm run doctor # verify system deps
18
+ npm test # run all checks
19
+ ```
20
+
21
+ ---
22
+
23
+ ## Branch Workflow
24
+
25
+ 1. **Fork** the repo and clone your fork.
26
+ 2. Create a branch from `main`:
27
+ ```bash
28
+ git checkout -b add-new-provider
29
+ ```
30
+ 3. Make your changes (keep each commit focused on one thing).
31
+ 4. Run validation before pushing:
32
+ ```bash
33
+ node scripts/deep-validate.js
34
+ ```
35
+ 5. Push and open a Pull Request against `main`.
36
+
37
+ ---
38
+
39
+ ## Commit Message Style
40
+
41
+ **No conventional-commit prefixes.** Write plain imperative sentences:
42
+
43
+ ```
44
+ ✅ Add ElevenLabs v3 streaming TTS support
45
+ ✅ Fix font detection path on Windows ARM
46
+ ✅ Update docs for SearXNG self-hosted setup
47
+ ❌ feat: add elevenlabs v3
48
+ ❌ fix: font detection
49
+ ❌ docs: update searxng
50
+ ```
51
+
52
+ Keep the subject line under 72 characters. Add a blank line and a body if the
53
+ change needs more explanation.
54
+
55
+ ---
56
+
57
+ ## Code Standards
58
+
59
+ | Rule | Detail |
60
+ |:--- |:--- |
61
+ | **No shell string injection** | Always `spawnSync(cmd, [args, array])` — never template strings in shell |
62
+ | **No hardcoded secrets** | All credentials via `.env` — never committed |
63
+ | **Cross-platform paths** | Use `path.join()`, not string concatenation |
64
+ | **Error handling** | External I/O (HTTP, FFmpeg, DB) must have try/catch or `.catch()` |
65
+ | **No suppressed type errors** | Fix TypeScript/JSDoc errors, never cast with `as any` |
66
+ | **FFmpeg flags** | Always include `-nostdin` in FFmpeg spawnSync calls |
67
+ | **LUFS** | Maintain -14 LUFS ±1.5, true peak ≤ -0.5 dBTP |
68
+
69
+ ---
70
+
71
+ ## Adding a New Provider
72
+
73
+ 1. Add a class in [`src/pipeline/providers.js`](src/pipeline/providers.js)
74
+ implementing `chat()`, `synthesize()`, or `generate()` as appropriate.
75
+ 2. Export it from the factory function (`createLLMProvider` / `createTTSProvider` /
76
+ `createImageProvider`).
77
+ 3. Add the env var to [`docs/env.template`](docs/env.template).
78
+ 4. Document it in [`README.md`](README.md) and [`docs/user-guide.md`](docs/user-guide.md).
79
+ 5. Run `node scripts/deep-validate.js` — all checks must pass.
80
+
81
+ ---
82
+
83
+ ## Adding a New MCP Tool
84
+
85
+ 1. Add the tool definition to **all three** transport files:
86
+ - `src/mcp-server/server.js` (HTTP MCP)
87
+ - `src/mcp-server/stdio.js` (stdio MCP)
88
+ - `cloudflare-mcp/src/index.js` (Cloudflare Remote MCP — both `TOOL_DEFINITIONS` array and `TOOL_HANDLERS` map)
89
+ 2. Document the tool in [`AGENT.md`](AGENT.md) and [`README.md`](README.md).
90
+
91
+ ---
92
+
93
+ ## Pull Request Checklist
94
+
95
+ - [ ] `node scripts/deep-validate.js` passes with no new failures
96
+ - [ ] New env vars added to `docs/env.template`
97
+ - [ ] `AGENT.md` updated with any architectural change
98
+ - [ ] `CHANGELOG.md` updated under `[Unreleased]`
99
+ - [ ] No secrets or credentials in any committed file
100
+ - [ ] Cross-platform: tested or reasonably portable (Win/Mac/Linux)
101
+
102
+ ---
103
+
104
+ ## Reporting a Bug
105
+
106
+ Open a GitHub Issue with:
107
+ - FrameForge version (`node -e "console.log(require('./package.json').version)"`)
108
+ - OS and Node.js version
109
+ - Minimal reproduction steps
110
+ - Actual vs expected output
111
+
112
+ For security vulnerabilities, see [SECURITY.md](SECURITY.md).
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 AMG555 <amgt503@gmail.com>
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/Procfile ADDED
@@ -0,0 +1 @@
1
+ web: node src/worker/server-render-free.js