基于Ubuntu16.04(64位)搭建WebRTC服务器(目前搭在局域网)

我的电脑是win764位,WebRTC只能在Linux下搭建,所以我就在虚拟机Ubuntu16.04上搭建的服务器,Ubuntu16.04的apt源不好,有些更新下载不了,就算是翻墙了,还是找不到资源,只能自己逐个去下载。有些问题,各种google,各种“百度一下”,还是很难找到答案,只能在很小的角落中找到答案。所以,得总结一下。主要工作就是搭建下面这4个服务器.

1. 搭建房间服务器(Room Server) 
2. 搭建信令服务器(Collider Server) 
3. 搭建STUN\TURN服务器 
4. 配置Nginx服务器 

注意:我的IP是192.168.30.141,后面对应的地方改成你自己的IP。

附:1.建议一开始就进入root模式,在终端命令行输入sudo passwd root ,输入你的密码,然后sudo su,再次输入你的密码即可

     2.如果安装过程或者启动过程中缺少Ubuntu的trusty相关包的话,apt又安装不了的话,比如我的就缺少libhiredis0.10这个包,可以从下面这个链接下载安装:

      https://www.ubuntuupdates.org/package/core/trusty/universe/base/libhiredis0.10


参考链接:http://blog.csdn.net/gladsnow/article/details/77900333#8

一、前期准备

    1.1 设置网络模式为桥接模式,因为我是虚拟机搭建的,为了让和主机同一个网段设备能访问到WebRTC服务器,方便后面的调试。

     


       1.2 搭建java的JDK1.8环境,请参考下面的连接

                http://blog.csdn.net/sxk874890728/article/details/78805603


             或者也可以下使用openjdk

                  add-apt-repository ppa:openjdk-r/ppa

apt-get update

apt-get install openjdk-8-jdk


二、搭建房间服务器(Room Server) 

2.1 安装nodejs相关包(Ubuntu16.04自带python2.7的,如果你的没有那就得自行安装):

预先解锁以下两个文件夹:

   sudo rm /var/cache/apt/archives/lock
   sudo rm /var/lib/dpkg/lock

开始安装nodejs相关包:

1)apt-get update

2)curl -sL https://deb.nodesource.com/setup_8.x | sudo -E bash -
sudo apt-get install -y nodejs

3)apt-get install npm

4)npm -g install grunt-cli

5)apt-get install python-webtest

        2.2 下载apprtc源码(操作所在目录/root/

    源码网址:https://github.com/webrtc/apprtc点击打开链接

git clone  https://github.com/webrtc/apprtc.git   
cd apprtc
npm install
  
  
  • 1
  • 2
  • 3
  • 修改文件 
    1.修改/root/apprtc/src/app_engine/constants.py
    TURN_BASE_URL = 'http://192.168.30.141:80'; #本机内网地址192.168.6.54,此处的端口号与Nginx监听的端口号保持一致
        TURN_URL_TEMPLATE = '%s/turn.php?username=%s&key=%s'; #如果turn.php未实现,可使用默认配置
        CEOD_KEY = 'inesadt'   #此处后面turn配置的用户名保持一致

        ICE_SERVER_BASE_URL = 'http://192.168.30.14:80';#此处的端口号与Nginx监听的端口号保持一致
        ICE_SERVER_URL_TEMPLATE = '%s/iceconfig.php?key=%s'; #如果iceconfig.php未实现,可用默认配置,但是Android Apk会有问题

        WSS_INSTANCE_HOST_KEY = '192.168.30.141:8089'  #信令服务器端口号8089  
        WSS_INSTANCE_NAME_KEY = 'vm_name'
        WSS_INSTANCE_ZONE_KEY = 'zone'
        WSS_INSTANCES = [{
        WSS_INSTANCE_HOST_KEY: '192.168.30.141:8089',
        WSS_INSTANCE_NAME_KEY: 'wsserver-std',
        WSS_INSTANCE_ZONE_KEY: 'us-central1-a'  
        }, {  
        WSS_INSTANCE_HOST_KEY: '192.168.30.141:8089',
        WSS_INSTANCE_NAME_KEY: 'wsserver-std-2', 
        WSS_INSTANCE_ZONE_KEY: 'us-central1-f'
        }]
  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19

2.修改/root/apprtc/src/app_engine/apprtc.py(若使用https,则不需修改此文件)

if wss_tls and wss_tls == 'false':
        wss_url = 'ws://' + wss_host_port_pair + '/ws'
        wss_post_url = 'http://' + wss_host_port_pair
        else:
        wss_url = 'ws://' + wss_host_port_pair + '/ws'
        wss_post_url = 'http://' + wss_host_port_pair
  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 编译(在apprtc目录下进行)
grunt build
  
  
  • 1

编译完成之后,会生成out目录,房间服务器编译完成。

  • 安装和配置google app engine

    1.下载google app engine 
    需翻墙,下载地址https://storage.googleapis.com/appengine-sdks/featured/google_appengine_1.9.50.zip,或者通过其他地方下载。

    2.配置google app engine 路径 
    解压google_appengine_1.9.50.zip

    unzip google_appengine_1.9.50.zip
        
        
    • 1

    编辑/etc/profile文件,在文件最后添加语句:

    export PATH="$PATH:/root/google_appengine/"
        
        
    • 1

    (当前安装目录是/root/google_appengine,请根据自己的安装目录进行配置) 
    保存profile文件,进行以下操作生效

    source /etc/profile
        
        
    • 1
  • 运行房间服务器(room server)

    在目录/root/google_appengine目录下找到dev_appserver.py脚本,执行以下语句

./dev_appserver.py --host=192.168.30.141 /root/apprtc/out/app_engine
  
  
  • 1

若想后台运行,则执行 
nohup ./dev_appserver.py --host=192.168.30.141 /root/apprtc/out/app_engine &


4. 搭建信令服务器(Collider Server)

  • 安装go语言编译器
apt-get install golang-go
  
  
  • 1
  • 复制collider源代码 
    (此源码在房间服务器源码目录下/root/apprtc/src/collider/) 
    在/root目录下新建文件夹
mkdir -p goWorkspace/src
  
  
  • 1

配置编译环境,此配置是暂时有效的

export GOPATH=/root/goWorkspace/
  
  
  • 1

把/root/apprtc/src/collider/目录下的三个目录(collider、collidermain、collidertest)复制到/root/goWorkspace/src/目录下

cp -rf /root/apprtc/src/collider/* /root/goWorkspace/src
  
  
  • 1
  • 修改代码 
    编辑文件/root/goWorkspace/src/collidermain/main.go,修改房间服务器的地址
var roomSrv = flag.String("room-server", "http://192.168.30.141:8080", "The origin of the room server")
  
  
  • 1
  • 编译信令服务器 
    进入目录/root/goWorkspace/src/,此处编译需要翻墙。
go get collidermain 
go install collidermain
  
  
  • 1
  • 2

编译成功后,在/root/goWorkspace/下会生成bin和pkg目录。 
若此处编译无法翻墙,可手动下载需要的文件。在/root/goWorkspace/src/目录下,

mkdir -p golang.org/x 
cd golang.org/x/
git clone https://github.com/golang/net
  
  
  • 1
  • 2
  • 3

然后再进行编译即可。

  • 运行信令服务器 
    进入/root/goWorkspace/bin/目录,运行信令服务器
./collidermain -port=8089 -tls=false
  
  
  • 1

若想后台运行,则执行

nohup ./collidermain -port=8089 -tls=false &
  
  
  • 1

5. 搭建STUN\TURN服务器

  • 安装coturn
apt-get install coturn
  
  
  • 1
  • 进行相关配置 
    1. 编辑文件/etc/default/coturn,把TURNSERVER_ENABLED=1的注释去掉。
    2. 编辑文件/etc/turnserver.conf,把以下内容加入到文件最后(或者在文件中找到相应的选项,进行配置)
  listening-device=eth0  #此处eth0是电脑网卡名称
  listening-port=3478       #turn服务器的端口号
  relay-device=eth0 #此处eth0是电脑网卡名称
  min-port=49152
  max-port=65535
  Verbose
  fingerprint
  lt-cred-mech
  use-auth-secret
  static-auth-secret=inesadt    #此处要和房间服务器配置时constants.py文件中的CODE_KEY保持一致。
  user=inesadt:0x7e3a2ed35d3cf7f19e2f8b015a186f54
  user=inesadt:inesadt
  stale-nonce
  cert=/usr/local/etc/turn_server_cert.pem
  pkey=/usr/local/etc/turn_server_pkey.pem
  no-loopback-peers
  no-multicast-peers
  mobility
  no-cli
  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19

上述文件中 0x7e3a2ed35d3cf7f19e2f8b015a186f54的生成方法:

turnadmin -k -u inesadt -r north.gov -p inesadt
  
  
  • 1
-k 表示生成一个long-term credential key  
-u 表示用户名  
-p 表示密码   
-r 表示Realm域(这个值的设置可能会有影响)。

  
  
  • 1
  • 2
  • 3
  • 4
  • 5

coturn的证书生成(即配置文件中cert和pkey)

sudo openssl req -x509 -newkey rsa:2048 -keyout /usr/local/etc/turn_server_pkey.pem -out /usr/local/etc/turn_server_cert.pem -days 99999 -nodes
  
  
  • 1
  • 启动coturn服务器
service coturn start
  
  
  • 1

6. 配置Nginx服务器

  • 安装Nginx
apt-get install nginx
  
  
  • 1
  • 安装php和php-fpm
apt-get install php
apt-get install php7.0-fpm
  
  
  • 1
  • 2
  • 编辑配置文件/etc/nginx/sites-available/default
upstream roomserver {
            server 192.168.30.141:8080;
        }
        server {
            #listen 80 default_server;
            #listen [::]:80 default_server;

            listen 80;
            # SSL configuration
            #
            # listen 443 ssl default_server;
            # listen [::]:443 ssl default_server;
            #
            # Note: You should disable gzip for SSL traffic.
            # See: https://bugs.debian.org/773332
            #
            # Read up on ssl_ciphers to ensure a secure configuration.
            # See: https://bugs.debian.org/765782
            #
            # Self signed certs generated by the ssl-cert package
            # Don't use them in a production server!
            #
            # include snippets/snakeoil.conf;

            root /var/www/html;

            # Add index.php to the list if you are using PHP
            index index.html index.htm index.nginx-debian.html index.php; #此处添加index.php

            server_name _;

            #   location / {
                # First attempt to serve request as file, then
                # as directory, then fall back to displaying a 404.
                #   try_files $uri $uri/ =404;
            #   }

            # pass the PHP scripts to FastCGI server listening on 127.0.0.1:9000
            #
            location ~ \.php$ {
                include snippets/fastcgi-php.conf;
                # With php7.0-cgi alone:
                #   fastcgi_pass 127.0.0.1:9000;
                # With php7.0-fpm:
                fastcgi_pass unix:/run/php/php7.0-fpm.sock;
            }

            location / {
                proxy_pass http://roomserver$request_uri;
                proxy_set_header Host $host;
            }
            # deny access to .htaccess files, if Apache's document root
            # concurs with nginx's one
            #
            #location ~ /\.ht {
                #   deny all;
            #}
        }

  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 编写turn.php文件和iceconfig.php文件,并把文件放到目录/var/www/html/目录下

    turn.php文件内容

 <?php  
            $request_username = $_GET["username"];  
            if(empty($request_username)) {  
                echo "username == null";  
                exit;  
            }  
            $request_key = $_GET["key"];  
            $time_to_live = 600;  
            $timestamp = time() + $time_to_live;//失效时间  
            $response_username = $timestamp.":".$_GET["username"];  
            $response_key = $request_key;  
            if(empty($response_key))  
            $response_key = "code_key"; //constants.py中CEOD_KEY  

            $response_password = getSignature($response_username, $response_key);  

            $jsonObj = new Response();  
            $jsonObj->username = $response_username;  
            $jsonObj->password = $response_password;  
            $jsonObj->ttl = 86400;
            //此处需配置自己的服务器
            $jsonObj->uris= array("stun:192.168.30.141:3478","turn:192.168.30.141:3478?transport=udp","turn:192.168.30.141:3478?transport=tcp");

            echo json_encode($jsonObj);  

        /**   
         * 使用HMAC-SHA1算法生成签名值   
         *   
         * @param $str 源串   
         * @param $key 密钥   
         *   
         * @return 签名值   
         */
        function getSignature($str, $key) {
        $signature = "";
        if (function_exists('hash_hmac')) {
        $signature = base64_encode(hash_hmac("sha1", $str, $key, true));
        } else {
        $blocksize = 64;
        $hashfunc = 'sha1';
        if (strlen($key) > $blocksize) {
        $key = pack('H*', $hashfunc($key));
        }
        $key = str_pad($key, $blocksize, chr(0x00));
        $ipad = str_repeat(chr(0x36), $blocksize);
        $opad = str_repeat(chr(0x5c), $blocksize);
        $hmac = pack(
        'H*', $hashfunc(
        ($key ^ $opad) . pack(
        'H*', $hashfunc(
        ($key ^ $ipad) . $str
        )
        )
        )
        );
        $signature = base64_encode($hmac);
        }
            return $signature;
            }

            class Response {  
                public $username = "";  
                public $password = "";  
                public $ttl = "";  
                public $uris = array("");  
            }  

        ?> 
  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68

iceconfig.php文件内容

<?php  
            $request_username = "inesadt";  //配置成自己的turn服务器用户名
            if(empty($request_username)) {  
                echo "username == null";  
                exit;  
            }  
            $request_key = "inesadt";  //配置成自己的turn服务器密码
            $time_to_live = 600;  
            $timestamp = time() + $time_to_live;//失效时间  
            $response_username = $timestamp.":".$_GET["username"];  
            $response_key = $request_key;  
            if(empty($response_key))  
            $response_key = "CEOD_KEY";//constants.py中CEOD_KEY  

            $response_password = getSignature($response_username, $response_key);  

            $arrayObj = array();
            $arrayObj[0]['username'] = $response_username;
            $arrayObj[0]['credential'] = $response_password;
            //配置成自己的stun/turn服务器
            $arrayObj[0]['urls'][0] = "stun:192.168.30.141:3478";
            $arrayObj[0]['urls'][1] = "turn:192.168.30.141:3478?transport=tcp";
            $arrayObj[0]['uris'][0] = "stun:192.168.30.141:3478";
            $arrayObj[0]['uris'][1] = "turn:192.168.30.141:3478?transport=tcp";
            $jsonObj = new Response();  
            $jsonObj->lifetimeDuration = "300.000s";
            $jsonObj->iceServers = $arrayObj;
            echo json_encode($jsonObj);  

            /**   
            * 使用HMAC-SHA1算法生成签名值   
            *   
            * @param $str 源串   
            * @param $key 密钥   
            *   
            * @return 签名值   
            */
            function getSignature($str, $key) {
                $signature = "";
                if (function_exists('hash_hmac')) {
                    $signature = base64_encode(hash_hmac("sha1", $str, $key, true));
                } else {
                    $blocksize = 64;
                    hashfunc = 'sha1';
                    if (strlen($key) > $blocksize) {
                        $key = pack('H*', $hashfunc($key));
                    }
                    $key = str_pad($key, $blocksize, chr(0x00));
                    $ipad = str_repeat(chr(0x36), $blocksize);
                    $opad = str_repeat(chr(0x5c), $blocksize);
                    $hmac = pack(    
                    'H*', $hashfunc(    
                            ($key ^ $opad) . pack(    
                                    'H*', $hashfunc(    
                                            ($key ^ $ipad) . $str    
                                   )    
                            )    
                        )    
                    ); 
                    $signature = base64_encode($hmac);
                }
                return $signature;
           }

            class Response {
                    public $lifetimeDuration = "";
                    public $iceServers = array("");
            } 
        ?>

  
  
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70

注:关于turn.php和iceconfig.php文件实现的必要性,如果是http局域网,即使不实现这两个文件,在浏览器之间也可实现视频通信,但是如果使用Google的Android apk作为客户端,则可能会存在问题。经过测试,实现iceconfig.php即可,turn.php文件可不实现。

  • 重启Nginx服务器和php7.0-fpm

    service nginx restart 
    service php7.0-fpm restart


7. 运行测试

  • PC浏览器(Android手机浏览器)之间的视频通信测试 
    访问http://192.168.30.141:8080 
    1.PC浏览器:Firefox 54.0.1(64bits),Android手机浏览器:Firefox 54.0.1

    测试OK

    2.PC浏览器:Google Chrome 59.0.3071.115(64bits),Android手机浏览器:Google Chrome 59.0.3071.125

    测试失败 
    失败原因:Error getting user media: Only secure origins are allowed。

  • Android APK客户端之间以及客户端与浏览器之间 (注意:在apk主界面设置按钮处设置为自己的服务器地址
    1.获取Android APK

    下载webrtc源码,在源码目录下webrtc/examples/androidapp,进行编译即可生成Android APK

    2.测试Android APK客户端之间

    测试OK

    2.测试Android APK客户端与浏览器(Firefox)之间

    测试OK

           备注: 只有火狐浏览器可以,其他的不行的。如果用普通浏览器,会发生如下错误:

                    Failed to get access to local media.Error name was NotAllowedError.Continuing without sending a stream.

附录

解决方法1: 
房间服务器编译完成后,在/root/apprtc/out/app_engine/js/apprtc.debug.js文件中找到window.history.pushState({‘roomId’: roomId, ‘roomLink’: roomLink}, roomId, roomLink),把这句话注释掉,重新运行即可。(如果重新编译,需要重新修改) 
解决方法2: 
在/root/apprtc/src/web_app/js/appcontroller.js文件中找到window.history.pushState({‘roomId’: roomId, ‘roomLink’: roomLink}, roomId, roomLink),把这句话注释掉,然后重新编译,重新运行房间服务器即可。

   

猜你喜欢

转载自blog.csdn.net/sxk874890728/article/details/78970180