OpenSSL (on Stack Overflow)
Although I've tried to show equivalent operations for all procedures, not all operations are possible in both applications.
In many cases, the commands I'm showing may be combined in a single command line operation, and in actual use would be. For example, there's nothing preventing you from setting an output file's bitrate in the same operation as a file conversion. For this cheat sheet, I often show these operations as separate commands for the sake of clarity.
Please let me know of useful additions or corrections. Pull requests are welcome.
This page contains a few more commands than are covered in this section. Not only are there plans to cover these topics (we have drafts already), we also hope this page will be a resource for multiple levels of expertise.
packager input=myvideo.mp4 --dump_stream_info
ffmpeg -i myvideo.mp4
Technically, FFmpeg always requires an output file format. Calling FFmpeg this way will give you an error message explaining that; however, it lists information not available using Shaka Packager.
Shaka Packager requires demuxing when converting files. This is also required for using media frameworks.
MP4
packager input=myvideo.mp4,stream=video,output=myvideo_video.mp4
packager input=myvideo.mp4,stream=audio,output=myvideo_audio.m4a
Or:
packager \
input=myvideo.mp4,stream=video,output=myvideo_video.mp4 \
input=myvideo.mp4,stream=audio,output=myvideo_audio.m4a
WebM
packager \
input=myvideo.webm,stream=video,output=myvideo_video.webm \
input=myvideo.webm,stream=audio,output=myvideo_audio.webm
MP4
ffmpeg -i myvideo.mp4 -vcodec copy -an myvideo_video.mp4
ffmpeg -i myvideo.mp4 -acodec copy -vn myvideo_audio.m4a
WebM
ffmpeg -i myvideo.webm -vcodec copy -an myvideo_video.webm
ffmpeg -i myvideo.webm -acodec copy -vn myvideo_audio.webm
For FFmpeg, I can do this while I'm converting to mp4 or WebM.
ffmpeg -i myvideo.mov -b:v 350K myvideo.mp4
ffmpeg -i myvideo.mov -vf setsar=1:1 -b:v 350K myvideo.webm
ffmpeg -i myvideo.webm -s 1920x1080 myvideo_1920x1080.webm
Shaka Packager cannot process mov files and hence cannot be used to convert files from that format.
mov to MP4
ffmpeg -i myvideo.mov myvideo.mp4
mov to WebM
ffmpeg -i myvideo.mov myvideo.webm
To ensure that audio and video synchronize during playback, insert keyframes.
ffmpeg -i myvideo.mp4 -keyint_min 150 -g 150 -f webm -vf setsar=1:1 out.webm
The tables below list common containers and codecs for both audio and video, as well as the FFmpeg library needed for conversion. A conversion library must be specified when converting files using FFmpeg.
Codec | Container | Library |
---|---|---|
av1 | mkv | libaom-av1 |
WebM | libaom-av1 | |
h264 | MP4 | libx264 |
vp9 | WebM | libvpx-vp9 |
Codec | Container | Library |
---|---|---|
aac | MP4 | aac |
opus | WebM | libopus |
vorbis | WebM | libvorbis |
MP4/H.264
ffmpeg -i myvideo.mp4 -c:v libx264 -c:a copy myvideo.mp4
Audio for an MP4
ffmpeg -i myvideo.mp4 -c:v copy -c:a aac myvideo.mp4
WebM/VP9
ffmpeg -i myvideo.webm -v:c libvpx-vp9 -v:a copy myvideo.webm
Audio for a WebM
ffmpeg -i myvideo.webm -v:c copy -v:a libvorbis myvideo.webm
ffmpeg -i myvideo.webm -v:c copy -v:a libopus myvideo.webm
Dynamic Adaptive Streaming over HTTP is a web-standards-based method of presenting video-on-demand for the web.
packager \
input=myvideo.mp4,stream=audio,output=myvideo_audio.mp4 \
input=myvideo.mp4,stream=video,output=myvideo_video.mp4 \
--mpd_output myvideo_vod.mpd
HTTP Live Streaming (HLS) is Apple's standard for live streaming and video on demand for the web.
ffmpeg -i myvideo.mp4 -c:a copy -b:v 8M -c:v copy -f hls -hls_time 10 \
-hls_list_size 0 myvideo.m3u8
You can use the same method to create a key for both DASH and HLS. Do this using openssl. The following will create a key made of 16 hex values.
openssl rand -out media.key 16
This command creates a file with white space and new line characters, which are not allowed by Shaka Packager. You'll need to open the key file and manually remove all whitespace including the final carriage return.
For the -key
flag use the key created earlier and stored in the media.key file. However, when entering it on the command line, be sure you've removed its whitespace. For the -key_id
flag repeat the key value.
packager \
input=myvideo.mp4,stream=audio,output=glocka.m4a \
input=myvideo.mp4,stream=video,output=glockv.mp4 \
--enable_fixed_key_encryption \
-key INSERT_KEY_HERE -key_id INSERT_KEY_ID_HERE \
To encrypt for HLS you need a key information file in addition to a key file. A key information file is a text file with the format below. It should have the extension .keyinfo
. For example: encrypt.keyinfo
.
key URI
key file path
private key
The key URI is where the media.key
(created above will be located on your server. The key file path is it's location relative to the key information file. Finally, the private key is the contents of the media.key
file itself. For example:
https://example.com/media.key
/path/to/media.key
8b4c39c498949536
packager \
'input=input.mp4,stream=video,segment_template=output$Number$.ts,playlist_name=video_playlist.m3u8' \
'input=input.mp4,stream=audio,segment_template=output_audio$Number$.ts,playlist_name=audio_playlist.m3u8,hls_group_id=audio,hls_name=ENGLISH' \
--hls_master_playlist_output="master_playlist.m3u8" \
--hls_base_url="http://localhost:1000/"
This command will accept a key with either 16 or 32 characters.
ffmpeg -i myvideo.mov -c:v libx264 -c:a aac -hls_key_info_file key_info myvideo.m3u8
packager \
input=glocken.mp4,stream=video,output=enc_video.mp4 \
input=glocken.mp4,stream=audio,output=enc_audio.m4a \
--enable_widevine_encryption \
--key_server_url "https://license.uat.widevine.com/cenc/getcontentkey/widevine_test" \
--content_id "Hex_converted_unique_ID" --signer "widevine_test" \
--aes_signing_key "1ae8ccd0e7985cc0b6203a55855a1034afc252980e970ca90e5202689f947ab9" \
--aes_signing_iv "d58ce954203b7c9a9a9d467f59839249"
This section shows in order commands needed to get from a raw mov file to encrypted assets packaged for DASH or HLS. For the sake of having a goal to illustrate, I'm converting my source file to a bitrate of 8Mbs at a resolution of 1080p (1920 x 1080). Adjust these values as your needs dictate.
Not all steps are possible with Shaka Packager, so I'll use ffmpeg when I need to.
Convert the file type and codec.
For this command you can use either liborbis
or libopus
for the audio codec.
ffmpeg -i glocken.mov -c:v libvpx-vp9 -c:a libvorbis -b:v 8M -vf setsar=1:1 -f webm glocken.webm
Create a Clear Key encryption key.
You'll need to open the key file and manually remove all whitespace including the final carriage return.
openssl rand -out media.key 16
Demux (separate) the audio and video, encrypt the new files, and output a media presentation description (MPD) file.
The -key
and -key_id
flags are copied from the media.key
file.
packager \
input=myvideo.webm,stream=video,output=myvideo_video.webm \
input=myvideo.webm,stream=audio,output=myvideo_audio.webm \
--enable_fixed_key_encryption --enable_fixed_key_decryption \
-key INSERT_KEY_HERE -key_id INSERT_KEY_ID_HERE \
--mpd_output myvideo_vod.mpd
Remux (recombine) the audio and video streams. If you're using a video framework, you may not need to do this.
ffmpeg -i mymovie.mp4 -i myaudio.m4a -c copy finalmovie.mp4
Not all steps are possible with Shaka Packager, so I'll use ffmpeg when I need to.
Convert the file type, video codec and bitrate.
The default pixel format, yuv420p is used because one isn't supplied in the command line. The app will give you an error message that it is deprecated. I've chosen not to override the default because, though deprecated yuv420p is the most widely supported.
ffmpeg -i mymovie.mov -c:v libx264 -c:a aac -b:v 8M -strict -2 mymovie.mp4
Create a Clear Key encryption key.
You'll need to open the key file and manually remove all whitespace including the final carriage return.
openssl rand -out media.key 16
Demux (separate) the audio and video, encrypt the new files, and output a media presentation description (MPD) file.
The -key
and -key_id
flags are copied from the media.key
file.
packager \
input=mymovie.mp4,stream=audio,output=myaudio.m4a \
input=mymovie.mp4,stream=video,output=myvideo.mp4 \
--enable_fixed_key_encryption --enable_fixed_key_decryption \
-key INSERT_KEY_HERE -key_id INSERT_KEY_ID_HERE \
--mpd_output myvideo_vod.mpd
Remux (recombine) the audio and video streams. If you're using a video framework, you may not need to do this.
ffmpeg -i mymovie.mp4 -i myaudio.m4a -c copy finalmovie.mp4
The two previous examples used Clear Key encryption. For widevine the final two steps are replaced with this.
Everything in this command except the name of your files and the --content-id
flag should be copied exactly from the example. The --content-id
is 16 or 32 random hex digits. Use the keys provided here instead of your own. (This is how Widevine works.)
Demux (separate) the audio and video, encrypt the new files, and output a media presentation description (MPD) file.
packager \
input=mymovie.mp4,stream=audio,output=myaudio.m4a \
input=mymovie.mp4,stream=video,output=myvideo.mp4 \
--enable_widevine_encryption \
--key_server_url "https://license.uat.widevine.com/cenc/getcontentkey/widevine_test" \
--content_id "fd385d9f9a14bb09" --signer "widevine_test" \
--aes_signing_key "1ae8ccd0e7985cc0b6203a55855a1034afc252980e970ca90e5202689f947ab9" \
--aes_signing_iv "d58ce954203b7c9a9a9d467f59839249"
Remux (recombine) the audio and video streams. If you're using a video framework, you may not need to do this.
ffmpeg -i mymovie.mp4 -i myaudio.m4a -c copy finalmovie.mp4
HLS only supports MP4, so first you'll need to convert to the MP4 container and supported codecs. Not all steps are possible with Shaka Packager, so I'll use FFmpeg when I need to.
Convert the file type, video codec, and bitrate.
The default pixel format, yuv420p, is used because one isn't supplied in the command line. The app will give you an error message that it is deprecated. I've chosen not to override the default because, though deprecated yuv420p is the most widely supported.
ffmpeg -i mymovie.mov -c:v libx264 -c:a aac -b:v 8M -strict -2 mymovie.mp4
Create a Clear Key encryption key.
You'll need to open the key file and manually remove all whitespace including the final carriage return.
openssl rand -out media.key 16
Create a key information file
packager \
'input=input.mp4,stream=video,segment_template=output$Number$.ts, \
playlist_name=video_playlist.m3u8' \
'input=input.mp4,stream=audio,segment_template=output_audio$Number$.ts, \
playlist_name=audio_playlist.m3u8,hls_group_id=audio,hls_name=ENGLISH' \
--hls_master_playlist_output="master_playlist.m3u8" \
--hls_base_url="http://localhost:1000/" \
--enable_fixed_key_encryption --enable_fixed_key_decryption \
-key INSERT_KEY_HERE -key_id INSERT_KEY_ID_HERE \