Nginx: Transcoding Video

From OnnoWiki
Jump to navigation Jump to search

Sumber: http://www.helping-squad.com/transcoding-your-video-with-nginx/



Today we want to take a look at the transcoding options nginx gives us. Under Linux we can directly use the exec directive to call ffmpeg as soon as a stream connects for example. On Windows we would have to do this by ourselves each time we want to start a transcoding, but more on that later. Now lets take at the example configuration by arut:

  1. Transcoding (ffmpeg needed)
       application big {
           live on;
           # On every pusblished stream run this command (ffmpeg)
           # with substitutions: $app/${app}, $name/${name} for application & stream name.
           #
           # This ffmpeg call receives stream from this application &
           # reduces the resolution down to 32x32. The stream is the published to
           # 'small' application (see below) under the same name.
           #
           # ffmpeg can do anything with the stream like video/audio
           # transcoding, resizing, altering container/codec params etc
           #
           # Multiple exec lines can be specified.
           exec ffmpeg -re -i rtmp://localhost:1935/$app/$name -vcodec flv -acodec copy -s 32x32
                       -f flv rtmp://localhost:1935/small/${name};
       }
       application small {
           live on;
           # Video with reduced resolution comes here from ffmpeg
       }

As you can see we have two applications “big” and “small” in this example. The big application receives a stream and automatically starts ffmpeg using this stream as the input source /&app/&name = /big/stream. FFmpeg in the example only resizes the video to a resolution of 32×32 pixel and copies the audio over. This result gets send to application “small” with the same name as the first stream. Now in this case the application small does nothing, but you could of course set it to push your stream to a different location or use the result to offer different resolutions. Let us now take a look at some example ffmpeg configurations, I created myself:

ffmpeg -i rtmp://localhost/big/1080 -vcodec libx264 -preset faster -x264opts nal-hrd=cbr:force-cfr=1:keyint=60 -b:v 3000k -maxrate 3000k -bufsize 3000k -s 1280x720 -sws_flags spline -r 30 -acodec copy -f flv rtmp://localhost/small/720

ffmpeg -i rtmp://localhost/big/1080 -vcodec libx264 -preset veryfast -b:v 2000k -maxrate 2000k -bufsize 2000k -s 1280x720 -sws_flags lanczos -r 60 -acodec copy -f flv rtmp://localhost/small/720

ffmpeg -i rtmp://localhost/big/1080 -vcodec flv -acodec copy -s 64x64 -f flv rtmp://localhost/small/720

These are three different examples of ffmpeg commandlines (can also be used under windows), for them to work you have to be on an up to date ffmpeg!! The first line is an example for twitch.tv. It sets the keyintervall according to the framerate and sets cbr padding. Preset used is faster and a bitrate of 3000 (if set in OBS or XSplit) with a resize to 720p. The second example uses a simple setup with lanczos resizing instead of spline, also to 720p and to a rough bitrate of 2K. While the third example uses aruts idea but resizes to a small 64×64 video which could be used as a live thumbnail or similar.

As mentioned earlier under Windows you cannot add the commandline directly to the config. For Windows just setup a batch file which you can start with a desktop shortcut. You can then use the shortcut when necessary to start the transcoding. Under both Windows and Linux always make sure you are using the latest ffmpeg (you can also use avconv) as earlier versions had no good rtmp support. Last but not least, remember transcoding uses a similar amount of CPU power than a similar streaming. So have enough power for your transcodes!

One last thing to mention, in arut’s example, he uses -re which is explained in the ffmpeg documentation like this:

Read input at native frame rate. Mainly used to simulate a grab device. or live input stream (e.g. when reading from a file). Should not be used with actual grab devices or live input streams (where it can cause packet loss). By default ffmpeg attempts to read the input(s) as fast as possible. This option will slow down the reading of the input(s) to the native frame rate of the input(s). It is useful for real-time output (e.g. live streaming).

Since this does more or less say, do not use it for live streaming, I did not use it in my examples. If you run into problems though, you might wanna toggle turning it on.




Referensi