yt-dlp-bridge 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.
Files changed (56) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +19 -0
  3. package/dist/argv.d.ts +18 -0
  4. package/dist/argv.d.ts.map +1 -0
  5. package/dist/argv.js +276 -0
  6. package/dist/argv.js.map +1 -0
  7. package/dist/config.d.ts +20 -0
  8. package/dist/config.d.ts.map +1 -0
  9. package/dist/config.js +36 -0
  10. package/dist/config.js.map +1 -0
  11. package/dist/environment.d.ts +27 -0
  12. package/dist/environment.d.ts.map +1 -0
  13. package/dist/environment.js +80 -0
  14. package/dist/environment.js.map +1 -0
  15. package/dist/errors.d.ts +3 -0
  16. package/dist/errors.d.ts.map +1 -0
  17. package/dist/errors.js +73 -0
  18. package/dist/errors.js.map +1 -0
  19. package/dist/filesystem.d.ts +23 -0
  20. package/dist/filesystem.d.ts.map +1 -0
  21. package/dist/filesystem.js +57 -0
  22. package/dist/filesystem.js.map +1 -0
  23. package/dist/generated/ytdlp-options.json +5513 -0
  24. package/dist/index.d.ts +13 -0
  25. package/dist/index.d.ts.map +1 -0
  26. package/dist/index.js +13 -0
  27. package/dist/index.js.map +1 -0
  28. package/dist/option-catalog.d.ts +34 -0
  29. package/dist/option-catalog.d.ts.map +1 -0
  30. package/dist/option-catalog.js +89 -0
  31. package/dist/option-catalog.js.map +1 -0
  32. package/dist/parsers.d.ts +11 -0
  33. package/dist/parsers.d.ts.map +1 -0
  34. package/dist/parsers.js +268 -0
  35. package/dist/parsers.js.map +1 -0
  36. package/dist/planner.d.ts +10 -0
  37. package/dist/planner.d.ts.map +1 -0
  38. package/dist/planner.js +233 -0
  39. package/dist/planner.js.map +1 -0
  40. package/dist/redaction.d.ts +4 -0
  41. package/dist/redaction.d.ts.map +1 -0
  42. package/dist/redaction.js +52 -0
  43. package/dist/redaction.js.map +1 -0
  44. package/dist/runner.d.ts +14 -0
  45. package/dist/runner.d.ts.map +1 -0
  46. package/dist/runner.js +78 -0
  47. package/dist/runner.js.map +1 -0
  48. package/dist/schemas.d.ts +818 -0
  49. package/dist/schemas.d.ts.map +1 -0
  50. package/dist/schemas.js +179 -0
  51. package/dist/schemas.js.map +1 -0
  52. package/dist/types.d.ts +163 -0
  53. package/dist/types.d.ts.map +1 -0
  54. package/dist/types.js +2 -0
  55. package/dist/types.js.map +1 -0
  56. package/package.json +65 -0
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Antonio Orionus
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/README.md ADDED
@@ -0,0 +1,19 @@
1
+ # yt-dlp-bridge
2
+
3
+ Typed, source-derived yt-dlp command planning and execution primitives for Node.js.
4
+
5
+ This package is intentionally MCP-agnostic. It provides the yt-dlp integration layer used by `yt-dlp-mcp-server`: option catalog access, safe argv generation, dependency-aware planning, process execution, redaction, filesystem policy, and structured error adaptation via `ytdlp-errors`.
6
+
7
+ ## Local pre-release use
8
+
9
+ ```bash
10
+ cd /home/anton/projects/y/yt-dlp-bridge
11
+ pnpm install
12
+ pnpm test
13
+ pnpm run typecheck
14
+ pnpm run build
15
+ ```
16
+
17
+ Node >= 20. ESM only.
18
+
19
+ This package is not published yet. It currently depends on the sibling local `ytdlp-errors` package via `file:../ytdlp-errors` so the full yt-dlp MCP stack can be polished before release.
package/dist/argv.d.ts ADDED
@@ -0,0 +1,18 @@
1
+ import type { z } from "zod";
2
+ import { type ServerConfig } from "./config.js";
3
+ import { type ResolvedOutputPolicy } from "./filesystem.js";
4
+ import { type DownloadInputSchema, type InspectInputSchema, type PlanDownloadInputSchema } from "./schemas.js";
5
+ import type { YtdlpCommand } from "./types.js";
6
+ type InspectInput = z.infer<typeof InspectInputSchema>;
7
+ type PlanDownloadInput = z.infer<typeof PlanDownloadInputSchema>;
8
+ type DownloadInput = z.infer<typeof DownloadInputSchema>;
9
+ type DownloadLikeInput = PlanDownloadInput | DownloadInput;
10
+ export type ListKind = "formats" | "subtitles" | "thumbnails";
11
+ export declare function ytdlpCommand(args: string[], config?: ServerConfig): YtdlpCommand;
12
+ export declare function buildMetadataArgs(input: InspectInput, config?: ServerConfig): string[];
13
+ export declare function buildSingleJsonArgs(input: InspectInput, config?: ServerConfig): string[];
14
+ export declare function buildListArgs(kind: ListKind, input: InspectInput, config?: ServerConfig): string[];
15
+ export declare function buildSimulationArgs(input: DownloadLikeInput, policy: ResolvedOutputPolicy, config?: ServerConfig): string[];
16
+ export declare function buildDownloadArgs(input: DownloadLikeInput, policy: ResolvedOutputPolicy, config?: ServerConfig): string[];
17
+ export {};
18
+ //# sourceMappingURL=argv.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"argv.d.ts","sourceRoot":"","sources":["../src/argv.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAC7B,OAAO,EAAU,KAAK,YAAY,EAAE,MAAM,aAAa,CAAC;AACxD,OAAO,EAAsB,KAAK,oBAAoB,EAAE,MAAM,iBAAiB,CAAC;AAEhF,OAAO,EACL,KAAK,mBAAmB,EACxB,KAAK,kBAAkB,EACvB,KAAK,uBAAuB,EAC7B,MAAM,cAAc,CAAC;AACtB,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,YAAY,CAAC;AAE/C,KAAK,YAAY,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,kBAAkB,CAAC,CAAC;AACvD,KAAK,iBAAiB,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,uBAAuB,CAAC,CAAC;AACjE,KAAK,aAAa,GAAG,CAAC,CAAC,KAAK,CAAC,OAAO,mBAAmB,CAAC,CAAC;AACzD,KAAK,iBAAiB,GAAG,iBAAiB,GAAG,aAAa,CAAC;AAE3D,MAAM,MAAM,QAAQ,GAAG,SAAS,GAAG,WAAW,GAAG,YAAY,CAAC;AAE9D,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,EAAE,MAAM,GAAE,YAAqB,GAAG,YAAY,CAMxF;AAED,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,YAAY,EAAE,MAAM,GAAE,YAAqB,GAAG,MAAM,EAAE,CAE9F;AAED,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,YAAY,EAAE,MAAM,GAAE,YAAqB,GAAG,MAAM,EAAE,CAEhG;AAED,wBAAgB,aAAa,CAAC,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,YAAY,EAAE,MAAM,GAAE,YAAqB,GAAG,MAAM,EAAE,CAG1G;AAED,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,iBAAiB,EAAE,MAAM,EAAE,oBAAoB,EAAE,MAAM,GAAE,YAAqB,GAAG,MAAM,EAAE,CAEnI;AAED,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,iBAAiB,EAAE,MAAM,EAAE,oBAAoB,EAAE,MAAM,GAAE,YAAqB,GAAG,MAAM,EAAE,CAkCjI"}
package/dist/argv.js ADDED
@@ -0,0 +1,276 @@
1
+ import { CONFIG } from "./config.js";
2
+ import { resolveManagedPath } from "./filesystem.js";
3
+ import { redactArgs } from "./redaction.js";
4
+ import {} from "./schemas.js";
5
+ export function ytdlpCommand(args, config = CONFIG) {
6
+ return {
7
+ command: config.ytdlpPath,
8
+ args,
9
+ redactedArgs: redactArgs(args)
10
+ };
11
+ }
12
+ export function buildMetadataArgs(input, config = CONFIG) {
13
+ return [...buildInspectBaseArgs(input, config), "--dump-json", input.url];
14
+ }
15
+ export function buildSingleJsonArgs(input, config = CONFIG) {
16
+ return [...buildInspectBaseArgs(input, config), "--dump-single-json", input.url];
17
+ }
18
+ export function buildListArgs(kind, input, config = CONFIG) {
19
+ const flag = kind === "formats" ? "--list-formats" : kind === "subtitles" ? "--list-subs" : "--list-thumbnails";
20
+ return [...buildInspectBaseArgs(input, config), flag, input.url];
21
+ }
22
+ export function buildSimulationArgs(input, policy, config = CONFIG) {
23
+ return ["--simulate", ...buildDownloadArgs(input, policy, config)];
24
+ }
25
+ export function buildDownloadArgs(input, policy, config = CONFIG) {
26
+ const args = buildBaseArgs(input, config);
27
+ push(args, "--paths", `home:${policy.outputRoot}`);
28
+ push(args, "--paths", `temp:${policy.tempRoot}`);
29
+ push(args, "--output", policy.outputTemplate);
30
+ args.push(policy.allowOverwrite ? "--force-overwrites" : "--no-overwrites");
31
+ args.push("--newline", "--progress");
32
+ push(args, "--print", "after_move:filepath");
33
+ appendSelectionArgs(args, input, policy, config);
34
+ appendDownloadArgs(args, input);
35
+ appendFormatArgs(args, input);
36
+ appendSubtitleArgs(args, input);
37
+ appendThumbnailArgs(args, input);
38
+ appendPostprocessArgs(args, input);
39
+ appendSponsorBlockArgs(args, input);
40
+ appendExtractorArgs(args, input);
41
+ if (input.kind === "audio" && !input.postprocess.extractAudio) {
42
+ args.push("--extract-audio");
43
+ }
44
+ if (input.kind === "subtitles") {
45
+ args.push("--skip-download");
46
+ if (!input.subtitles.writeSubs && !input.subtitles.writeAutoSubs)
47
+ args.push("--write-subs");
48
+ }
49
+ if (input.kind === "thumbnail") {
50
+ args.push("--skip-download");
51
+ if (!input.thumbnails.writeThumbnail && !input.thumbnails.writeAllThumbnails)
52
+ args.push("--write-thumbnail");
53
+ }
54
+ if (input.kind === "playlist" && !input.selection.noPlaylist)
55
+ args.push("--yes-playlist");
56
+ args.push(input.url);
57
+ return args;
58
+ }
59
+ function buildInspectBaseArgs(input, config) {
60
+ const args = buildBaseArgs(input, config);
61
+ if (input.flatPlaylist)
62
+ args.push("--flat-playlist");
63
+ return args;
64
+ }
65
+ function buildBaseArgs(input, config) {
66
+ const args = ["--ignore-config", "--no-warnings"];
67
+ appendNetworkArgs(args, input.network);
68
+ appendAuthArgs(args, input.auth, config);
69
+ return args;
70
+ }
71
+ function appendNetworkArgs(args, network) {
72
+ push(args, "--proxy", network.proxy);
73
+ if (network.socketTimeout !== undefined)
74
+ push(args, "--socket-timeout", String(network.socketTimeout));
75
+ push(args, "--source-address", network.sourceAddress);
76
+ push(args, "--impersonate", network.impersonate);
77
+ push(args, "--geo-verification-proxy", network.geoVerificationProxy);
78
+ push(args, "--xff", network.xff);
79
+ if (network.forceIpv4)
80
+ args.push("--force-ipv4");
81
+ if (network.forceIpv6)
82
+ args.push("--force-ipv6");
83
+ }
84
+ function appendAuthArgs(args, auth, config) {
85
+ push(args, "--username", auth.username);
86
+ push(args, "--password", auth.password);
87
+ push(args, "--twofactor", auth.twofactor);
88
+ if (auth.netrc) {
89
+ requireConfigFilePolicy("auth.netrc", config);
90
+ args.push("--netrc");
91
+ }
92
+ if (auth.netrcLocation)
93
+ requireConfigFilePolicy("auth.netrcLocation", config);
94
+ if (auth.netrcCmd)
95
+ requireConfigFilePolicy("auth.netrcCmd", config);
96
+ push(args, "--netrc-location", auth.netrcLocation);
97
+ push(args, "--netrc-cmd", auth.netrcCmd);
98
+ push(args, "--video-password", auth.videoPassword);
99
+ push(args, "--cookies", configuredOrAllowed(auth.cookiesFile, config.cookiesFile, "auth.cookiesFile", config));
100
+ push(args, "--cookies-from-browser", configuredOrAllowed(auth.cookiesFromBrowser, config.cookiesFromBrowser, "auth.cookiesFromBrowser", config));
101
+ }
102
+ function appendSelectionArgs(args, input, policy, config) {
103
+ const selection = input.selection;
104
+ push(args, "--playlist-items", selection.playlistItems);
105
+ if (selection.noPlaylist)
106
+ args.push("--no-playlist");
107
+ if (selection.yesPlaylist)
108
+ args.push("--yes-playlist");
109
+ push(args, "--min-filesize", selection.minFilesize);
110
+ push(args, "--max-filesize", selection.maxFilesize);
111
+ push(args, "--date", selection.date);
112
+ push(args, "--datebefore", selection.dateBefore);
113
+ push(args, "--dateafter", selection.dateAfter);
114
+ pushRepeated(args, "--match-filters", selection.matchFilters);
115
+ pushRepeated(args, "--break-match-filters", selection.breakMatchFilters);
116
+ if (selection.ageLimit !== undefined)
117
+ push(args, "--age-limit", String(selection.ageLimit));
118
+ push(args, "--download-archive", selection.downloadArchive ? resolveManagedPath(policy.outputRoot, selection.downloadArchive, "downloadArchive", config.allowArbitraryOutputPaths) : undefined);
119
+ if (selection.maxDownloads !== undefined)
120
+ push(args, "--max-downloads", String(selection.maxDownloads));
121
+ if (selection.breakOnExisting)
122
+ args.push("--break-on-existing");
123
+ if (selection.breakPerInput)
124
+ args.push("--break-per-input");
125
+ if (selection.skipPlaylistAfterErrors !== undefined)
126
+ push(args, "--skip-playlist-after-errors", String(selection.skipPlaylistAfterErrors));
127
+ }
128
+ function configuredOrAllowed(inputValue, configuredValue, label, config) {
129
+ if (inputValue !== undefined && inputValue !== configuredValue)
130
+ requireConfigFilePolicy(label, config);
131
+ return inputValue ?? configuredValue;
132
+ }
133
+ function requireConfigFilePolicy(label, config) {
134
+ if (!config.allowConfigFiles)
135
+ throw new Error(`${label} requires YTDLP_MCP_ALLOW_CONFIG_FILES=true or a matching server-level environment setting`);
136
+ }
137
+ function appendDownloadArgs(args, input) {
138
+ const download = input.download;
139
+ if (download.concurrentFragments !== undefined)
140
+ push(args, "--concurrent-fragments", String(download.concurrentFragments));
141
+ push(args, "--limit-rate", download.limitRate);
142
+ push(args, "--throttled-rate", download.throttledRate);
143
+ push(args, "--retries", download.retries);
144
+ push(args, "--file-access-retries", download.fileAccessRetries);
145
+ push(args, "--fragment-retries", download.fragmentRetries);
146
+ pushRepeated(args, "--retry-sleep", download.retrySleep);
147
+ if (download.keepFragments)
148
+ args.push("--keep-fragments");
149
+ push(args, "--buffer-size", download.bufferSize);
150
+ push(args, "--http-chunk-size", download.httpChunkSize);
151
+ if (download.playlistRandom)
152
+ args.push("--playlist-random");
153
+ if (download.lazyPlaylist)
154
+ args.push("--lazy-playlist");
155
+ if (download.hlsUseMpegts)
156
+ args.push("--hls-use-mpegts");
157
+ pushRepeated(args, "--download-sections", download.downloadSections);
158
+ pushRepeated(args, "--downloader", download.downloader);
159
+ pushRepeated(args, "--downloader-args", download.downloaderArgs);
160
+ }
161
+ function appendFormatArgs(args, input) {
162
+ const format = input.format;
163
+ push(args, "--format", format.format);
164
+ pushRepeated(args, "--format-sort", format.formatSort);
165
+ if (format.formatSortReset)
166
+ args.push("--format-sort-reset");
167
+ if (format.formatSortForce)
168
+ args.push("--format-sort-force");
169
+ if (format.videoMultistreams)
170
+ args.push("--video-multistreams");
171
+ if (format.audioMultistreams)
172
+ args.push("--audio-multistreams");
173
+ if (format.preferFreeFormats)
174
+ args.push("--prefer-free-formats");
175
+ if (format.checkFormats)
176
+ args.push("--check-formats");
177
+ if (format.checkAllFormats)
178
+ args.push("--check-all-formats");
179
+ push(args, "--merge-output-format", format.mergeOutputFormat);
180
+ }
181
+ function appendSubtitleArgs(args, input) {
182
+ const subtitles = input.subtitles;
183
+ if (subtitles.writeSubs)
184
+ args.push("--write-subs");
185
+ if (subtitles.writeAutoSubs)
186
+ args.push("--write-auto-subs");
187
+ push(args, "--sub-format", subtitles.subFormat);
188
+ push(args, "--sub-langs", subtitles.subLangs);
189
+ push(args, "--convert-subs", subtitles.convertSubs);
190
+ }
191
+ function appendThumbnailArgs(args, input) {
192
+ const thumbnails = input.thumbnails;
193
+ if (thumbnails.writeThumbnail)
194
+ args.push("--write-thumbnail");
195
+ if (thumbnails.writeAllThumbnails)
196
+ args.push("--write-all-thumbnails");
197
+ push(args, "--convert-thumbnails", thumbnails.convertThumbnails);
198
+ }
199
+ function appendPostprocessArgs(args, input) {
200
+ const postprocess = input.postprocess;
201
+ if (postprocess.extractAudio)
202
+ args.push("--extract-audio");
203
+ push(args, "--audio-format", postprocess.audioFormat);
204
+ push(args, "--audio-quality", postprocess.audioQuality);
205
+ push(args, "--remux-video", postprocess.remuxVideo);
206
+ push(args, "--recode-video", postprocess.recodeVideo);
207
+ pushRepeated(args, "--postprocessor-args", postprocess.postprocessorArgs);
208
+ if (postprocess.keepVideo)
209
+ args.push("--keep-video");
210
+ if (postprocess.postOverwrites)
211
+ args.push("--post-overwrites");
212
+ if (postprocess.embedSubs)
213
+ args.push("--embed-subs");
214
+ if (postprocess.embedThumbnail)
215
+ args.push("--embed-thumbnail");
216
+ if (postprocess.embedMetadata)
217
+ args.push("--embed-metadata");
218
+ if (postprocess.embedChapters)
219
+ args.push("--embed-chapters");
220
+ if (postprocess.embedInfoJson)
221
+ args.push("--embed-info-json");
222
+ pushRepeated(args, "--parse-metadata", postprocess.parseMetadata);
223
+ pushRepeated(args, "--replace-in-metadata", postprocess.replaceInMetadata);
224
+ if (postprocess.xattrs)
225
+ args.push("--xattrs");
226
+ push(args, "--concat-playlist", postprocess.concatPlaylist);
227
+ push(args, "--fixup", postprocess.fixup);
228
+ if (postprocess.splitChapters)
229
+ args.push("--split-chapters");
230
+ pushRepeated(args, "--remove-chapters", postprocess.removeChapters);
231
+ if (postprocess.forceKeyframesAtCuts)
232
+ args.push("--force-keyframes-at-cuts");
233
+ pushRepeated(args, "--use-postprocessor", postprocess.usePostprocessor);
234
+ }
235
+ function appendSponsorBlockArgs(args, input) {
236
+ push(args, "--sponsorblock-mark", input.sponsorblock.mark);
237
+ push(args, "--sponsorblock-remove", input.sponsorblock.remove);
238
+ push(args, "--sponsorblock-chapter-title", input.sponsorblock.chapterTitle);
239
+ push(args, "--sponsorblock-api", input.sponsorblock.api);
240
+ }
241
+ function appendExtractorArgs(args, input) {
242
+ const extractor = input.extractor;
243
+ push(args, "--extractor-retries", extractor.extractorRetries);
244
+ if (extractor.allowDynamicMpd)
245
+ args.push("--allow-dynamic-mpd");
246
+ if (extractor.hlsSplitDiscontinuity)
247
+ args.push("--hls-split-discontinuity");
248
+ pushRepeated(args, "--extractor-args", extractor.extractorArgs);
249
+ const youtube = extractor.youtube;
250
+ if (!youtube)
251
+ return;
252
+ push(args, "--extractor-args", keyed("youtube", "lang", youtube.lang));
253
+ push(args, "--extractor-args", keyed("youtube", "comment_sort", youtube.commentSort));
254
+ push(args, "--extractor-args", keyed("youtube", "max_comments", youtube.maxComments));
255
+ push(args, "--extractor-args", keyed("youtube", "fetch_pot", youtube.fetchPot));
256
+ pushJoined(args, "youtube", "skip", youtube.skip);
257
+ pushJoined(args, "youtube", "player_client", youtube.playerClient);
258
+ pushJoined(args, "youtube", "formats", youtube.formats);
259
+ pushJoined(args, "youtube", "po_token", youtube.poToken);
260
+ }
261
+ function keyed(namespace, key, value) {
262
+ return value ? `${namespace}:${key}=${value}` : undefined;
263
+ }
264
+ function pushJoined(args, namespace, key, values) {
265
+ if (values.length > 0)
266
+ push(args, "--extractor-args", `${namespace}:${key}=${values.join(",")}`);
267
+ }
268
+ function push(args, flag, value) {
269
+ if (value !== undefined && value !== "")
270
+ args.push(flag, value);
271
+ }
272
+ function pushRepeated(args, flag, values) {
273
+ for (const value of values)
274
+ push(args, flag, value);
275
+ }
276
+ //# sourceMappingURL=argv.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"argv.js","sourceRoot":"","sources":["../src/argv.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,20 @@
1
+ export interface ServerConfig {
2
+ ytdlpPath: string;
3
+ ffmpegPath?: string | undefined;
4
+ ffprobePath?: string | undefined;
5
+ outputRoot: string;
6
+ tempRoot: string;
7
+ allowArbitraryOutputPaths: boolean;
8
+ allowConfigFiles: boolean;
9
+ allowPluginDirs: boolean;
10
+ enableExpertMode: boolean;
11
+ defaultTimeoutMs: number;
12
+ maxOutputBytes: number;
13
+ cookiesFile?: string | undefined;
14
+ cookiesFromBrowser?: string | undefined;
15
+ jsRuntimes: string[];
16
+ }
17
+ export declare function expandHome(input: string): string;
18
+ export declare function loadConfig(env?: NodeJS.ProcessEnv): ServerConfig;
19
+ export declare const CONFIG: ServerConfig;
20
+ //# sourceMappingURL=config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAGA,MAAM,WAAW,YAAY;IAC3B,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IAChC,WAAW,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACjC,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;IACjB,yBAAyB,EAAE,OAAO,CAAC;IACnC,gBAAgB,EAAE,OAAO,CAAC;IAC1B,eAAe,EAAE,OAAO,CAAC;IACzB,gBAAgB,EAAE,OAAO,CAAC;IAC1B,gBAAgB,EAAE,MAAM,CAAC;IACzB,cAAc,EAAE,MAAM,CAAC;IACvB,WAAW,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACjC,kBAAkB,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACxC,UAAU,EAAE,MAAM,EAAE,CAAC;CACtB;AAWD,wBAAgB,UAAU,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAIhD;AAED,wBAAgB,UAAU,CAAC,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,YAAY,CAiB7E;AAED,eAAO,MAAM,MAAM,cAAe,CAAC"}
package/dist/config.js ADDED
@@ -0,0 +1,36 @@
1
+ import os from "node:os";
2
+ import path from "node:path";
3
+ function bool(value) {
4
+ return value ? ["1", "true", "yes", "on"].includes(value.toLowerCase()) : false;
5
+ }
6
+ function int(value, fallback) {
7
+ const parsed = value ? Number.parseInt(value, 10) : Number.NaN;
8
+ return Number.isFinite(parsed) ? parsed : fallback;
9
+ }
10
+ export function expandHome(input) {
11
+ if (input === "~")
12
+ return os.homedir();
13
+ if (input.startsWith("~/") || input.startsWith("~\\"))
14
+ return path.join(os.homedir(), input.slice(2));
15
+ return input;
16
+ }
17
+ export function loadConfig(env = process.env) {
18
+ return {
19
+ ytdlpPath: env.YTDLP_MCP_YTDLP_PATH ?? env.YTDLP_PATH ?? "yt-dlp",
20
+ ffmpegPath: env.YTDLP_MCP_FFMPEG_PATH ?? env.FFMPEG_PATH,
21
+ ffprobePath: env.YTDLP_MCP_FFPROBE_PATH ?? env.FFPROBE_PATH,
22
+ outputRoot: path.resolve(expandHome(env.YTDLP_MCP_OUTPUT_ROOT ?? path.join(os.homedir(), "Downloads", "yt-dlp-mcp"))),
23
+ tempRoot: path.resolve(expandHome(env.YTDLP_MCP_TEMP_ROOT ?? path.join(os.tmpdir(), "yt-dlp-mcp"))),
24
+ allowArbitraryOutputPaths: bool(env.YTDLP_MCP_ALLOW_ARBITRARY_OUTPUT_PATHS),
25
+ allowConfigFiles: bool(env.YTDLP_MCP_ALLOW_CONFIG_FILES),
26
+ allowPluginDirs: bool(env.YTDLP_MCP_ALLOW_PLUGIN_DIRS),
27
+ enableExpertMode: bool(env.YTDLP_MCP_ENABLE_EXPERT),
28
+ defaultTimeoutMs: int(env.YTDLP_MCP_TIMEOUT_MS, 15 * 60 * 1000),
29
+ maxOutputBytes: int(env.YTDLP_MCP_MAX_OUTPUT_BYTES, 4 * 1024 * 1024),
30
+ cookiesFile: env.YTDLP_MCP_COOKIES_FILE,
31
+ cookiesFromBrowser: env.YTDLP_MCP_COOKIES_FROM_BROWSER,
32
+ jsRuntimes: (env.YTDLP_MCP_JS_RUNTIMES ?? "deno,node,bun,quickjs").split(",").map((v) => v.trim()).filter(Boolean)
33
+ };
34
+ }
35
+ export const CONFIG = loadConfig();
36
+ //# sourceMappingURL=config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,SAAS,CAAC;AACzB,OAAO,IAAI,MAAM,WAAW,CAAC;AAmB7B,SAAS,IAAI,CAAC,KAAyB;IACrC,OAAO,KAAK,CAAC,CAAC,CAAC,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,EAAE,IAAI,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC;AAClF,CAAC;AAED,SAAS,GAAG,CAAC,KAAyB,EAAE,QAAgB;IACtD,MAAM,MAAM,GAAG,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC;IAC/D,OAAO,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,QAAQ,CAAC;AACrD,CAAC;AAED,MAAM,UAAU,UAAU,CAAC,KAAa;IACtC,IAAI,KAAK,KAAK,GAAG;QAAE,OAAO,EAAE,CAAC,OAAO,EAAE,CAAC;IACvC,IAAI,KAAK,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,KAAK,CAAC,UAAU,CAAC,KAAK,CAAC;QAAE,OAAO,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,OAAO,EAAE,EAAE,KAAK,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC;IACtG,OAAO,KAAK,CAAC;AACf,CAAC;AAED,MAAM,UAAU,UAAU,CAAC,MAAyB,OAAO,CAAC,GAAG;IAC7D,OAAO;QACL,SAAS,EAAE,GAAG,CAAC,oBAAoB,IAAI,GAAG,CAAC,UAAU,IAAI,QAAQ;QACjE,UAAU,EAAE,GAAG,CAAC,qBAAqB,IAAI,GAAG,CAAC,WAAW;QACxD,WAAW,EAAE,GAAG,CAAC,sBAAsB,IAAI,GAAG,CAAC,YAAY;QAC3D,UAAU,EAAE,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC,GAAG,CAAC,qBAAqB,IAAI,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,OAAO,EAAE,EAAE,WAAW,EAAE,YAAY,CAAC,CAAC,CAAC;QACrH,QAAQ,EAAE,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC,GAAG,CAAC,mBAAmB,IAAI,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,EAAE,EAAE,YAAY,CAAC,CAAC,CAAC;QACnG,yBAAyB,EAAE,IAAI,CAAC,GAAG,CAAC,sCAAsC,CAAC;QAC3E,gBAAgB,EAAE,IAAI,CAAC,GAAG,CAAC,4BAA4B,CAAC;QACxD,eAAe,EAAE,IAAI,CAAC,GAAG,CAAC,2BAA2B,CAAC;QACtD,gBAAgB,EAAE,IAAI,CAAC,GAAG,CAAC,uBAAuB,CAAC;QACnD,gBAAgB,EAAE,GAAG,CAAC,GAAG,CAAC,oBAAoB,EAAE,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC;QAC/D,cAAc,EAAE,GAAG,CAAC,GAAG,CAAC,0BAA0B,EAAE,CAAC,GAAG,IAAI,GAAG,IAAI,CAAC;QACpE,WAAW,EAAE,GAAG,CAAC,sBAAsB;QACvC,kBAAkB,EAAE,GAAG,CAAC,8BAA8B;QACtD,UAAU,EAAE,CAAC,GAAG,CAAC,qBAAqB,IAAI,uBAAuB,CAAC,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC;KACnH,CAAC;AACJ,CAAC;AAED,MAAM,CAAC,MAAM,MAAM,GAAG,UAAU,EAAE,CAAC"}
@@ -0,0 +1,27 @@
1
+ import { type ServerConfig } from "./config.js";
2
+ import type { DetectedDependency } from "./types.js";
3
+ export interface EnvironmentReport {
4
+ platform: NodeJS.Platform;
5
+ arch: string;
6
+ node: {
7
+ version: string;
8
+ execPath: string;
9
+ };
10
+ dependencies: DetectedDependency[];
11
+ cookies: {
12
+ fileConfigured: boolean;
13
+ fileExists?: boolean;
14
+ browserConfigured: boolean;
15
+ browser?: string;
16
+ };
17
+ policy: {
18
+ outputRoot: string;
19
+ tempRoot: string;
20
+ allowArbitraryOutputPaths: boolean;
21
+ allowConfigFiles: boolean;
22
+ allowPluginDirs: boolean;
23
+ enableExpertMode: boolean;
24
+ };
25
+ }
26
+ export declare function checkEnvironment(config?: ServerConfig): Promise<EnvironmentReport>;
27
+ //# sourceMappingURL=environment.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"environment.d.ts","sourceRoot":"","sources":["../src/environment.ts"],"names":[],"mappings":"AAEA,OAAO,EAAU,KAAK,YAAY,EAAE,MAAM,aAAa,CAAC;AAExD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,YAAY,CAAC;AAErD,MAAM,WAAW,iBAAiB;IAChC,QAAQ,EAAE,MAAM,CAAC,QAAQ,CAAC;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE;QACJ,OAAO,EAAE,MAAM,CAAC;QAChB,QAAQ,EAAE,MAAM,CAAC;KAClB,CAAC;IACF,YAAY,EAAE,kBAAkB,EAAE,CAAC;IACnC,OAAO,EAAE;QACP,cAAc,EAAE,OAAO,CAAC;QACxB,UAAU,CAAC,EAAE,OAAO,CAAC;QACrB,iBAAiB,EAAE,OAAO,CAAC;QAC3B,OAAO,CAAC,EAAE,MAAM,CAAC;KAClB,CAAC;IACF,MAAM,EAAE;QACN,UAAU,EAAE,MAAM,CAAC;QACnB,QAAQ,EAAE,MAAM,CAAC;QACjB,yBAAyB,EAAE,OAAO,CAAC;QACnC,gBAAgB,EAAE,OAAO,CAAC;QAC1B,eAAe,EAAE,OAAO,CAAC;QACzB,gBAAgB,EAAE,OAAO,CAAC;KAC3B,CAAC;CACH;AAED,wBAAsB,gBAAgB,CAAC,MAAM,GAAE,YAAqB,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAiChG"}
@@ -0,0 +1,80 @@
1
+ import fs from "node:fs";
2
+ import os from "node:os";
3
+ import { CONFIG } from "./config.js";
4
+ import { runCommand } from "./runner.js";
5
+ export async function checkEnvironment(config = CONFIG) {
6
+ const dependencies = await Promise.all([
7
+ detectBinary("yt-dlp", config.ytdlpPath, ["--version"], ["all yt-dlp operations"], true, config),
8
+ detectBinary("ffmpeg", config.ffmpegPath ?? "ffmpeg", ["-version"], ["merge", "remux", "recode", "extract audio", "embed assets"], false, config),
9
+ detectBinary("ffprobe", config.ffprobePath ?? "ffprobe", ["-version"], ["audio extraction", "media probing"], false, config),
10
+ detectBinary("deno", "deno", ["--version"], ["yt-dlp JavaScript challenges"], false, config),
11
+ detectBinary("node", process.execPath, ["--version"], ["yt-dlp JavaScript challenges"], false, config),
12
+ detectBinary("bun", "bun", ["--version"], ["yt-dlp JavaScript challenges"], false, config),
13
+ detectBinary("qjs", "qjs", ["--version"], ["yt-dlp JavaScript challenges"], false, config),
14
+ detectBinary("AtomicParsley", "AtomicParsley", ["--version"], ["legacy thumbnail embedding"], false, config),
15
+ detectBinary("aria2c", "aria2c", ["--version"], ["external downloader"], false, config),
16
+ detectBinary("curl", "curl", ["--version"], ["external downloader"], false, config),
17
+ detectBinary("wget", "wget", ["--version"], ["external downloader"], false, config)
18
+ ]);
19
+ return {
20
+ platform: process.platform,
21
+ arch: os.arch(),
22
+ node: {
23
+ version: process.version,
24
+ execPath: process.execPath
25
+ },
26
+ dependencies,
27
+ cookies: cookieStatus(config),
28
+ policy: {
29
+ outputRoot: config.outputRoot,
30
+ tempRoot: config.tempRoot,
31
+ allowArbitraryOutputPaths: config.allowArbitraryOutputPaths,
32
+ allowConfigFiles: config.allowConfigFiles,
33
+ allowPluginDirs: config.allowPluginDirs,
34
+ enableExpertMode: config.enableExpertMode
35
+ }
36
+ };
37
+ }
38
+ async function detectBinary(name, command, args, requiredFor, required, config) {
39
+ try {
40
+ const result = await runCommand(command, args, {
41
+ timeoutMs: Math.min(config.defaultTimeoutMs, 10_000),
42
+ maxOutputBytes: 64 * 1024
43
+ });
44
+ return {
45
+ name,
46
+ status: "available",
47
+ command,
48
+ version: firstLine(result.stdout || result.stderr),
49
+ requiredFor,
50
+ notes: required ? [] : ["Optional dependency; required only for matching workflows."]
51
+ };
52
+ }
53
+ catch (error) {
54
+ return {
55
+ name,
56
+ status: "missing",
57
+ command,
58
+ requiredFor,
59
+ notes: [required ? "Required dependency is not available." : "Optional dependency is not available.", error instanceof Error ? error.message : String(error)]
60
+ };
61
+ }
62
+ }
63
+ function cookieStatus(config) {
64
+ const status = {
65
+ fileConfigured: Boolean(config.cookiesFile),
66
+ browserConfigured: Boolean(config.cookiesFromBrowser)
67
+ };
68
+ if (config.cookiesFile)
69
+ status.fileExists = fs.existsSync(config.cookiesFile);
70
+ if (config.cookiesFromBrowser) {
71
+ const browser = config.cookiesFromBrowser.split(":")[0];
72
+ if (browser)
73
+ status.browser = browser;
74
+ }
75
+ return status;
76
+ }
77
+ function firstLine(value) {
78
+ return value.split(/\r?\n/).map((line) => line.trim()).find(Boolean) ?? "";
79
+ }
80
+ //# sourceMappingURL=environment.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"environment.js","sourceRoot":"","sources":["../src/environment.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ import type { StructuredError } from "./types.js";
2
+ export declare function toStructuredError(error: unknown): StructuredError;
3
+ //# sourceMappingURL=errors.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../src/errors.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,YAAY,CAAC;AAElD,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,OAAO,GAAG,eAAe,CAmCjE"}
package/dist/errors.js ADDED
@@ -0,0 +1,73 @@
1
+ import { classifyYtDlpStderr, errorKindMetadata, extractLastError } from "ytdlp-errors";
2
+ import { excerpt } from "./redaction.js";
3
+ import { CommandExecutionError } from "./runner.js";
4
+ export function toStructuredError(error) {
5
+ if (error instanceof CommandExecutionError) {
6
+ const stderr = error.result.stderr || error.result.stdout || error.message;
7
+ const classified = classifyYtDlpStderr(stderr);
8
+ const kind = inferUnsupportedUrl(stderr) ? "unsupportedUrl" : classified.kind;
9
+ const metadata = errorKindMetadata(kind);
10
+ const structured = {
11
+ kind,
12
+ message: extractLastError(stderr) || error.message,
13
+ retryable: metadata.recoverable,
14
+ exitCode: error.result.exitCode,
15
+ stderrExcerpt: excerpt(stderr),
16
+ suggestedFixes: suggestedFixes(kind, metadata.suggestedFlags)
17
+ };
18
+ const dependency = inferDependency(stderr);
19
+ if (dependency)
20
+ structured.dependency = dependency;
21
+ return structured;
22
+ }
23
+ if (error instanceof Error) {
24
+ return {
25
+ kind: "internal",
26
+ message: error.message,
27
+ retryable: false,
28
+ stderrExcerpt: excerpt(error.stack ?? error.message),
29
+ suggestedFixes: []
30
+ };
31
+ }
32
+ return {
33
+ kind: "internal",
34
+ message: String(error),
35
+ retryable: false,
36
+ suggestedFixes: []
37
+ };
38
+ }
39
+ function inferDependency(text) {
40
+ if (/ffmpeg/i.test(text))
41
+ return "ffmpeg";
42
+ if (/ffprobe/i.test(text))
43
+ return "ffprobe";
44
+ if (/atomicparsley/i.test(text))
45
+ return "AtomicParsley";
46
+ if (/aria2c/i.test(text))
47
+ return "aria2c";
48
+ if (/curl_cffi|impersonat/i.test(text))
49
+ return "curl_cffi";
50
+ if (/deno|node|bun|quickjs|javascript/i.test(text))
51
+ return "js-runtime";
52
+ return undefined;
53
+ }
54
+ function inferUnsupportedUrl(text) {
55
+ return /unsupported url|no suitable extractor|not a valid URL/i.test(text);
56
+ }
57
+ function suggestedFixes(kind, flags) {
58
+ const fixes = new Set();
59
+ for (const flag of flags ?? [])
60
+ fixes.add(`Consider ${flag} when appropriate.`);
61
+ if (kind === "missingDependency")
62
+ fixes.add("Install the missing dependency or configure its path with the matching server environment variable.");
63
+ if (kind === "botBlock" || kind === "loginRequired" || kind === "ageRestricted")
64
+ fixes.add("Provide cookies via a cookies file or cookies-from-browser configuration.");
65
+ if (kind === "rateLimit")
66
+ fixes.add("Retry later or add conservative sleep/retry settings.");
67
+ if (kind === "geoBlocked")
68
+ fixes.add("Use an allowed region, proxy, or yt-dlp geo-bypass option where legal.");
69
+ if (kind === "outOfDiskSpace")
70
+ fixes.add("Free disk space or choose a different output root.");
71
+ return [...fixes];
72
+ }
73
+ //# sourceMappingURL=errors.js.map