Tuesday, October 5, 2010

Automatic Video Conversion in Ubuntu

A friend of mine recently created an automated video conversion system using OS X’s Automator. It’s a simple system. He drops a video file in a folder, Compressor (via the Automator script) grabs the file which then converts it and drops the output somewhere predefined. For good measure, he set it up so that the folder being watched by the Automator script is also being synced by Dropbox. That way, he can add video files to be converted regardless of where he is or what computer he is on.

Being the true linux user that I am, upon hearing about this system, I immediately set out to replicate the functionality using Ubuntu. It turned out to be relatively simple. From a functional standpoint, it is identical. Here I am going to outline the steps required to set up a similar system. If everything is followed exactly, you’ll end with two folders for converting video files from just about any format into webm or ogv video files (depending on which folder you drop the source in).

This was all done on the Ubuntu 10.10 beta, but I don’t expect it to be much different on just about any version of Ubuntu or Debian.

The video conversion uses ffmpeg so here’s a quick note on ffmpeg: Ubuntu 10.10 has ffmpeg 0.6 in the repositories. Older version should be fine except that they may not have the same video codec support. The script below to convert video files to the webm format won’t work with anything less than 0.6, but the ogg script will probably work fine for any version of ffmpeg.

We will need something to watch the folder and respond when changes occur. For this I use Watcher. Watcher is a simple python daemon I wrote that watches folders for changes and responds accordingly. It is configured via a simple yaml file.

Here are the commands to get all files and folders in place:

wget http://www.grehz.com/watcher.py
mkdir ~/.watcher # used by watcher for config files
touch ~/.watcher/jobs.yml # main (only) config file for watcher
mkdir ~/Videos/to_ogv # folder for video files that will be converted to ogv
mkdir ~/Videos/to_webm # folder for video files that will be converted to webm
mkdir ~/Videos/processed # folder to store the original source video file
mkdir ~/Videos/converted # folder to store the output video files in webm or ogv format
mkdir ~/bin # this is where I keep all my home brewed scripts
touch ~/bin/to_ogv # the script to convert video files to ogv
touch ~/bin/to_webm # the script to convert video files to webm
Ok, now that all the files and folders are set up, let’s get to configuration.

First off, we’ll create the scripts to handle the actual conversion. Open up ~/bin/to_ogv in your favorite editor. Like this for gedit:

gedit ~/bin/to_ogv

Paste this as the contents of the file and save it (change /home/gregg to your home directory):

ffmpeg -i $1 -acodec libvorbis -ab 128000 -vcodec libtheora -b 761000 /home/gregg/Videos/converted/`date +%F--%k:%M:%S`.ogv
mv $1 /home/gregg/Videos/processed/

Do the same for ~/bin/to_webm, but paste this instead (change /home/gregg to your home directory):

ffmpeg -i $1 -acodec libvorbis -ab 128000 -vcodec libvpx -b 761000 /home/gregg/Videos/converted/`date +%F--%k:%M:%S`.webm
mv $1 /home/gregg/Videos/processed/

You can change the quality of the audio and video by adjusting the -ab and -b options in the ffmpeg lines. -ab is the audio bitrate and -b is the video bitrate. A higher value means higher quality and larger filesize.

Now let’s set up watcher.

gedit ~/.watcher/jobs.yml

Paste this (change /home/gregg to your home directory):

label: Convert to ogv
watch: /home/gregg/Videos/to_ogv
events: ['create', 'move_to']
recursive: false
command: /home/gregg/bin/to_ogv $filename

label: Convert to webm
watch: /home/gregg/Videos/to_webm
events: ['create', 'move_to']
recursive: false
command: /home/gregg/bin/to_webm $filename

Make sure all indentation is exactly two spaces.

Alright, all the configuration should be ready to go. Let’s start the daemon

./water.py start

If there were no errors, everything should be good. You can view the output with this:

tail -f /tmp/watcher_out

At this point, any video files dropped in ~/Videos/to_ogv or ~/Videos/to_webm will be automatically converted to the respective video type. All your source files will be droped in ~/Videos/processed (careful, it will overwrite filenames) and your converted video files will be in ~/Videos/converted.

If you're interested in the watcher script (it is extremely flexible), you can get the source and skim some documentation here: http://github.com/greggoryhz/Watcher

It is also possible to replace watcher with incron. I consider it slightly more difficult to configure, but I originally had setup this system using incron.


  1. I will be trying this out this evening as I had an idea to try and set something like this up myself :-) Thanks in advance!

  2. I also think I might have spotted a small error, to start the daemon aren't you going to need to use "./watcher.py start" not "./water.py statrt"?