Nginx搭建flv視頻點播服務器

Nginx搭建flv視頻點播服務器

??????? 前一段時間使用Nginx搭建的多媒體服務器只能在緩沖過的時間區域內拖放, 而不能拖放到未緩沖的地方. 這就帶來了一個問題: 如果視頻限速的速率很小, 那么客戶端觀看視頻時肯定不流暢, 而且用戶不能向前拖放, 用戶體驗很不好. 如果視頻限速的速率很大或者不限速, 服務器是承受不了的, 特別是在某個熱門視頻高并發訪問的情況下, 而且客戶端瀏覽器也在快速的從服務器接收數據, 同樣會造成客戶端視頻播放不流暢的問題, 對服務器的性能和網絡帶寬都是很大的挑戰. 所以很有必要將實現視頻服務器的點播功能, 這樣既可以對視頻進行限速, 避免大量不必要數據在網上的傳送, 又可以改善用戶體驗.

??????? 本文主要參考了 [1] 的實現, 期間會遇到各種意想不到問題, 然后從網上搜索到了解決方法. 本次搭建使用的Nginx版本是1.4.1, jwplayer的版本是6.6.

資料:

HTTP Live Streaming(縮寫是 HLS)是一個由蘋果公司提出的基于HTTP的流媒體 網絡傳輸協議。
HLS只請求基本的HTTP報文,與實時傳輸協議(RTP)不同,HLS可以穿過任何允許HTTP數據通過的防火墻或者代理服務器。它也很容易使用內容分發網絡來傳輸媒體流。

一 準備

搭建點播服務器需要如下幾個模塊:

  • nginx_mod_h264_streaming: 使nginx支持h264編碼的視頻
  • http_flv_module: 支持flv
  • http_mp4_module: 支持mp4
  • nginx-rtmp-module: 支持rtmp協議

其中http_flv_module和http_mp4_module兩個模塊是nginx自帶的, 可以在編譯的時候加上相應的選項.

nginx_mod_h264_streaming的下載地址:?http://h264.code-shop.com/trac/wiki/Mod-H264-Streaming-Nginx-Version2

nginx-rtmp-module托管在GitHub上:?https://github.com/arut/nginx-rtmp-module

注意在GitHub的"Build"部分有這樣一句話:

Several versions of nginx (1.3.14 - 1.5.0) require http_ssl_module to be added as well:

1
./configure --add-module=<path-to-nginx-rtmp-module> --with-http_ssl_module

我用的nginx版本是1.4.1, 所以在configure的時候需要加上"--with-http_ssl_module"選項, 否則會出現錯誤:

1
2
3
4
5
src/http/ngx_http_request.c: 在函數‘ngx_http_set_virtual_server’中:
src/http/ngx_http_request.c:1992:9: 錯誤: 未知的類型名‘ngx_http_ssl_srv_conf_t’
src/http/ngx_http_request.c:1999:16: 錯誤: ‘ngx_http_ssl_module’未聲明(在此函數內第一次使用)
src/http/ngx_http_request.c:1999:16: 附注: 每個未聲明的標識符在其出現的函數內只報告一次
src/http/ngx_http_request.c:2001:17: 錯誤: 在非結構或聯合中請求成員‘verify’

ssl的安裝可以參考網上教程, 也可以參考 [1] . 注意Ubuntu環境下SSL庫是libssl-dev:

sudo apt-get install libssl-dev

?

關于ffmpeg及其依賴庫的安裝, 請參考我的上一篇文章:http://www.cnblogs.com/wanghetao/p/3386311.html, 在此不再贅述.

???

?二 安裝Nginx及其相關模塊

(Nginx使用的是Perl正則表達式, 所以需要首先安裝PCRE, 讀者能夠從網上找到PCRE的安裝過程, 在此不贅述. )

# mkdir nginx

# cd nginx

# cp ../nginx-1.4.1.tar.gz ../nginx_mod_h264_streaming-2.2.7.tar.gz ../nginx-rtmp-module-master.zip ./

#? tar -zxvf nginx-1.4.1.tar.gz?????????????????????????????????? (同樣地將其余兩個包解壓縮)

# cd nginx-1.4.1

# ./configure --prefix=/usr/local/nginx --add-module=../nginx_mod_h264_streaming-2.2.7 --add-module=../nginx-rtmp-module-master/ --with-http_flv_module --with-http_mp4_module --with-http_gzip_static_module --with-http_stub_status_module --with-cc-opt="-I/usr/local/ffmpeg2/include" --with-ld-opt="-L/usr/local/ffmpeg2/lib"

# make

這個時候出現了錯誤:

1
2
3
4
5
6
7
8
9
10
../nginx_mod_h264_streaming-2.2.7/src/mp4_reader.c: 在函數‘esds_read’中:
../nginx_mod_h264_streaming-2.2.7/src/mp4_reader.c:377:16: 錯誤: 變量‘stream_priority’被設定但未被使用 [-Werror=unused-but-set-variable]
../nginx_mod_h264_streaming-2.2.7/src/mp4_reader.c:376:12: 錯誤: 變量‘stream_id’被設定但未被使用 [-Werror=unused-but-set-variable]
../nginx_mod_h264_streaming-2.2.7/src/mp4_reader.c: 在函數‘stsd_parse_vide’中:
../nginx_mod_h264_streaming-2.2.7/src/mp4_reader.c:529:22: 錯誤: 變量‘level_indication’被設定但未被使用 [-Werror=unused-but-set-variable]
../nginx_mod_h264_streaming-2.2.7/src/mp4_reader.c:528:22: 錯誤: 變量‘profile_compatibility’被設定但未被使用 [-Werror=unused-but-set-variable]
../nginx_mod_h264_streaming-2.2.7/src/mp4_reader.c:527:22: 錯誤: 變量‘profile_indication’被設定但未被使用 [-Werror=unused-but-set-variable]
../nginx_mod_h264_streaming-2.2.7/src/mp4_reader.c:526:22: 錯誤: 變量‘configuration_version’被設定但未被使用 [-Werror=unused-but-set-variable]
cc1: all warnings being treated as errors
make[1]: *** [objs/addon/src/mp4_reader.o] 錯誤 1

?# vim objs/Makefile (修改objs/Makefile文件, 去掉其中的"-Werror"), 然后就能夠正常編譯了.

# make

# make install

至此nginx安裝成功了.

?

三 修改nginx配置文件nginx.conf, 配置虛擬主機

這一部分請參考 [1] , 其中比較傳神的地方是限速功能的實現. 使用一個端口提供視頻文件視頻文件的訪問以及并發訪問量和限速功能(比如8081), 然后從另一個端口配置虛擬主機, 在網頁中使用http協議對8081的視頻文件進行訪問.

?

四 flv文件轉碼和元數據的注入

使用ffmpeg轉碼后的flv文件需要注入元數據(metadata)之后才能實現拖放, metadata中主要是關鍵幀. 我使用yamdi實現元數據的注入.?yamdi為flv文件增加了很多metadata信息,比如創建者、是否有關鍵幀、是否有視頻、是否有音頻,視頻高度和寬度等等。而yamdi加入的meta數據中,最有效的要數關鍵幀。被注入了關鍵幀的flv可以實現像土豆網、優酷網等大型視頻網站一樣的“拖進度”,提前拖到緩沖還未加載到的位置開始播放。另一個可用的工具是flvtool2, 網上一個文章提供了兩者的用法和比較:?http://blog.csdn.net/zhangxh1013/article/details/5896482.

yamdi的安裝也很簡單:

(1) 下載:?http://yamdi.sourceforge.net/

(2) # tar -zxvf yamdi-1.9.tar.gz

(3) # cd yamdi-1.9

(4) # make & make install

元數據注入:

1
yamdi -i input.flv -o output.flv

?

輸出的文件使用ffmpeg查看, 可以看到這樣的信息:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
Metadata:
???creator???????? : m_8efd9a8eb9c1c7434e76fc0e27052f91_md Tudou, Inc.
???metadatacreator : Tudou Metadata Injector?for?FLV - Version 1.0
???hasKeyframes??? :?true
???hasVideo??????? :?true
???hasAudio??????? :?true
???hasMetadata???? :?true
???canSeekToEnd??? :?false
???datasize??????? : 14485828
???videosize?????? : 13399710
???audiosize?????? : 1041346
???lasttimestamp?? : 251
???lastkeyframetimestamp: 245
???lastkeyframelocation: 14458306
???encoder???????? : Lavf55.12.100

?這說明元數據注入成功, 并且輸出文件中含有關鍵幀.

當然, 在ffmpeg轉碼的同時也可以向flv文件中加入關鍵幀, 只需加入 "-keyint_min" 參數. ffmpeg文檔中對此的解釋是:

1
2
3
‘keyint_min integer (encoding,video)’
????Set minimum interval between IDR-frames.????? (設定IDR幀之間的最小間隔)

?

但是用ffmpeg轉碼的方法添加元數據仍然不能對視頻隨意拖放, 用ffmpeg可以看到轉碼后的視頻的元數據信息:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
ffmpeg -i output.flv
......
?Metadata:
????creator???????? : m_8efd9a8eb9c1c7434e76fc0e27052f91_md Tudou, Inc.
????metadatacreator : Tudou Metadata Injector?for?FLV - Version 1.0
????hasKeyframes??? :?true
????hasVideo??????? :?true
????hasAudio??????? :?true
????hasMetadata???? :?true
????canSeekToEnd??? :?false
????datasize??????? : 14485828
????videosize?????? : 13399710
????audiosize?????? : 1041346
????lasttimestamp?? : 251
????lastkeyframetimestamp: 245
????lastkeyframelocation: 14458306
????encoder???????? : Lavf55.12.100

?它與使用yamdi方法產生的結果的位于區別是"canSeekToEnd"為false, 為什么這樣的flv視頻不能拖放還有待于以后研究.

?

五 jwplayer播放器的設定

通過以上四個步驟, flv視頻點播服務器已經基本搭建成功了. 下面要使用jwplayer播放視頻, 檢驗以上的設置是否成功. 編寫以下PHP文檔并在瀏覽器中打開:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<!DOCTYPE heml>
<html>
????<head>
????????<script type="text/javascript"?src="jwplayer/jwplayer.js"></script>
????????<meta http-equiv="Content-Type"?content="text/html;charset=utf-8"?/>
????</head>
?????
????<body>???????
????????<div id="myElement">Loading the page...</div>
????????<script type="text/javascript">
????????????var?file_name =?"<?php echo? $_GET['id']; ?>";
????????????jwplayer("myElement").setup({
????????????????file:?"http://localhost:82/"?+ file_name,
????????????????// image: "data/myposter.jpg",
????????????????title: file_name,
????????????});
????????</script>
????</body>
</html>

  

?瀏覽器中輸入URL:

1
http://localhost/videoplayer/?id=output.flv

?滿懷激動地心情, 結果還是失望了: 視頻仍然不能拖放!!! 為什么會這樣呢? 原因是jwplayer的設定不正確. 需要向jwplayer中添加SEEK功能, 告訴它要對文件進行seek, 這是通過"starttime"參數實現的. 可以參考:?http://www.longtailvideo.com/support/jw-player/28855/pseudo-streaming-in-flash. 對于不同編碼和不同視頻格式的文件, "starttime"的值各不相同. 對于h264編碼的flv格式文件, "starttiem"設為"start".

?

修改完成后, 在瀏覽器中再次輸入URL, 嘗試拖動進度條, 成功了!!! 真的很高興..來個高清大圖給乃們瞧瞧.

參考文獻:

[1]?http://5iqiong.blog.51cto.com/2999926/1132639

分類:?ffmpeg與multimedia

轉載于:https://www.cnblogs.com/archoncap/p/4988907.html

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/397197.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/397197.shtml
英文地址,請注明出處:http://en.pswp.cn/news/397197.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

編碼拾遺

1 #!/usr/bin/env python32 #-*- coding:utf-8 -*-3 4 Administrator 5 2018/8/16 6 7 8 # fopen("demo","r",encoding"utf8")9 # dataf.read() 10 # print(data) 11 # f.close() 12 13 14 # print("沈哲子") 15 16 s"中國&qu…

Xcode:Foundation框架找不到,或者是自動提示出現問題

問題描述&#xff1a;Foundation框架找不到&#xff0c;或者是自動提示出現問題 之前的操作&#xff1a;手賤&#xff0c;不少心把編譯器里面的源碼改了處理辦法&#xff1a;清理緩存緩存位置&#xff1a;點擊桌面后&#xff0c;選擇系統菜單欄&#xff1a;前往—電腦—硬盤—用…

mybatis 不生效 參數_Mybatis-日志配置

日志Mybatis 的內置日志工廠提供日志功能&#xff0c;內置日志工廠將日志交給以下其中一種工具作代理&#xff1a;SLF4JApache Commons LoggingLog4j 2Log4jJDK loggingMyBatis 內置日志工廠基于運行時自省機制選擇合適的日志工具。它會使用第一個查找得到的工具(按上文列舉的順…

PS通過濾色實現簡單的圖片拼合

素材如下&#xff1a; 素材一&#xff1a; 雪山 素材二&#xff1a; 月亮 效果&#xff1a; 實現步驟 1、在PS中打開雪山素材一 2、將月亮素材直接拖入雪山所在的圖層中 3、鎖定置入素材的高寬比&#xff08;點擊一下鏈狀按鈕&#xff09; 4、調整月亮到合適大小合適位置 5、…

預處理:主成分分析與白化

主成分分析 引言 主成分分析&#xff08;PCA&#xff09;是一種能夠極大提升無監督特征學習速度的數據降維算法。更重要的是&#xff0c;理解PCA算法&#xff0c;對實現白化算法有很大的幫助&#xff0c;很多算法都先用白化算法作預處理步驟。 假設你使用圖像來訓練算法&#x…

jQuery Ajax

jQuery load()方法&#xff1a;是簡單但強大的Ajax 方法load() 方法從服務器(URL,data,callback);必須的URL 參數規定您希望架加載的URL可選的data參數 規定與請求一同發送的差字符串鍵/值對集合。可選的callback參數時load()方法完成后所執行的函數名稱$(documnet).ready(…

swagger 修改dto注解_Web服務開發:Spring集成Swagger,3步自動生成API文檔

目錄&#xff1a;1&#xff0c;Spring Boot集成Swagger2&#xff0c;Swagger接口文檔頁面3&#xff0c;常見問題和解決方法在Sping開發REST接口服務時&#xff0c;API文檔是不可缺少的一個重要部分。Swagger框架定義了完整的REST接口文檔規范&#xff0c;提供了強大的頁面測試功…

WPF自定義控件之列表滑動特效 PowerListBox

列表控件是應用程序中常見的控件之一&#xff0c;對其做一些絢麗的視覺特效&#xff0c;可以讓軟件增色不少。 本人網上看過一個視頻&#xff0c;是windows phone 7系統上的一個App的列表滾動效果&#xff0c;效果非常炫 現在在WPF上用ListBox重現此效果 首先我們來分析一下&am…

去除inline-block元素間間距

根本原因&#xff1a;inline-block元素之間之所以有空白間距是因為空格有字體大小原因。 第一種&#xff1a; 把代碼之間的換行空白都去掉。 例如&#xff1a; <div>第一個inline-block元素</div><div>第二個inline-block元素</div> 第二種&#xff1a…

python - 定時清理ES 索引

只保留三天 #!/usr/bin/env python3 # -*- coding:utf-8 -*- import os import datetime# 時間轉化為字符串now_time datetime.datetime.now().strptime(datetime.datetime.now().strftime("%Y.%m.%d"),"%Y.%m.%d") os.system("curl -XGET http://12…

CnosDB如何確保多步操作的最終一致性?

背景 在時序數據庫中&#xff0c;資源的操作是一個復雜且關鍵的任務。這些操作通常涉及到多個步驟&#xff0c;每個步驟都可能會失敗&#xff0c;導致資源處于不一致的狀態。例如&#xff0c;一個用戶可能想要在CnosDB集群中刪除一個租戶&#xff0c;這個操作可能需要刪除租戶…

頸椎前路caspar撐開器_“骨質增生”導致的頸椎病怎么破?

來源&#xff1a;《脊柱外科微創手術精要》作者&#xff1a;中日友好醫院 鄒海波此文是區別于頸椎間盤軟性突出診治一文&#xff0c;主要針對“骨質增生”導致的頸椎病(Spondylosis)進行介紹。傳統的頸椎前路手術主要為頸椎病而設計。一度認為對頸椎病采用前路手術的主要好處在…

Struts2整合Freemarker生成靜態頁面

2019獨角獸企業重金招聘Python工程師標準>>> 這是生成靜態頁面的預覽&#xff1a; 其對應的模板文件&#xff1a; <table style"text-align:center;FONT-SIZE: 11pt; WIDTH: 600px; FONT-FAMILY: 宋體; BORDER-COLLAPSE: collapse" borderColor#3399ff…

使用flot.js 發現x軸y軸無法顯示軸名稱

添加此插件解決問題 flot-axislabels https://github.com/markrcote/flot-axislabels 轉載于:https://www.cnblogs.com/feehuang/p/4993920.html

快速冪、矩陣快速冪、快速乘法

快速冪 快速冪是我們經常用到的一種算法&#xff0c;快速冪顧名思義就是快速的冪運算。我們在很多題目中都會遇到冪運算&#xff0c;但是在指數很大的時候&#xff0c;我們如果用for或者是pow就會超時&#xff0c;這時候就用到了快速冪。 快速冪的原理就是&#xff0c;當求b^p的…

vue 前端顯示圖片加token_手摸手,帶你用vue擼后臺 系列二(登錄權限篇)

完整項目地址&#xff1a;vue-element-adminhttps://github.com/PanJiaChen/vue-element-admin前言拖更有點嚴重&#xff0c;過了半個月才寫了第二篇教程。無奈自己是一個業務猿&#xff0c;每天被我司的產品虐的死去活來&#xff0c;之前又病了一下休息了幾天&#xff0c;大家…

注釋工具_蘋果已購丨Notability丨功能強大而簡單易用的筆記及PDF注釋工具

點擊上方“天澤黑科技”右上角“...”點選“設為星標”點擊加星★ 貼近你心 ?今天給大家購買效率類排行第3名的 Notability &#xff01;大家在桌面 App store 登陸我的賬號&#xff0c;搜索下載即可&#xff01;榮獲 iPad、iPhone 和 Mac 的 Apple「編」愛新 App 殊榮&#x…

第四章 大網高級 ? NSSA

STUB、完全stub、NSSA、完全nssa實驗要求&#xff1a;1、配置IP地址2、配置OSPF多區域3、配置 stub 末梢區域4、配置完全stub末梢區域5、配置 nssa 非純末梢區域6、配置完全nssa非純末梢區域7、配置兩種協議相互注入重分發8、實現全網互通一、配置OSPF多區域二、配置rip v2三、…

[AlwaysOn Availability Groups] 健康模型 Part 2 ——擴展

[AlwaysOn Availability Groups] 健康模型 Part 2 ——擴展 健康模型擴展 第一部分已經介紹了AlwayOn健康模型的概述。現在是創建一個自己的PBM策略&#xff0c;然后設置為制定的歸類。創建這些策略&#xff0c;創建之后修改一下配置&#xff0c;dashboard就會自動評估這些策略…

665. Non-decreasing Array - LeetCode

Question 665. Non-decreasing Array Solution 題目大意&#xff1a; 思路&#xff1a;當前判斷2的時候可以將當前元素2變為4&#xff0c;也可以將上一個元素4變為2&#xff0c;再判斷兩變化后是否滿足要求。 Java實現&#xff1a; public boolean checkPossibility(int[] nums…