This guide explains how to install and use the latest major version of PHP-FFMpeg (v1.x) on an Ubuntu server, with WebM (VP9) and AV1 encoding enabled.
It is written for backend services, queues, and SaaS media processing, not desktop usage.
Important context: PHP-FFMpeg is a PHP wrapper around the system
ffmpegandffprobebinaries. Codec support depends entirely on how FFmpeg is built on your server.
Official project repository:
PHP-FFMpeg on GitHub
What This Article Covers
- Ubuntu server installation
- FFmpeg version and encoder verification
- Enabling WebM (VP9) and AV1 encoding
- PHP-FFMpeg installation (latest major version)
- Practical PHP examples
- Common production gotchas
- Performance optimization tips
1) Install System Dependencies on Ubuntu
Update your system and install PHP and FFmpeg:
sudo apt update
sudo apt install -y \
php-cli php-mbstring php-xml php-zip unzip git \
ffmpeg
Verify FFmpeg and FFprobe:
ffmpeg -version
ffprobe -version
Both binaries must be available for PHP-FFMpeg to function correctly.
2) Verify Codec Support (Critical Step)
Before writing any PHP code, confirm that your FFmpeg build supports the required encoders.
ffmpeg -hide_banner -encoders | egrep "libvpx-vp9|libopus|libaom-av1|libsvtav1|librav1e"
You should see:
libvpx-vp9→ WebM VP9 videolibopus→ WebM audiolibaom-av1and/orlibsvtav1→ AV1 video
If AV1 encoders are missing, FFmpeg must be compiled manually.
3) Compile FFmpeg for AV1 Support (Recommended for Services)
Ubuntu’s packaged FFmpeg may not include AV1 encoders depending on version and repository policy.
Use the official FFmpeg build reference for Ubuntu:
FFmpeg Compilation Guide for Ubuntu
When compiling, ensure support for:
- libvpx (VP9)
- libopus (Opus)
- libaom (AV1)
- SVT-AV1 (recommended for faster encoding)
- dav1d (optional, AV1 decoding)
After compiling, verify again:
ffmpeg -hide_banner -encoders | egrep "libvpx-vp9|libopus|libaom-av1|libsvtav1"
4) Install PHP-FFMpeg (Latest Major Version)
PHP-FFMpeg v1.x supports PHP 8.0+.
Install via Composer:
composer require php-ffmpeg/php-ffmpeg:^1.3
Package details and versions:
PHP-FFMpeg on Packagist
5) Create the FFmpeg Instance (Production Setup)
In production, always specify binary paths and increase timeouts.
<?php
require __DIR__ . '/vendor/autoload.php';
use FFMpeg\FFMpeg;
$ffmpeg = FFMpeg::create([
'ffmpeg.binaries' => '/usr/bin/ffmpeg',
'ffprobe.binaries' => '/usr/bin/ffprobe',
// AV1 encoding can be slow
'timeout' => 3600,
// Control CPU usage
'ffmpeg.threads' => 8,
// Dedicated temp directory
'temporary_directory' => '/var/ffmpeg-tmp',
]);
6) Encode WebM (VP9 + Opus)
WebM supports:
- Video: VP8, VP9, AV1
- Audio: Opus or Vorbis
VP9 + Opus is widely supported and efficient for the web.
VP9 WebM Example
<?php
use FFMpeg\Format\Video\WebM;
$video = $ffmpeg->open('/path/to/input.mp4');
$format = new WebM();
$format->setAdditionalParameters([
'-c:v', 'libvpx-vp9',
'-crf', '32',
'-b:v', '0',
'-row-mt', '1',
'-c:a', 'libopus',
'-b:a', '96k',
]);
$video->save($format, '/path/to/output_vp9.webm');
7) Encode AV1 in WebM
AV1 offers significantly better compression but is CPU-intensive.
Official FFmpeg AV1 documentation:
FFmpeg AV1 Encoding Guide
Option A: AV1 via libaom-av1 (Highest Quality)
<?php
use FFMpeg\Format\Video\WebM;
$video = $ffmpeg->open('/path/to/input.mp4');
$format = new WebM();
$format->setAdditionalParameters([
'-c:v', 'libaom-av1',
'-crf', '34',
'-b:v', '0',
'-cpu-used', '6',
'-threads', '8',
'-c:a', 'libopus',
'-b:a', '96k',
]);
$video->save($format, '/path/to/output_av1_aom.webm');
Option B: AV1 via SVT-AV1 (Much Faster)
<?php
use FFMpeg\Format\Video\WebM;
$video = $ffmpeg->open('/path/to/input.mp4');
$format = new WebM();
$format->setAdditionalParameters([
'-c:v', 'libsvtav1',
'-crf', '35',
'-preset', '8',
'-c:a', 'libopus',
'-b:a', '96k',
]);
$video->save($format, '/path/to/output_av1_svt.webm');
8) Common Production Gotchas
FFmpeg Installed but Encoder Missing
If FFmpeg reports Unknown encoder, your build lacks codec support. Recompile FFmpeg with the required libraries.
WebM Muxing Errors
WebM only supports VP8, VP9, or AV1 video with Opus or Vorbis audio. H.264 + AAC will fail.
AV1 Timeouts
AV1 encoding is slow. Always increase PHP-FFMpeg timeouts for services.
PATH Differences in PHP-FPM
FFmpeg may work in CLI but fail under PHP-FPM or systemd. Always specify absolute binary paths.
Disk Space Pressure
Transcoding creates large temporary files. Plan disk space accordingly.
9) Performance Optimization Tips
- Prefer SVT-AV1 for high-throughput services
- Use CRF-based encoding instead of fixed bitrates
- Limit FFmpeg threads to protect server resources
- Run encodes in background workers or queues
- Monitor CPU, memory, and disk I/O
10) Optional: Progress Reporting
$format->on('progress', function ($video, $format, $percentage) {
error_log("Transcode progress: {$percentage}%");
});