simple-ffmpegjs 0.5.4 → 0.5.5
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/package.json +1 -1
- package/src/core/validation.js +5 -2
- package/src/simpleffmpeg.js +19 -1
- package/types/index.d.mts +19 -1
- package/types/index.d.ts +19 -1
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "simple-ffmpegjs",
|
|
3
|
-
"version": "0.5.
|
|
3
|
+
"version": "0.5.5",
|
|
4
4
|
"description": "Declarative video composition for Node.js — define clips, transitions, text, and audio as simple objects, and let FFmpeg handle the rest.",
|
|
5
5
|
"author": "Brayden Blackwell <braydenblackwell21@gmail.com> (https://github.com/Fats403)",
|
|
6
6
|
"license": "MIT",
|
package/src/core/validation.js
CHANGED
|
@@ -388,7 +388,7 @@ function validateEffectClip(clip, path, errors) {
|
|
|
388
388
|
* Validate a single clip and return issues
|
|
389
389
|
*/
|
|
390
390
|
function validateClip(clip, index, options = {}) {
|
|
391
|
-
const { skipFileChecks = false } = options;
|
|
391
|
+
const { skipFileChecks = false, skipExtensionsCheck = false } = options;
|
|
392
392
|
const errors = [];
|
|
393
393
|
const warnings = [];
|
|
394
394
|
const path = `clips[${index}]`;
|
|
@@ -639,7 +639,9 @@ function validateClip(clip, index, options = {}) {
|
|
|
639
639
|
} catch (_) {}
|
|
640
640
|
}
|
|
641
641
|
|
|
642
|
-
|
|
642
|
+
if (!skipExtensionsCheck) {
|
|
643
|
+
validateMediaUrlExtension(clip, path, errors);
|
|
644
|
+
}
|
|
643
645
|
|
|
644
646
|
if (typeof clip.cutFrom === "number") {
|
|
645
647
|
if (!Number.isFinite(clip.cutFrom)) {
|
|
@@ -1406,6 +1408,7 @@ function validateTimelineGaps(clips) {
|
|
|
1406
1408
|
* @param {Array} clips - Array of clip objects to validate
|
|
1407
1409
|
* @param {Object} options - Validation options
|
|
1408
1410
|
* @param {boolean} options.skipFileChecks - Skip file existence checks (useful for AI validation)
|
|
1411
|
+
* @param {boolean} options.skipExtensionsCheck - Skip media extension/type checks (video/image)
|
|
1409
1412
|
* @returns {Object} Validation result { valid, errors, warnings }
|
|
1410
1413
|
*/
|
|
1411
1414
|
function validateConfig(clips, options = {}) {
|
package/src/simpleffmpeg.js
CHANGED
|
@@ -63,6 +63,8 @@ class SIMPLEFFMPEG {
|
|
|
63
63
|
* @param {number} options.fps - Frames per second (default: 30)
|
|
64
64
|
* @param {string} options.preset - Platform preset ('tiktok', 'youtube', 'instagram-post', etc.)
|
|
65
65
|
* @param {string} options.validationMode - Validation behavior: 'warn' or 'strict' (default: 'warn')
|
|
66
|
+
* @param {boolean} options.skipFileChecks - Skip file existence checks during load() validation
|
|
67
|
+
* @param {boolean} options.skipExtensionsCheck - Skip media URL extension/type checks (video/image) during load() validation
|
|
66
68
|
* @param {string} options.fontFile - Default font file path (.ttf, .otf) applied to all text clips unless overridden per-clip
|
|
67
69
|
* @param {string} options.emojiFont - Path to a .ttf/.otf emoji font for rendering emoji in text overlays (opt-in). Without this, emoji are silently stripped from text. Recommended: Noto Emoji (B&W outline).
|
|
68
70
|
* @param {string} options.tempDir - Custom directory for temporary files (gradient images, unrotated videos, intermediate renders). Defaults to os.tmpdir(). Useful for fast SSDs, ramdisks, or environments with constrained /tmp.
|
|
@@ -97,6 +99,8 @@ class SIMPLEFFMPEG {
|
|
|
97
99
|
width: options.width || presetConfig.width || C.DEFAULT_WIDTH,
|
|
98
100
|
height: options.height || presetConfig.height || C.DEFAULT_HEIGHT,
|
|
99
101
|
validationMode: options.validationMode || C.DEFAULT_VALIDATION_MODE,
|
|
102
|
+
skipFileChecks: options.skipFileChecks === true,
|
|
103
|
+
skipExtensionsCheck: options.skipExtensionsCheck === true,
|
|
100
104
|
preset: options.preset || null,
|
|
101
105
|
fontFile: options.fontFile || null,
|
|
102
106
|
emojiFont: options.emojiFont || null,
|
|
@@ -279,6 +283,9 @@ class SIMPLEFFMPEG {
|
|
|
279
283
|
* @param {string} clipObjs[].text - Text content (for text clips)
|
|
280
284
|
* @param {string} clipObjs[].mode - Text mode: 'static', 'word-replace', 'word-sequential', 'karaoke'
|
|
281
285
|
* @param {string} clipObjs[].kenBurns - Ken Burns effect for images: 'zoom-in', 'zoom-out', 'pan-left', etc.
|
|
286
|
+
* @param {Object} options - Load options
|
|
287
|
+
* @param {boolean} options.skipFileChecks - Override file existence checks for media URLs
|
|
288
|
+
* @param {boolean} options.skipExtensionsCheck - Override extension/type validation for media URLs
|
|
282
289
|
* @returns {Promise<void>} Resolves when all clips are loaded
|
|
283
290
|
* @throws {ValidationError} If clip configuration is invalid
|
|
284
291
|
*
|
|
@@ -288,7 +295,7 @@ class SIMPLEFFMPEG {
|
|
|
288
295
|
* { type: 'text', text: 'Hello', position: 1, end: 4, fontSize: 48 }
|
|
289
296
|
* ]);
|
|
290
297
|
*/
|
|
291
|
-
async load(clipObjs) {
|
|
298
|
+
async load(clipObjs, options = {}) {
|
|
292
299
|
// Guard against concurrent load() calls
|
|
293
300
|
if (this._isLoading) {
|
|
294
301
|
throw new SimpleffmpegError(
|
|
@@ -308,11 +315,21 @@ class SIMPLEFFMPEG {
|
|
|
308
315
|
|
|
309
316
|
// Resolve shorthand: duration → end, auto-sequential positioning
|
|
310
317
|
const resolved = resolveClips(clipObjs);
|
|
318
|
+
const skipExtensionsCheck =
|
|
319
|
+
typeof options.skipExtensionsCheck === "boolean"
|
|
320
|
+
? options.skipExtensionsCheck
|
|
321
|
+
: this.options.skipExtensionsCheck;
|
|
322
|
+
const skipFileChecks =
|
|
323
|
+
typeof options.skipFileChecks === "boolean"
|
|
324
|
+
? options.skipFileChecks
|
|
325
|
+
: this.options.skipFileChecks;
|
|
311
326
|
|
|
312
327
|
// Merge resolution errors into validation
|
|
313
328
|
const result = validateConfig(resolved.clips, {
|
|
314
329
|
width: this.options.width,
|
|
315
330
|
height: this.options.height,
|
|
331
|
+
skipFileChecks,
|
|
332
|
+
skipExtensionsCheck,
|
|
316
333
|
});
|
|
317
334
|
|
|
318
335
|
// Prepend resolution errors (e.g. duration+end conflict)
|
|
@@ -1286,6 +1303,7 @@ class SIMPLEFFMPEG {
|
|
|
1286
1303
|
* @param {Array} clips - Array of clip objects to validate
|
|
1287
1304
|
* @param {Object} options - Validation options
|
|
1288
1305
|
* @param {boolean} options.skipFileChecks - Skip file existence checks (useful for AI)
|
|
1306
|
+
* @param {boolean} options.skipExtensionsCheck - Skip media URL extension/type checks (video/image)
|
|
1289
1307
|
* @returns {Object} Validation result { valid, errors, warnings }
|
|
1290
1308
|
*
|
|
1291
1309
|
* @example
|
package/types/index.d.mts
CHANGED
|
@@ -434,6 +434,8 @@ declare namespace SIMPLEFFMPEG {
|
|
|
434
434
|
interface ValidateOptions {
|
|
435
435
|
/** Skip file existence checks (useful for AI generating configs before files exist) */
|
|
436
436
|
skipFileChecks?: boolean;
|
|
437
|
+
/** Skip media URL extension/type checks for video/image clips */
|
|
438
|
+
skipExtensionsCheck?: boolean;
|
|
437
439
|
/** Project width - used to validate Ken Burns images are large enough */
|
|
438
440
|
width?: number;
|
|
439
441
|
/** Project height - used to validate Ken Burns images are large enough */
|
|
@@ -453,6 +455,10 @@ declare namespace SIMPLEFFMPEG {
|
|
|
453
455
|
height?: number;
|
|
454
456
|
/** Validation mode: 'warn' logs warnings, 'strict' throws on warnings (default: 'warn') */
|
|
455
457
|
validationMode?: "warn" | "strict";
|
|
458
|
+
/** Skip file existence checks during load() validation */
|
|
459
|
+
skipFileChecks?: boolean;
|
|
460
|
+
/** Skip media URL extension/type checks for video/image clips during load() validation */
|
|
461
|
+
skipExtensionsCheck?: boolean;
|
|
456
462
|
/** Default font file path (.ttf, .otf) applied to all text clips. Individual clips can override this with their own fontFile. */
|
|
457
463
|
fontFile?: string;
|
|
458
464
|
/** Path to a .ttf/.otf emoji font for rendering emoji in text overlays (opt-in). Without this, emoji are silently stripped from text. Recommended: Noto Emoji (B&W outline). */
|
|
@@ -868,6 +874,14 @@ declare namespace SIMPLEFFMPEG {
|
|
|
868
874
|
totalDuration: number;
|
|
869
875
|
}
|
|
870
876
|
|
|
877
|
+
/** Options for load() */
|
|
878
|
+
interface LoadOptions {
|
|
879
|
+
/** Override file existence checks for media URLs */
|
|
880
|
+
skipFileChecks?: boolean;
|
|
881
|
+
/** Override extension/type validation for media URLs (video/image) */
|
|
882
|
+
skipExtensionsCheck?: boolean;
|
|
883
|
+
}
|
|
884
|
+
|
|
871
885
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
872
886
|
// Media Info (probe)
|
|
873
887
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
@@ -911,8 +925,12 @@ declare class SIMPLEFFMPEG {
|
|
|
911
925
|
/**
|
|
912
926
|
* Load clips into the project
|
|
913
927
|
* @param clips Array of clip descriptors (video, audio, text, image, music)
|
|
928
|
+
* @param options Load options
|
|
914
929
|
*/
|
|
915
|
-
load(
|
|
930
|
+
load(
|
|
931
|
+
clips: SIMPLEFFMPEG.Clip[],
|
|
932
|
+
options?: SIMPLEFFMPEG.LoadOptions
|
|
933
|
+
): Promise<void[]>;
|
|
916
934
|
|
|
917
935
|
/**
|
|
918
936
|
* Get a preview of the FFmpeg command without executing it (dry-run)
|
package/types/index.d.ts
CHANGED
|
@@ -434,6 +434,8 @@ declare namespace SIMPLEFFMPEG {
|
|
|
434
434
|
interface ValidateOptions {
|
|
435
435
|
/** Skip file existence checks (useful for AI generating configs before files exist) */
|
|
436
436
|
skipFileChecks?: boolean;
|
|
437
|
+
/** Skip media URL extension/type checks for video/image clips */
|
|
438
|
+
skipExtensionsCheck?: boolean;
|
|
437
439
|
/** Project width - used to validate Ken Burns images are large enough */
|
|
438
440
|
width?: number;
|
|
439
441
|
/** Project height - used to validate Ken Burns images are large enough */
|
|
@@ -453,6 +455,10 @@ declare namespace SIMPLEFFMPEG {
|
|
|
453
455
|
height?: number;
|
|
454
456
|
/** Validation mode: 'warn' logs warnings, 'strict' throws on warnings (default: 'warn') */
|
|
455
457
|
validationMode?: "warn" | "strict";
|
|
458
|
+
/** Skip file existence checks during load() validation */
|
|
459
|
+
skipFileChecks?: boolean;
|
|
460
|
+
/** Skip media URL extension/type checks for video/image clips during load() validation */
|
|
461
|
+
skipExtensionsCheck?: boolean;
|
|
456
462
|
/** Default font file path (.ttf, .otf) applied to all text clips. Individual clips can override this with their own fontFile. */
|
|
457
463
|
fontFile?: string;
|
|
458
464
|
/** Path to a .ttf/.otf emoji font for rendering emoji in text overlays (opt-in). Without this, emoji are silently stripped from text. Recommended: Noto Emoji (B&W outline). */
|
|
@@ -868,6 +874,14 @@ declare namespace SIMPLEFFMPEG {
|
|
|
868
874
|
totalDuration: number;
|
|
869
875
|
}
|
|
870
876
|
|
|
877
|
+
/** Options for load() */
|
|
878
|
+
interface LoadOptions {
|
|
879
|
+
/** Override file existence checks for media URLs */
|
|
880
|
+
skipFileChecks?: boolean;
|
|
881
|
+
/** Override extension/type validation for media URLs (video/image) */
|
|
882
|
+
skipExtensionsCheck?: boolean;
|
|
883
|
+
}
|
|
884
|
+
|
|
871
885
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
872
886
|
// Media Info (probe)
|
|
873
887
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
@@ -911,8 +925,12 @@ declare class SIMPLEFFMPEG {
|
|
|
911
925
|
/**
|
|
912
926
|
* Load clips into the project
|
|
913
927
|
* @param clips Array of clip descriptors (video, audio, text, image, music)
|
|
928
|
+
* @param options Load options
|
|
914
929
|
*/
|
|
915
|
-
load(
|
|
930
|
+
load(
|
|
931
|
+
clips: SIMPLEFFMPEG.Clip[],
|
|
932
|
+
options?: SIMPLEFFMPEG.LoadOptions
|
|
933
|
+
): Promise<void[]>;
|
|
916
934
|
|
|
917
935
|
/**
|
|
918
936
|
* Get a preview of the FFmpeg command without executing it (dry-run)
|