使用playbin保存GStreamer RTSP流到文件报协商错误如何解决
问题根因
你用于保存MP4的管道存在配置错误,抛出的not-negotiated (-4)错误是GStreamer典型的能力集(caps)协商失败问题,核心错误点有两个:
- 你在
videoconvert后直接强制声明输出为video/x-h264格式,但videoconvert仅负责原始视频帧的色彩空间转换,不具备编码能力,输出永远是未压缩的原始视频帧,不可能直接产出H.264编码数据。 - 你发布的RTSP流本身是未压缩RAW视频(通过
rtpvrawpay打包),playbin拉流解码后输出的也是原始视频帧;MP4容器需要接收编码后的音视频数据才能封装,你跳过了H.264编码环节直接要求输出H.264格式,整个链路格式完全无法匹配。
你之前能成功捕获单张JPEG图像,是因为jpegenc本身就是图像编码器,接收原始帧输入后直接输出JPEG编码数据,链路能力集是通顺的,和保存MP4时漏加编码器的场景有本质区别。
修正后的命令
补全缺失的编码、码流解析环节,用专门的videoscale组件做分辨率缩放,不要直接在编码caps里硬写尺寸,修正后可正常保存MP4的命令如下:
gst-launch-1.0 playbin uri=rtsp://<替换为你的摄像头IP>:8554 video-sink="videoconvert ! videoscale ! video/x-raw,width=320,height=240 ! x264enc ! h264parse ! mp4mux ! filesink location=test.mp4"
video-sink链路各组件作用
videoconvert:自动适配原始视频帧的色彩空间格式,匹配后续编码组件的输入要求videoscale:负责将原始640x480分辨率的视频缩放至目标320x240分辨率video/x-raw,width=320,height=240:声明缩放后输出的原始视频帧参数,和之前错误配置的video/x-h264有本质区别x264enc:将原始视频帧编码为H.264格式h264parse:解析H.264码流的参数、时序信息,保证MP4封装格式合规mp4mux:将编码后的H.264码流封装为MP4容器格式filesink:将封装完成的数据写入本地test.mp4文件
调试提示
如果首次运行仍有协商报错,可以先去掉分辨率缩放相关的videoscale ! video/x-raw,width=320,height=240段,先跑通编码+封装的基础链路,再逐步添加缩放参数调试。
内容的提问来源于stack exchange,提问作者Lucas Nascimento
相关产品推荐
相关产品推荐

