1.9.14 • Published 8 months ago

@profullstack/transcoder v1.9.14

Weekly downloads
-
License
MIT
Repository
github
Last release
8 months ago

@profullstack/transcoder

A lightweight Node.js module for transcoding videos to web-friendly MP4 format using FFmpeg. This module is designed for server-side use and ensures compatibility with all modern browsers including Safari, Chrome, and Firefox on both desktop and mobile devices.

GitHub GitHub commit activity GitHub last commit npm version npm downloads npm bundle size

Windows macOS Linux

Features

  • Transcodes any video format to web-friendly MP4 (H.264/AAC)
  • Transcodes audio files between formats (MP3, AAC, FLAC, OGG, etc.)
  • Converts and optimizes images with various transformations (using ImageMagick)
  • Ensures compatibility across all modern browsers
  • Modern ESM (ECMAScript Modules) implementation
  • Async/await API with real-time progress reporting
  • Event-based progress tracking
  • Customizable encoding options
  • Smart Presets for popular platforms (Instagram, YouTube, Twitter, etc.)
  • Audio enhancement features (normalization, noise reduction, fades)
  • Thumbnail Generation at specified intervals or timestamps
  • Batch processing of multiple files with a fancy terminal UI
  • No file storage - just passes through to FFmpeg
  • Lightweight with minimal dependencies

Prerequisites

This module requires the following software to be installed on your system:

  1. FFmpeg and ffprobe - For video and audio processing

  2. ImageMagick - For image processing

    • Download from imagemagick.org
    • Required for image transformations, especially for PNG with transparency

Building FFmpeg from Source

The package includes a script to automatically build FFmpeg from source with custom flags optimized for video transcoding and thumbnail generation:

# Using npm
npm run install-ffmpeg

# Using yarn
yarn install-ffmpeg

# Using pnpm
pnpm install-ffmpeg

# Or directly
./bin/build-ffmpeg.sh

The build script:

  • Builds FFmpeg from source with optimized flags
  • Enables all necessary codecs and libraries for maximum compatibility
  • Includes support for ffprobe and thumbnail generation
  • Installs all required dependencies

The script supports:

  • macOS
  • Ubuntu/Debian
  • Arch Linux
  • Windows (via WSL - Windows Subsystem for Linux)

Installing ImageMagick

The package includes a script to automatically install ImageMagick with all necessary dependencies:

# Using npm
npm run install-imagemagick

# Using yarn
yarn install-imagemagick

# Using pnpm
pnpm install-imagemagick

# Or directly
./bin/install-imagemagick.sh

The script supports:

  • macOS (via Homebrew)
  • Ubuntu/Debian
  • Arch Linux
  • Windows (via Chocolatey)

If you already have FFmpeg installed but need to rebuild it (for example, if thumbnail generation is not working), you can use the --force flag:

# Force rebuild of FFmpeg from source
pnpm install-ffmpeg -- --force

# Or directly
./bin/build-ffmpeg.sh --force

The custom build includes support for:

  • H.264/H.265 encoding and decoding
  • AAC, MP3, and Opus audio codecs
  • VP8/VP9 video codecs
  • Hardware acceleration (when available)
  • Rubberband library (required for ffprobe and thumbnail generation)
  • And many other optimizations for video processing

If you prefer to install FFmpeg manually:

Ubuntu/Debian:

sudo apt update
sudo apt install ffmpeg

macOS (using Homebrew):

brew install ffmpeg

Windows (using Scoop - recommended):

# Install Scoop if not already installed
iwr -useb get.scoop.sh | iex

# Install FFmpeg
scoop install ffmpeg

Windows (using Chocolatey):

choco install ffmpeg

Arch Linux:

sudo pacman -S ffmpeg

Installation

npm install @profullstack/transcoder
# or
yarn add @profullstack/transcoder
# or
pnpm add @profullstack/transcoder

Usage

Basic Usage with Async/Await

import { transcode } from '@profullstack/transcoder';

async function transcodeVideo() {
  try {
    const { outputPath, emitter } = await transcode('input.mov', 'output.mp4');
    
    // Listen for progress events
    emitter.on('progress', (progress) => {
      console.log(`Progress: ${JSON.stringify(progress)}`);
      // Example output: {"frame":120,"fps":30,"time":4.5,"bitrate":1500,"size":1024000,"speed":2.5}
    });
    
    console.log('Transcoding completed successfully:', outputPath);
  } catch (error) {
    console.error('Transcoding failed:', error.message);
  }
}

transcodeVideo();

With Custom Options

import { transcode } from '@profullstack/transcoder';

async function transcodeWithOptions() {
  try {
    const options = {
      videoCodec: 'libx264',
      audioBitrate: '192k',
      videoBitrate: '2500k',
      width: 1280,
      height: 720,
      fps: 30,
      preset: 'slow',  // Higher quality but slower encoding
      overwrite: true  // Overwrite existing file if it exists
    };
    
    const { outputPath, emitter } = await transcode('input.mov', 'output.mp4', options);
    
    // Create a progress bar
    emitter.on('progress', (progress) => {
      if (progress.time) {
        const percent = Math.min(100, Math.round((progress.time / 60) * 100)); // Assuming 1-minute video
        const barLength = 30;
        const filledLength = Math.round(barLength * percent / 100);
        const bar = '█'.repeat(filledLength) + '░'.repeat(barLength - filledLength);
        
        process.stdout.write(`\r[${bar}] ${percent}% | ${progress.fps || 0} fps | ${progress.bitrate || 0} kbps`);
      }
    });
    
    console.log('\nTranscoding completed successfully:', outputPath);
  } catch (error) {
    console.error('Transcoding failed:', error.message);
  }
}

transcodeWithOptions();

Extracting Metadata

The module automatically extracts metadata from the input video during transcoding:

import { transcode } from '@profullstack/transcoder';

async function extractMetadata() {
  try {
    const { outputPath, metadata } = await transcode('input.mp4', 'output.mp4');
    
    // Display format information
    console.log('Format:', metadata.format.formatName);
    console.log('Duration:', metadata.format.duration, 'seconds');
    console.log('File Size:', metadata.format.size, 'bytes');
    console.log('Bitrate:', metadata.format.bitrate, 'bps');
    
    // Display video stream information
    console.log('Video Codec:', metadata.video.codec);
    console.log('Resolution:', metadata.video.width + 'x' + metadata.video.height);
    console.log('Frame Rate:', metadata.video.fps, 'fps');
    console.log('Pixel Format:', metadata.video.pixelFormat);
    
    // Display audio stream information
    console.log('Audio Codec:', metadata.audio.codec);
    console.log('Sample Rate:', metadata.audio.sampleRate, 'Hz');
    console.log('Channels:', metadata.audio.channels);
    console.log('Channel Layout:', metadata.audio.channelLayout);
  } catch (error) {
    console.error('Transcoding failed:', error.message);
  }
}

extractMetadata();

Batch Processing

The module supports batch processing of multiple files with a fancy terminal UI:

import { batchProcessDirectory, attachBatchUI } from '@profullstack/transcoder';

// Directory containing media files
const inputDir = './videos';

// Batch processing options
const batchOptions = {
  // Output directory
  outputDir: './processed',
  
  // Add a prefix to output filenames
  outputPrefix: 'processed-',
  
  // Transcoding options (same as for single file transcoding)
  transcodeOptions: {
    // Use the 'web' preset
    preset: 'web',
    
    // Generate thumbnails
    thumbnails: {
      count: 1,
      format: 'jpg'
    },
    
    // Always overwrite existing files
    overwrite: true
  },
  
  // Process 2 files concurrently
  concurrency: 2
};

// Scan options
const scanOptions = {
  // Only process video files
  mediaTypes: ['video'],
  
  // Recursively scan subdirectories
  recursive: true
};

console.log(`Starting batch processing of files in ${inputDir}...`);

// Start batch processing
batchProcessDirectory(inputDir, batchOptions, scanOptions)
  .then(({ results, emitter }) => {
    // Attach terminal UI to emitter
    const ui = attachBatchUI(emitter);
    
    // Listen for batch processing completion
    emitter.on('complete', () => {
      // Give user time to see the results before exiting
      setTimeout(() => {
        ui.destroy();
        
        // Print summary
        console.log(`\nBatch processing completed!`);
        console.log(`Processed ${results.total} files: ${results.successful.length} successful, ${results.failed.length} failed`);
      }, 3000);
    });
  })
  .catch(err => {
    console.error(`Error: ${err.message}`);
  });

Using Smart Presets

The module includes pre-configured settings optimized for specific platforms and use cases:

import { transcode } from '@profullstack/transcoder';

// Transcode for Instagram (square format 1080x1080)
await transcode('input.mp4', 'instagram-output.mp4', { preset: 'instagram' });

// Transcode for YouTube HD (1920x1080)
await transcode('input.mp4', 'youtube-output.mp4', { preset: 'youtube-hd' });

// Transcode for Twitter with custom overrides
await transcode('input.mp4', 'twitter-output.mp4', {
  preset: 'twitter',
  videoBitrate: '6000k' // Override the preset's videoBitrate
});

Available presets:

Video Presets:

PresetDescriptionResolutionOptimized For
instagramSquare format1080x1080Instagram feed
instagram-storiesVertical format1080x1920Instagram stories
youtube-hdHD format1920x1080YouTube
youtube-4k4K format3840x2160YouTube
twitterHD format1280x720Twitter
facebookHD format1280x720Facebook
tiktokVertical format1080x1920TikTok
vimeo-hdHD format1920x1080Vimeo
webOptimized for web1280x720Web playback
mobileOptimized for mobile640x360Mobile devices

Audio Presets:

PresetDescriptionCodecBitrateSample RateChannels
audio-highHigh quality audioAAC320k48000 Hz2 (stereo)
audio-mediumMedium quality audioAAC192k44100 Hz2 (stereo)
audio-lowLow quality audioAAC96k44100 Hz2 (stereo)
audio-voiceVoice optimizedAAC128k44100 Hz1 (mono)
mp3-highHigh quality MP3MP3320k44100 Hz2 (stereo)
mp3-mediumMedium quality MP3MP3192k44100 Hz2 (stereo)
mp3-lowLow quality MP3MP396k44100 Hz2 (stereo)

Image Presets:

PresetDescriptionFormatQualityOptimized For
jpeg-highHigh quality JPEGJPEG95%High quality images
jpeg-mediumMedium quality JPEGJPEG85%Web images
jpeg-lowLow quality JPEGJPEG70%Small file size
webp-highHigh quality WebPWebP90%Modern browsers
webp-mediumMedium quality WebPWebP80%Web images
webp-lowLow quality WebPWebP65%Small file size
pngStandard PNGPNGLosslessImages with transparency
png-optimizedOptimized PNGPNGLosslessSmaller PNG files
avif-highHigh quality AVIFAVIF80%Modern browsers
avif-mediumMedium quality AVIFAVIF60%Small file size
thumbnailThumbnail sizeJPEG80%Thumbnails (300x300)
social-mediaSocial media sizeJPEG90%Social sharing (1200x630)
squareSquare with paddingPNGLosslessSquare images with transparent padding
square-whiteSquare with white paddingJPEG90%Square images with white background
instagram-squareInstagram squareJPEG90%Instagram (1080x1080)

You can also override any preset setting by providing your own options:

// Use YouTube HD preset but with a higher bitrate
await transcode('input.mp4', 'output.mp4', {
  preset: 'youtube-hd',
  videoBitrate: '15000k'
});

Using Watermarks

You can add image or text watermarks to your videos:

import { transcode } from '@profullstack/transcoder';

// Add an image watermark
await transcode('input.mp4', 'output.mp4', {
  watermark: {
    image: 'logo.png',
    position: 'bottomRight', // Options: topLeft, topRight, bottomLeft, bottomRight, center
    opacity: 0.7,            // 0.0 to 1.0
    margin: 10               // Margin from the edge in pixels
  }
});

// Add a text watermark
await transcode('input.mp4', 'output.mp4', {
  watermark: {
    text: '© Copyright 2025',
    position: 'bottomRight',
    fontColor: 'white',
    fontSize: 24,
    fontFile: '/path/to/your/font.ttf',  // Optional path to a font file
    boxColor: 'black@0.5',   // Optional background box with opacity
    opacity: 0.8
  }
});

// Audio enhancement for videos
await transcode('input.mp4', 'output.mp4', {
  audio: {
    normalize: true,        // Normalize audio levels
    noiseReduction: 0.3,    // Reduce background noise (0.0 to 1.0)
    fadeIn: 1.5,            // Fade in duration in seconds
    fadeOut: 2.0,           // Fade out duration in seconds
    volume: 1.2             // Adjust volume (1.0 = original volume)
  }
});

Using Audio Enhancement

The module includes powerful audio enhancement features to improve the quality of audio in your videos:

import { transcode } from '@profullstack/transcoder';

// Basic audio normalization
await transcode('input.mp4', 'output.mp4', {
  preset: 'web',
  audio: {
    normalize: true  // Normalize audio levels for consistent volume
  }
});

// Noise reduction
await transcode('input.mp4', 'output.mp4', {
  preset: 'web',
  audio: {
    noiseReduction: 0.3  // Value between 0 and 1, higher values = more noise reduction
  }
});

// Add fade in/out
await transcode('input.mp4', 'output.mp4', {
  preset: 'web',
  audio: {
    fadeIn: 1.5,  // Fade in duration in seconds
    fadeOut: 2.0  // Fade out duration in seconds
  }
});

// Adjust volume
await transcode('input.mp4', 'output.mp4', {
  preset: 'web',
  audio: {
    volume: 1.5  // Increase volume by 50%
  }
});

// Combine multiple audio enhancements
await transcode('input.mp4', 'output.mp4', {
  preset: 'web',
  audio: {
    normalize: true,
    noiseReduction: 0.2,
    fadeIn: 0.5,
    fadeOut: 1.0,
    volume: 1.2
  }
});

Important Note: The audio enhancement features are primarily designed for enhancing audio tracks in video files. They work best when used with the transcode function for video files.

For standalone audio files, the support varies by format:

  • WAV and AAC files are fully supported for audio enhancement
  • MP3, FLAC, and OGG files are not fully supported for direct enhancement and will be skipped with a warning

When batch processing audio files with enhancements:

  • WAV and AAC files will be processed normally
  • MP3, FLAC, and OGG files will be skipped with a warning message
  • No error will be thrown, allowing the batch process to continue with supported files

When applying audio enhancements to video files, the audio track is processed while preserving the video quality.

For the best results with standalone audio files, consider using a two-step approach: 1. First, convert to a well-supported format like WAV 2. Then apply audio enhancements

// Example for enhancing standalone audio files
import { transcodeAudio } from '@profullstack/transcoder';

// First convert to WAV (if needed)
await transcodeAudio('input.mp3', 'temp.wav', {
  audioCodec: 'pcm_s16le'
});

// Then apply enhancements
await transcodeAudio('temp.wav', 'enhanced.wav', {
  normalize: true,
  noiseReduction: 0.2
});

You can also use the batch processing feature to enhance multiple audio files:

import { batchProcessDirectory } from '@profullstack/transcoder';

// Batch enhance audio files
const result = await batchProcessDirectory('./audio-files', {
  outputDir: './enhanced-audio',
  transcodeOptions: {
    audio: {
      normalize: true,
      noiseReduction: 0.2,
      fadeIn: 0.5,
      fadeOut: 0.5
    }
  }
}, {
  mediaTypes: ['audio']
});

// Check for skipped files
const skippedFiles = result.results.failed.filter(file => file.skipped);
if (skippedFiles.length > 0) {
  console.log('Skipped files:');
  skippedFiles.forEach(file => {
    console.log(`- ${file.input}: ${file.warning}`);
  });
}

Using the CLI Tool

The module includes a command-line interface (CLI) for easy video transcoding, thumbnail generation, and watermarking directly from your terminal:

# Basic usage
transcoder input.mp4 output.mp4

# Using a preset
transcoder input.mp4 output.mp4 --preset youtube-hd

# Generate thumbnails during transcoding
transcoder input.mp4 output.mp4 --thumbnails 3

# Generate thumbnails without transcoding
transcoder --thumbnails-only input.mp4 --count 5

# Customize video settings
transcoder input.mp4 output.mp4 --width 1280 --height 720 --bitrate 2M

# Trim a video
transcoder input.mp4 output.mp4 --trim --start 00:00:10 --end 00:00:30

# Pass custom ffmpeg arguments directly
transcoder input.mp4 output.mp4 --ffmpeg-args="-vf eq=brightness=0.1:saturation=1.5"

# Batch process all videos in a directory
transcoder --path ./videos --preset web --output-dir ./processed

# Batch process with recursive directory scanning
transcoder --path ./videos --recursive --preset mobile --output-dir ./processed

The CLI tool features a cool progress bar with real-time information:

Progress Bar

  • Colorful progress visualization
  • Percentage completion
  • Current FPS (frames per second)
  • Elapsed time
  • Estimated time remaining (ETA)
  • Fast and efficient thumbnail generation

For batch processing, the CLI tool provides a fancy terminal UI:

  • Overall progress tracking
  • Individual file progress
  • Real-time statistics (completed files, success/failure rate)
  • Estimated time remaining
  • Detailed log output

CLI Options

OptionDescription
--preset, -pUse a predefined preset (e.g., youtube-hd, twitter, instagram)
--width, -wOutput video width
--height, -hOutput video height
--bitrate, -bOutput video bitrate (e.g., 1M, 5M)
--fps, -fOutput video frame rate
--codec, -cVideo codec to use (e.g., h264, h265)
--audio-codec, -aAudio codec to use (e.g., aac, mp3)
--audio-bitrateAudio bitrate (e.g., 128k, 256k)
--thumbnails, -tNumber of thumbnails to generate during transcoding
--thumbnails-onlyGenerate thumbnails without transcoding
--countNumber of thumbnails to generate (for thumbnails-only mode)
--formatThumbnail format (jpg or png)
--timestampsSpecific timestamps for thumbnails (comma-separated, in seconds or HH:MM:SS format)
--thumbnail-outputOutput pattern for thumbnails (e.g., "thumb-%d.jpg")
--trimEnable video trimming
--startStart time for trimming (in seconds or HH:MM:SS format)
--endEnd time for trimming (in seconds or HH:MM:SS format)
--watermark-imagePath to image file to use as watermark
--watermark-textText to use as watermark
--watermark-positionPosition of the watermark (topLeft, topRight, bottomLeft, bottomRight, center)
--watermark-opacityOpacity of the watermark (0.0 to 1.0)
--watermark-marginMargin from the edge in pixels
--watermark-font-sizeFont size for text watermark in pixels
--watermark-font-colorFont color for text watermark
--watermark-fontPath to font file for text watermark
--watermark-box-colorBackground box color for text watermark
--pathPath to directory containing media files for batch processing
--recursiveRecursively process files in subdirectories (for batch processing)
--output-dirOutput directory for batch processed files
--output-prefixPrefix to add to output filenames (for batch processing)
--output-suffixSuffix to add to output filenames (for batch processing)
--output-extensionExtension for output files (for batch processing)
--media-typesMedia types to process (for batch processing)
--concurrencyNumber of files to process concurrently (for batch processing)
--fancy-uiUse fancy terminal UI for batch processing
--ffmpeg-argsPass custom arguments directly to ffmpeg (e.g., "--ffmpeg-args='-vf eq=brightness=0.1'")
--verbose, -vShow detailed progress information
--help, -?Show help

Installation

The CLI tool is automatically installed when you install the package:

# Install globally
npm install -g @profullstack/transcoder

# Now you can use the 'transcoder' command from anywhere
transcoder input.mp4 output.mp4 --preset youtube-hd

# Or use npx without installing
npx @profullstack/transcoder input.mp4 output.mp4 --preset youtube-hd

When installed globally, you can use the transcoder command from any directory:

# Basic usage
transcoder input.mp4 output.mp4

# With options
transcoder input.mp4 output.mp4 --preset youtube-hd --thumbnails 3

# Generate thumbnails only
transcoder --thumbnails-only input.mp4 --count 5

# Batch processing
transcoder --path ./videos --preset web --output-dir ./processed

API Reference

transcode(inputPath, outputPath, options)

Transcodes a video file to web-friendly MP4 format.

Parameters:

  • inputPath (string): Path to the input video file
  • outputPath (string): Path where the transcoded video will be saved
  • options (object, optional): Transcoding options or preset name
    • Can include a preset property with one of the predefined platform presets
    • Can include a thumbnails property for generating thumbnails during transcoding

Returns:

  • Promise that resolves with an object containing:
    • outputPath (string): Path to the transcoded video
    • emitter (TranscodeEmitter): Event emitter for progress tracking
    • thumbnails (Array, optional): Array of thumbnail paths if thumbnails were requested
    • metadata (Object, optional): Video metadata extracted from the input file
      • format: Format information (duration, size, bitrate, etc.)
      • video: Video stream information (codec, resolution, fps, etc.)
      • audio: Audio stream information (codec, sample rate, channels, etc.)

transcodeAudio(inputPath, outputPath, options)

Transcodes an audio file to another format with various enhancements. Can also extract audio from video files.

Parameters:

  • inputPath (string): Path to the input audio or video file
  • outputPath (string): Path where the transcoded audio will be saved
  • options (object, optional): Transcoding options or preset name
    • Can include a preset property with one of the predefined audio presets
    • Can include audio enhancement options like normalize, fadeIn, fadeOut, etc.

Returns:

  • Promise that resolves with an object containing:
    • outputPath (string): Path to the transcoded audio
    • emitter (TranscodeEmitter): Event emitter for progress tracking
    • metadata (Object, optional): Audio metadata extracted from the input file
      • format: Format information (duration, size, bitrate, etc.)
      • audio: Audio stream information (codec, sample rate, channels, etc.)

transcodeImage(inputPath, outputPath, options)

Transcodes an image file to another format with various transformations.

Parameters:

  • inputPath (string): Path to the input image file
  • outputPath (string): Path where the transcoded image will be saved
  • options (object, optional): Transcoding options or preset name
    • Can include a preset property with one of the predefined image presets
    • Can include transformation options like resize, rotate, crop, squarePad, etc.
    • squarePad (boolean): Convert rectangular image to square with padding
    • padColor (string): Color for padding (e.g., 'transparent', 'white', 'black')
    • padSize (number): Additional padding size in pixels

Returns:

  • Promise that resolves with an object containing:
    • outputPath (string): Path to the transcoded image
    • emitter (TranscodeEmitter): Event emitter for progress tracking
    • metadata (Object, optional): Image metadata extracted from the input file
      • format: Format information (size, format name, etc.)
      • image: Image information (width, height, codec, etc.)

transcodeImageBatch(items, globalOptions)

Transcodes multiple images in batch with shared global options.

Parameters:

  • items (Array): Array of objects with input, output, and options properties
    • Each item must have input and output properties
    • Each item can have an optional options property for image-specific options
  • globalOptions (object, optional): Global options applied to all items

Returns:

  • Promise that resolves with an object containing:
    • successful (Array): Array of successfully transcoded images with metadata
    • failed (Array): Array of failed operations with error messages

batchProcessDirectory(dirPath, batchOptions, scanOptions)

Processes all media files in a directory.

Parameters:

  • dirPath (string): Path to the directory containing media files
  • batchOptions (object, optional): Batch processing options
    • outputDir (string): Directory where processed files will be saved
    • outputPrefix (string): Prefix to add to output filenames
    • outputSuffix (string): Suffix to add to output filenames
    • outputExtension (string): Extension for output files
    • transcodeOptions (object): Options for transcoding (same as for single file transcoding)
    • concurrency (number): Number of files to process concurrently
  • scanOptions (object, optional): Options for scanning the directory
    • mediaTypes (array): Media types to process ('video', 'audio', 'image')
    • recursive (boolean): Whether to scan subdirectories

Returns:

  • Promise that resolves with an object containing:
    • results (object): Results of batch processing
      • total (number): Total number of files processed
      • successful (array): Array of successfully processed files with metadata
      • failed (array): Array of failed operations with error messages
    • emitter (BatchProcessEmitter): Event emitter for progress tracking

attachBatchUI(emitter, options)

Attaches a terminal UI to a batch process emitter.

Parameters:

  • emitter (BatchProcessEmitter): Batch process emitter
  • options (object, optional): Terminal UI options

Returns:

  • Terminal UI object with methods for updating the UI

generateThumbnails(inputPath, outputDir, options)

Generates thumbnails from a video file without transcoding.

Parameters:

  • inputPath (string): Path to the input video file
  • outputDir (string): Directory where thumbnails will be saved
  • options (object, optional): Thumbnail generation options
    • count (number, default: 3): Number of thumbnails to generate
    • format (string, default: 'jpg'): Image format ('jpg' or 'png')
    • filenamePattern (string, default: 'thumbnail-%03d'): Pattern for thumbnail filenames
    • timestamps (boolean, default: false): Whether to use specific timestamps instead of intervals
    • timestampList (Array, default: []): List of timestamps (only used if timestamps is true)

Returns:

  • Promise that resolves with an array of thumbnail paths

BatchProcessEmitter Events

The emitter returned by the batchProcessDirectory function emits the following events:

  • start: Emitted when the batch processing starts
    • Payload: { total: number }
  • fileStart: Emitted when processing of a file starts
    • Payload: { filePath: string, outputPath: string, mediaType: string, index: number }
  • fileProgress: Emitted when FFmpeg reports progress for a file
    • Payload: { percent: number }
  • fileComplete: Emitted when processing of a file completes successfully
    • Payload: { filePath: string, outputPath: string, mediaType: string, metadata: object, success: true }
  • fileError: Emitted when processing of a file fails
    • Payload: { filePath: string, error: string }
  • progress: Emitted when overall batch progress updates
    • Payload: { completed: number, total: number, percent: number }
  • complete: Emitted when batch processing completes
    • Payload: { total: number, completed: number, successful: array, failed: array }
  • log: Emitted for log messages
    • Payload: string

TranscodeEmitter Events

The emitter returned by the transcode function emits the following events:

  • start: Emitted when the transcoding process starts
    • Payload: { command: string, args: string[] }
  • progress: Emitted when FFmpeg reports progress
    • Payload: { frame: number, fps: number, time: number, bitrate: number, size: number, speed: number }
  • log: Emitted for each line of FFmpeg output
    • Payload: string

DEFAULT_OPTIONS

An object containing the default transcoding options.

Options

The following options can be customized:

OptionTypeDefaultDescription
presetstring-Platform preset name (e.g., 'instagram', 'youtube-hd', 'twitter')
thumbnailsobject-Thumbnail generation options (see below)
watermarkobject-Watermark options (see below)
audioobject-Audio enhancement options (see below)
videoCodecstring'libx264'Video codec to use
audioCodecstring'aac'Audio codec to use
videoBitratestring'1500k'Video bitrate
audioBitratestring'128k'Audio bitrate
widthnumber-1Output width (use -1 to maintain aspect ratio)
heightnumber-1Output height (use -1 to maintain aspect ratio)
fpsnumber-1Frames per second (use -1 to maintain original fps)
presetstring'medium'Encoding preset (ultrafast, superfast, veryfast, faster, fast, medium, slow, slower, veryslow)
profilestring'main'H.264 profile (baseline, main, high)
levelstring'4.0'H.264 level
pixelFormatstring'yuv420p'Pixel format
movflagsstring'+faststart'MP4 container flags
threadsnumber0Number of threads to use (0 = auto)
overwritebooleanfalseWhether to overwrite existing output file

Thumbnail Options:

OptionTypeDefaultDescription
countnumber3Number of thumbnails to generate
formatstring'jpg'Image format ('jpg' or 'png')
filenamePatternstring'thumbnail-%03d'Pattern for thumbnail filenames
timestampsbooleanfalseWhether to use specific timestamps instead of intervals
timestampListArray[]List of timestamps (only used if timestamps is true)

Watermark Options:

OptionTypeDefaultDescription
imagestring-Path to image file to use as watermark
textstring-Text to use as watermark
positionstring'bottomRight'Position of the watermark (topLeft, topRight, bottomLeft, bottomRight, center)
opacitynumber0.7Opacity of the watermark (0.0 to 1.0)
marginnumber10Margin from the edge in pixels
fontSizenumber24Font size for text watermark in pixels
fontColorstring'white'Font color for text watermark
fontFilestring-Path to font file for text watermark (if not specified, will try to find a system font)
boxColorstring-Background box color for text watermark (e.g., "black@0.5" for semi-transparent black)

Audio Enhancement Options:

OptionTypeDefaultDescription
normalizebooleanfalseWhether to normalize audio levels for consistent volume
noiseReductionnumber0Noise reduction amount (0.0 to 1.0, higher values = more reduction)
fadeInnumber0Fade in duration in seconds
fadeOutnumber0Fade out duration in seconds
volumenumber1.0Volume adjustment factor (1.0 = original volume)

Note: When using a platform preset, the preset option refers to the platform name (e.g., 'instagram'). The FFmpeg encoding preset (e.g., 'medium', 'slow') is still configurable but is included in each platform preset with appropriate values.

How It Works

This module uses Node.js's built-in child_process.spawn() to call FFmpeg with appropriate parameters to transcode the video. It parses the FFmpeg output to provide real-time progress updates through an event emitter. The module does not store any files itself but simply passes through to FFmpeg.

Testing

Manual Testing

The module includes a script to generate a 5-second test video for manual testing purposes:

# Generate test media
pnpm generate-test-video
pnpm generate-test-audio

# Run the basic example with the test video
pnpm example

# Run the Smart Presets example
pnpm example:presets

# Run the Thumbnail Generation example
pnpm example:thumbnails

# Run the Audio Transcoding example
pnpm example:audio

# Run the Image Transcoding example
pnpm example:image

# Run the Square Padding example
pnpm example:square

# Run the Batch Processing example
pnpm example:batch

# Run the CLI Examples script
pnpm example:cli

This will: 1. Create a tiny 2-second test video (320x240) in .mov format in the test-videos/input directory 2. Transcode it to MP4 format in the test-videos/output directory 3. Run the example file that demonstrates basic usage and custom options

Automated Tests

The module includes Mocha tests for automated testing:

# Run the automated tests
pnpm test

The module includes the following test files:

  • test/transcode.test.js - Tests for the core transcoding functionality
  • test/presets.test.js - Tests for the Smart Presets feature
  • test/thumbnails.test.js - Tests for the Thumbnail Generation feature
  • test/watermarking.test.js - Tests for the Watermarking feature
  • test/trimming.test.js - Tests for the Video Trimming feature
  • test/responsive.test.js - Tests for the Responsive Video Profiles feature
  • test/audio.test.js - Tests for the Audio Transcoding feature
  • test/image.test.js - Tests for the Image Transcoding feature
  • test/batch.test.js - Tests for the Batch Processing feature
  • test/terminal-ui.test.js - Tests for the Terminal UI feature

CLI Examples

The module includes a script with common CLI use cases that you can run to see the transcoder in action:

# Run the CLI examples script
pnpm example:cli

This script demonstrates various use cases for the CLI tool:

  1. Basic transcoding
  2. Using a preset (YouTube HD)
  3. Custom resolution and bitrate
  4. Generate thumbnails during transcoding
  5. Generate thumbnails only (no transcoding)
  6. Add a watermark
  7. Trim a video
  8. Audio transcoding - MP3 to AAC
  9. Audio transcoding - Extract audio from video
  10. Image transcoding - JPEG to WebP
  11. Image transcoding - Square padding
  12. Batch process all videos in a directory
  13. Batch process with recursive directory scanning
  14. Batch process with output filename customization
  15. Batch process with concurrent processing
  16. Batch process specific media types
  17. Batch process audio files
  18. Batch process image files

You can also run the script directly:

./examples/example.sh

These tests verify the core functionality of the module, including error handling, option processing, preset handling, thumbnail generation, watermarking, trimming, responsive profiles, audio transcoding, and image transcoding.

License

MIT

1.9.14

8 months ago

1.9.13

8 months ago

1.9.12

8 months ago

1.9.9

8 months ago

1.9.8

8 months ago

1.9.7

8 months ago

1.9.6

8 months ago

1.9.5

8 months ago

1.8.3

8 months ago

1.8.1

8 months ago

1.8.0

8 months ago

1.7.0

8 months ago

1.6.3

8 months ago

1.6.2

8 months ago

1.6.1

8 months ago

1.6.0

8 months ago

1.5.0

8 months ago

1.4.0

8 months ago

1.3.0

8 months ago

1.2.0

8 months ago

1.1.2

8 months ago

1.1.1

8 months ago

1.1.0

8 months ago

1.0.0

8 months ago