gstreamer-cheat-sheet/rtmp.md

184 lines
5.9 KiB
Markdown
Raw Normal View History

2018-02-20 12:23:23 +00:00
# RTMP (GStreamer command-line cheat sheet)
GStreamer can receive an RTMP stream from an RTMP server. It can also send an RTMP stream to an RTMP server.
If you need your own RTMP server, [the Nginx RTMP extension](https://github.com/arut/nginx-rtmp-module) works quite well though is no longer supported.
### Play an RTMP stream
To play from RTMP server, playbin can be used (as with files and HLS streams):
2018-02-20 12:23:23 +00:00
```
gst-launch-1.0 playbin uri=$RTMP_SRC
2018-02-20 12:23:23 +00:00
```
A test RTMP stream is available at `rtmp://184.72.239.149/vod/BigBuckBunny_115k.mov` which serves as a useful example:
2018-02-20 12:23:23 +00:00
```
gst-launch-1.0 playbin uri='rtmp://184.72.239.149/vod/BigBuckBunny_115k.mov'
2018-02-20 12:23:23 +00:00
```
Instead of using `playbin`, it's possible to get video only with `uridecodebin` then shown with `autovideosink`:
2018-02-20 12:23:23 +00:00
```
gst-launch-1.0 uridecodebin uri=$RTMP_SRC ! autovideosink
```
Or as a step further we can split out into the source and decode too. This does video:
```
gst-launch-1.0 rtmpsrc location=$RTMP_SRC ! decodebin ! autovideosink
```
and this does the audio:
```
gst-launch-1.0 rtmpsrc name=rtmpsrc location=$RTMP_SRC ! decodebin ! \
queue ! audioconvert ! autoaudiosink
```
We can vget flvdemux to pull out the audio:
```
gst-launch-1.0 rtmpsrc location=$RTMP_SRC ! \
flvdemux name=t t.audio ! decodebin ! autoaudiosink
```
2018-02-23 08:09:52 +00:00
Incidentally, all of these work with a direct *flv* file:
```
gst-launch-1.0 filesrc location="/Users/clarkm22/workspace/silver/assets/test.flv" ! \
flvdemux name=t t.audio ! decodebin ! autoaudiosink
```
If you want to use `flvdemux` to do the video, you need to capture the audio too or else it will fail. This example puts it in `fakesink` which is basically discarding it:
```
gst-launch-1.0 rtmpsrc location="$RTMP_SRC" ! \
flvdemux name=demux \
demux.audio ! queue ! decodebin ! fakesink \
demux.video ! queue ! decodebin ! autovideosink
```
You could then use this to capture the RTMP as an MP4, e.g.
2018-02-20 12:23:23 +00:00
```
gst-launch-1.0 -e rtmpsrc location="$RTMP_SRC" ! \
flvdemux name=demux \
demux.audio ! queue ! decodebin ! audioconvert ! faac bitrate=32000 ! mux. \
demux.video ! queue ! decodebin ! videoconvert ! video/x-raw,format=I420 ! x264enc speed-preset=superfast tune=zerolatency psy-tune=grain sync-lookahead=5 bitrate=480 key-int-max=50 ref=2 ! mux. \
mp4mux name=mux ! filesink location="out.mp4"
2018-02-20 12:23:23 +00:00
```
2018-02-23 08:09:52 +00:00
According to [this conversation](http://gstreamer-devel.966125.n4.nabble.com/flvdemux-working-sometimes-td4677796.html), the following also works, although personally I find it intermittent:
```
export QUEUE="queue max-size-time=0 max-size-bytes=0 max-size-buffers=0"
gst-launch-1.0 \
rtmpsrc location="$RTMP_SRC live=1" ! \
$QUEUE ! \
flvdemux name=demux ! \
$QUEUE ! \
aacparse ! \
avdec_aac ! \
autoaudiosink sync=0 demux.video ! \
$QUEUE ! \
h264parse ! \
avdec_h264 ! \
$QUEUE ! \
videoconvert ! \
autovideosink sync=0
```
### Adding an RTMP as picture-in-Picture
This overlays an RTMP source as a picture-in-picture on top of a local filesource (set as `$SRC`)
```
export QUEUE="queue max-size-time=0 max-size-bytes=0 max-size-buffers=0"
2018-02-23 08:09:52 +00:00
gst-launch-1.0 \
filesrc location="$SRC" ! \
decodebin ! videoconvert ! \
videoscale ! video/x-raw,width=640,height=360 ! \
compositor name=mix sink_0::alpha=1 sink_1::alpha=1 sink_1::xpos=50 sink_1::ypos=50 ! \
videoconvert ! autovideosink \
rtmpsrc location="$RTMP_SRC" ! \
flvdemux name=demux \
demux.audio ! $QUEUE ! decodebin ! autoaudiosink \
demux.video ! $QUEUE ! decodebin ! \
videoconvert ! \
videoscale ! video/x-raw,width=320,height=180! \
mix.
```
## Sending to an RTMP server
### Sending a test stream to an RTMP server
This will send a test video source:
```
gst-launch-1.0 videotestsrc is-live=true ! \
queue ! x264enc ! flvmux name=muxer ! rtmpsink location="$RTMP_DEST live=1"
```
This sends both video and audio as a test source:
```
gst-launch-1.0 videotestsrc is-live=true ! \
videoconvert ! x264enc bitrate=1000 tune=zerolatency ! video/x-h264 ! h264parse ! \
video/x-h264 ! queue ! flvmux name=mux ! \
rtmpsink location=$RTMP_DEST audiotestsrc is-live=true ! \
audioconvert ! audioresample ! audio/x-raw,rate=48000 ! \
voaacenc bitrate=96000 ! audio/mpeg ! aacparse ! audio/mpeg, mpegversion=4 ! mux.
```
### Send a file over RTMP
2018-03-20 08:18:38 +00:00
Audio & video:
2018-02-23 08:09:52 +00:00
```
gst-launch-1.0 filesrc location=$SRC ! \
qtdemux name=demux \
demux.video_0 ! queue ! \
decodebin ! videoconvert ! x264enc bitrate=1000 tune=zerolatency ! video/x-h264 ! h264parse ! \
video/x-h264 ! queue ! flvmux name=mux ! \
rtmpsink location=$RTMP_DEST \
demux.audio_0 ! queue ! decodebin ! audioconvert ! audioresample ! \
audio/x-raw,rate=48000 ! \
voaacenc bitrate=96000 ! audio/mpeg ! aacparse ! audio/mpeg, mpegversion=4 ! mux.
```
2018-03-20 08:18:38 +00:00
Just video:
```
gst-launch-1.0 filesrc location=$SRC ! \
qtdemux name=demux \
demux.video_0 ! queue ! \
decodebin ! videoconvert ! x264enc bitrate=1000 tune=zerolatency ! video/x-h264 ! h264parse ! \
video/x-h264 ! queue ! flvmux name=mux ! \
rtmpsink location=$RTMP_DEST
```
---
Can we work out why a bad RTMP brings down the other mix?
```
export QUEUE="queue max-size-time=0 max-size-bytes=0 max-size-buffers=0"
gst-launch-1.0 \
filesrc location="$SRC2" ! \
decodebin ! videoconvert ! \
videoscale ! video/x-raw,width=640,height=360 ! \
compositor name=mix sink_0::alpha=1 sink_1::alpha=1 sink_1::xpos=50 sink_1::ypos=50 ! \
videoconvert ! autovideosink \
rtmpsrc location="$RTMP_DEST" ! \
flvdemux name=demux \
demux.audio ! $QUEUE ! decodebin ! fakesink \
demux.video ! $QUEUE ! decodebin ! \
videoconvert ! \
videoscale ! video/x-raw,width=320,height=180! \
mix.
```