• 示例工程

【免费下载链接】WebRTC-Experiment

WebRTC, WebRTC and WebRTC. Everything here is all about WebRTC!!

项目地址: https://gitcode.com/gh_mirrors/we/WebRTC-Experiment
点击查看 免费下载

本篇指南以 RTCMultiConnection 仓库中 dist/README.md 为骨架,系统讲解 WebRTC 库 RTCMultiConnection 的脚本引入方式:核心库 dist/RTCMultiConnection.min.js 的本地、Heroku、GitHub Releases 与 CDN 四种加载路径,文件分享场景下 FileBufferReader.js 的配套引入,以及 dev 目录按需加载为何顺序无关。读完你不仅能正确地把 RTCMultiConnection 挂载进自己的页面,还能理解 distdev 两套目录的构建关系,并结合仓库内的 Gruntfile.jspackage.jsondemos 实例写出可直接运行的 WebRTC 页面。

一、这份文档解决什么问题

dist/README.md 是 RTCMultiConnection 的脚本引入速查卡:它不讲解 API,只回答一个最实际的问题——在 HTML 页面里到底应该怎么把 RTCMultiConnection 加载进来,以及在哪些场景下还需要额外引入 FileBufferReader.js

原文档虽短,但信息密度很高,覆盖了四种核心库加载路径、文件分享的附加依赖、以及 dev 目录的使用原则。下面我们逐段继承,并结合仓库源码把每一行的背后逻辑讲透。

二、核心库的四种引入方式(完整继承)

原文档给出的标准引入代码块如下,先原样继承:

<script src="/dist/RTCMultiConnection.min.js"></script>

<!-- Heroku Link -->
<script src="http://rtcmulticonnection.herokuapp.com/dist/RTCMultiConnection.min.js"></script>

<!-- or specific version -->
<script src="https://github.com/muaz-khan/RTCMultiConnection/releases/download/3.4.3/RTCMultiConnection.js"></script>

<!-- or CDN -->
<script src="https://rawgit.com/muaz-khan/RTCMultiConnection/master/dist/RTCMultiConnection.min.js"></script>

四种方式各有适用场景,分别说明:

1. 本地静态路径(推荐用于自有服务器)

<script src="/dist/RTCMultiConnection.min.js"></script>

这是部署到自有服务器后的首选方式。在仓库中,/dist/ 目录下实际存放着两个构建产物(见 dist 目录):

从源码结构看,min.jsjs 内容完全等价,只是是否经过 uglify 压缩的区别。

2. Heroku 在线演示服务器

<script src="http://rtcmulticonnection.herokuapp.com/dist/RTCMultiConnection.min.js"></script>

适用于快速验证、临时 demo 或没有自建服务器时的联调。注意原文档此处为 http://,但 WebRTC 的 getUserMedia 等能力依赖安全上下文(HTTPS),正式使用时更稳妥的是在 HTTPS 页面上引用对应资源。

3. 按版本号锁定(GitHub Releases)

<script src="https://github.com/muaz-khan/RTCMultiConnection/releases/download/3.4.3/RTCMultiConnection.js"></script>

当项目需要固定某一历史版本时,通过 Releases 下载路径引用可避免 CDN 缓存与上游更新带来的行为漂移。仓库中当前版本为 3.6.9,若你依赖的是更早的 3.4.x,就用这种方式锁定。

4. CDN

<script src="https://rawgit.com/muaz-khan/RTCMultiConnection/master/dist/RTCMultiConnection.min.js"></script>

引用 master 分支最新构建产物,适合个人实验;生产项目建议改用带版本号的路径,保证可复现。

实践建议:这四种方式本质指向同一个文件——dist 目录下由构建流水线产出的 RTCMultiConnection.js。无论选哪一种,页面上 new RTCMultiConnection() 的用法完全一致。

三、dist 目录的由来:Grunt 构建产物

理解了 dist 是什么,就理解了"为什么文档让你引 dist 下的文件"。dist 不是手写的源码,而是由 Gruntfile.jsdev 目录 下的数十个模块按固定顺序拼接、替换、压缩后生成的。

Gruntfile.jsconcat 任务可以看到完整的拼接顺序:

src: [
    'dev/head.js',
    'dev/amd.js',

    'dev/SocketConnection.js', // You can replace it with: FirebaseConnection.js || PubNubConnection.js
    'dev/MultiPeersHandler.js',

    // 'dev/adapter.js', ---- optional
    'node_modules/detectrtc/DetectRTC.js', // npm install detectrtc
    'dev/globals.js',

    'dev/ios-hacks.js', // to support ios
    'dev/RTCPeerConnection.js',
    'dev/CodecsHandler.js', // to force H264 or codecs other than opus

    'dev/OnIceCandidateHandler.js',
    'dev/IceServersHandler.js',

    'dev/getUserMedia.js',
    'dev/StreamsHandler.js',

    'dev/TextSenderReceiver.js',
    'dev/FileProgressBarHandler.js',

    'dev/TranslationHandler.js',

    'dev/RTCMultiConnection.js',
    'dev/tail.js'
],

后续任务链为:replace(注入 config.json 内容与版本号)→ uglify(生成 dist/RTCMultiConnection.min.js)→ copy(把未压缩版拷贝到 dist/RTCMultiConnection.js)→ clean(清理临时目录)。开发者模式下还可通过 grunt watch 监听 dev/*.js 的改动自动重新构建。

因此,"引 dist 下那一个文件"等价于"引入了 dev 下全部核心模块",这也是 package.json"main": "./dist/RTCMultiConnection.js" 的含义:无论是浏览器 <script> 还是 Node 环境 require('rtcmulticonnection'),最终加载的都是这个统一产物。

四、文件分享场景:必须额外引入 FileBufferReader.js

原文档特别强调:如果你要用 RTCMultiConnection 分享文件,除了核心库,还必须再引入 FileBufferReader。原文如下:

<script src="/dev/FileBufferReader.js"></script>

<!-- or CDN -->
<script src="https://cdn.webrtc-experiment.com:443/FileBufferReader.js"></script>

为什么文件分享需要它

文件二进制数据必须切片、分包、重组才能在 DataChannel 上可靠传输,这部分工作由 FileBufferReader 完成。在仓库中可以找到佐证:

  • 核心构建 Gruntfile.js 的拼接列表里包含 dev/FileProgressBarHandler.js,而文件传输的底层实现依赖 FileBufferReader 的分片能力;
  • MultiPeersHandler.jsenableV2Api.js 中均有对 FileBufferReader 的直接引用;
  • package.json 的依赖列表中,fbr(FileBufferReader 的 npm 包名)被显式列出。

当前仓库中 FileBufferReader 的实际位置

原文档中的 /dev/FileBufferReader.js 指的是发布包内 dev 目录的写法。从当前镜像仓库的结构看,FileBufferReader 已独立成单独的顶层模块:

仓库内的真实 demo 也印证了这一点——demos/file-sharing.html 的引入方式为:

<script src="/dist/RTCMultiConnection.min.js"></script>
<script src="/node_modules/webrtc-adapter/out/adapter.js"></script>
<script src="/socket.io/socket.io.js"></script>
<script src="/node_modules/fbr/FileBufferReader.js"></script>

也就是说:本地化部署时,把 FileBufferReader.js(或经 npm 安装的 fbr 包)与核心库一并引入即可,其余代码完全不变。同样的模式也出现在 text-chat-file-sharing.html 等 demo 中。

五、dev 目录按需加载:为什么"顺序无关"

原文档最后一句是关键使用提示:

You can link multiple files from dev directory. Order doesn't matters.

(可以从 dev 目录链接多个文件,顺序无关紧要。)

这一条该怎么理解

dev 目录下是未压缩、可独立加载的模块源码。当你不使用打包好的 dist 产物、而是逐个链接 dev 文件时,顺序无所谓,原因可以从代码组织方式推断:

  1. 运行时引用而非加载时引用:dev 模块之间通过运行时查找全局对象或延迟调用互相协作(例如 RTCMultiConnectionnew 之后才去查找 Socket、RTCPeerConnection 等能力),而不是在脚本解析阶段就要求目标必须已就绪;
  2. 入口统一:所有模块最终服务于全局 RTCMultiConnection 构造函数(见 dev/head.jsvar RTCMultiConnection = function(roomid, forceOptions) {...}),实例化发生在所有 <script> 加载完成之后。

需要顺序的场景只有一处:构建

真正对顺序敏感的是构建过程而非页面加载——即第三节展示的 Gruntfile.js concat 列表,它决定了 dist 产物的内部组织。对最终用户而言,直接引 dist 单文件即可,完全不用关心顺序;只有当你想在调试时逐文件打断点、或按需裁剪功能模块时,才使用 dev 目录的逐文件引入方式。

六、一个完整的最小可运行页面

结合 docs/getting-started.md 的"From Scratch"章节,把脚本引入落到一个完整示例上。先引入库与信令客户端:

<script src="https://rtcmulticonnection.herokuapp.com/dist/RTCMultiConnection.min.js"></script>
<script src="https://rtcmulticonnection.herokuapp.com/socket.io/socket.io.js"></script>

再加两个房间控制按钮:

<button id="btn-open-room">Open Room</button>
<button id="btn-join-room">Join Room</button><hr>

然后是业务代码(放在页面底部):

var connection = new RTCMultiConnection();

// 使用公共信令服务器;自建服务器时改为 '/' 或你自己的地址
connection.socketURL = 'https://rtcmulticonnection.herokuapp.com:443/';

// 以下为推荐配置
connection.session = {
    audio: true,
    video: true
};

connection.sdpConstraints.mandatory = {
    OfferToReceiveAudio: true,
    OfferToReceiveVideo: true
};

connection.onstream = function(event) {
    document.body.appendChild(event.mediaElement);
};

按钮事件:

var predefinedRoomId = 'YOUR_Name';

document.getElementById('btn-open-room').onclick = function() {
    this.disabled = true;
    connection.open(predefinedRoomId);
};

document.getElementById('btn-join-room').onclick = function() {
    this.disabled = true;
    connection.join(predefinedRoomId);
};

注意:getting-started 文档明确要求页面运行在 HTTPS 下(Remember HTTPs is required),这是 WebRTC 媒体能力的浏览器安全前提。

自有信令服务器时的引入差异

如果你自建信令服务器(仓库内 RTCMultiConnection-Server 即此类服务端),页面引入方式会变成仓库 demo 中的标准三件套(见 demos/One-to-One.html):

<script src="/dist/RTCMultiConnection.min.js"></script>
<script src="/node_modules/webrtc-adapter/out/adapter.js"></script>
<script src="/socket.io/socket.io.js"></script>

同时把 connection.socketURL 指向自己的服务器(本地默认 /),信令事件名等参数可通过 config.json 配置。安装与启动流程参见 docs/installation-guide.md

七、引入顺序与常见排错清单

基于原文档与仓库示例,汇总一份引入与排错核对表:

  1. 核心库放最后或页面底部<script> 建议放在 </body> 前,保证 DOM 就绪后再初始化 connection
  2. 文件分享必须带 FileBufferReader:只引核心库就调用 send() 分享文件会报错——这是最常见的遗漏(对应原文档第二节的提醒);
  3. 验证信令可用性:自建服务器启动后,浏览器打开 https://localhost:9001/socket.io/socket.io.js,能加载该文件说明 socket.io 服务正常;
  4. 注意协议一致性:页面是 HTTPS 时,脚本资源尽量也用 HTTPS 引入,避免混合内容被浏览器拦截;
  5. 版本一致性:核心库、FileBufferReader、服务端若来自不同发布渠道,尽量保持同一版本线,避免 API 不匹配(当前仓库核心库版本为 3.6.9)。

八、深入阅读

  • 示例工程

【免费下载链接】WebRTC-Experiment

WebRTC, WebRTC and WebRTC. Everything here is all about WebRTC!!

项目地址: https://gitcode.com/gh_mirrors/we/WebRTC-Experiment
点击查看 免费下载
Logo

火山引擎视频云技术社区,是面向 AI 音视频开发者的技术交流平台。这里汇聚源自抖音、豆包等亿级 DAU 产品的 RTC、直播、点播、AI 媒体处理、音视频互动技术,提供接入指南、最佳实践、性能调优、场景案例、Demo 代码、开源项目、白皮书和 API 文档。社区汇聚官方工程师与一线开发者,为 AI 视频通话、数字人、AI 视频处理等应用的开发与落地提供技术支持。

更多推荐