返回知识中心
指纹

MediaDevices 枚举与虚拟摄像头隐私

区分设备列表、权限与实际媒体流,理解枚举限制,并正确处理虚拟摄像头来源与采集失败。

BotBrowser Team

文档中心

想直接进入 指纹 文档吗?

这篇文章属于知识中心的指南库。若你要步骤化配置、参考说明和持续更新,请直接进入对应 docs 分区。

媒体设备枚举可以帮助用户选择摄像头或麦克风,但不能证明网页能从该设备采集内容。enumerateDevices() 返回受权限和策略影响的输入/输出设备视图;getUserMedia() 则单独请求权限并尝试打开真实来源。虚拟摄像头依赖浏览器之外的软件提供。应把列表既视为隐私敏感的浏览器表面,也视为有限的选择辅助:说明媒体用途,只请求所需流,并显示当前活动来源。BotBrowser 可以控制网页看到的枚举报告,但不会创建来源、授予权限或保证媒体流可用。

这一区分关系到浏览器身份判断。即使尚未显示可读标签,网页也可能知道当前上下文似乎有摄像头或麦克风选项;但这不等于用户已同意、硬件正常或媒体流可用。相关背景见浏览器权限指纹和WebRTC 网络身份与隐私。

设备枚举、权限与来源可用性是媒体流程中的不同阶段

观看视频

这段英文视频在受控实验页中跟踪一次 enumerateDevices() 调用:页面收到的 kind、label 和 deviceId,标签为何受权限限制,以及配置档模式与真实模式作为设备来源有何不同。它只展示一次 Ubuntu runner 上的观察;不比较不同主机,不授予采集权限,也不能证明身份、匿名性、访问权限或远程站点的判定。

摘要

设备枚举是受权限筛选的发现视图,不代表网页已经能够采集。BotBrowser 可以控制基于配置文件向网页报告的设备列表,但权限、来源可用性和媒体流仍是浏览器与操作系统的独立条件。

目录

设备枚举会告诉网页什么

设备变化通知仅在浏览器支持时可用,触发时机也可能不同。界面应能刷新列表,并处理来源在打开前消失的情况。

navigator.mediaDevices.enumerateDevices() 返回当前上下文中浏览器公开的 MediaDeviceInfo 输入和输出记录。kind 区分音频输入、视频输入和音频输出;允许披露时,label 提供供用户选择的名称。浏览器可能把默认采集设备排在前面。因此结果是有序且受当前上下文影响的视图,不是系统连接设备的完整清单。第一项也不必然是“摄像头”:列表包含不同类型,默认排序也不代表用户偏好。

当前上下文会限制列表。相关接口要求安全上下文;Permissions Policy 可以排除某些设备类型,权限状态也会影响可见设备和标签。访问前列表可能缺少项目或只显示空标签。授权后结果可能更具体,但仍不是固定清单。插入耳机、切换摄像头、修改浏览器权限或操作系统隐私设置都可能改变结果。

即使标签为空,条目的存在和类型也可能透露网页环境似乎有无摄像头或麦克风选项。数量、排序和名称变化会提供更多设备配置线索。反复收集因此是隐私决策,不是无害诊断。如果用户只需为通话选择一个来源,就把列表留在界面上,不要默认发送到分析系统。支持人员若需要错误记录,也只保存能回答问题的必要信息,而非原始设备清单。

把返回结果看作一个时间点的快照。连接耳机、启用虚拟摄像头应用、改变权限或换电脑,都可能改变浏览器报告的内容。Media Capture 规范定义了针对文档可见设备变化的通知,但应用仍应在合适的交互节点刷新选项,并处理用户选择后、实际采集前设备消失的情况。该通知不保证每个浏览器都会立即报告所有硬件或操作系统变化。

为适应窄屏,将每个结果作为简短状态卡片阅读:

  • 列表里有视频输入。 可以说明:浏览器当前向此上下文报告了一个视频来源。不能证明:摄像头已通电、已获准或能输出画面。下一步:请求所需媒体流并处理结果。
  • 标签为空或笼统。 可以说明:当前上下文没有收到有用的设备名称。不能证明:设备不存在或损坏。下一步:检查安全上下文、策略、权限和预期标签行为。
  • 出现多个来源或排序变化。 可以说明:当前报告多个选项,或列表视图有变化。不能证明:第一项是用户偏好,或列表稳定不变。下一步:让用户选择,并在设备变化时刷新界面。
  • 没有匹配来源。 可以说明:当前枚举结果没有公开符合条件的选项。不能证明:系统中没有物理或虚拟来源。下一步:检查操作系统、来源应用和策略。

这张表用于避免把浏览器观察夸大为对硬件或同意状态的断言。MediaDeviceInfo.label 是选择界面的标签,不能证明设备归属或实际内容;它也不同于开始采集后媒体轨道的 MediaStreamTrack.label。

为什么列表受限且涉及隐私

媒体访问受到多层控制。相关接口要求安全上下文;浏览器执行自身权限模型,嵌入网页的 Permissions Policy 也可能限制设备类型。用户可以拒绝,操作系统也可以单独阻止摄像头或麦克风。浏览器允许访问不代表操作系统一定能提供画面;操作系统设置本身也不等于网页来源获得了许可。关于权限策略如何更广泛地限制浏览器能力,可参阅Permissions Policy、浏览器能力与隐私。

浏览器可能只公开默认设备,或在来源获得采集权限前隐藏标签。不要承诺枚举总会返回完整列表,也不要把空标签直接当作故障。应说明有意义的下一步:确认页面使用安全连接,检查嵌入策略是否允许所需设备类型,必要时检查浏览器权限,然后由用户操作发起重试。如果产品没有采集用途,不应只为读取设备名称而请求打开媒体流。

不同环境报告的设备选项可能不同,网站若收集这些数据,可能把它们与其他信息结合成更完整的浏览器指纹。适当做法是数据最小化并说明访问原因,而不是承诺枚举数据完全保密或各处一致。deviceId 对调用来源唯一,按浏览器隐私模型可能跨会话保持,但清除存储或使用隐私模式可能使其轮换。groupId 按文档生成,跨浏览会话并不稳定。两者都不是永久身份。不要超出选择或支持需要保留设备名、数量或标识符,也不要把设备清单用于认证或代替用户身份选择。

跨源嵌入受两层策略约束:顶层响应头定义允许的来源,iframe 的 allow 属性只能在该范围内委派能力。例如:

Permissions-Policy: camera=(self "https://meet.example"), microphone=(self "https://meet.example")
<iframe src="https://meet.example" allow="camera; microphone"></iframe>

如果响应头排除了嵌入来源,allow 不能增加权限。策略阻止的摄像头或麦克风类型不会出现在 enumerateDevices() 结果中;这表示来源看到的是受策略过滤的列表,不代表设备不存在。getUserMedia() 仍是单独步骤,还要满足权限与来源可用性条件。

用户看到的操作应对应真实请求:说明需要音频、视频还是两者、谁会接收内容、是否录制,以及拒绝其中一项后还能做什么。纯语音客服通话不应强制要求摄像头;设备设置页也不应暗中开始采集。提供更换来源与停止采集的入口,并让这些控件可访问,而不是只依靠预览画面。关于音频相关的浏览器接口,可参阅Web Audio API 访问与音频工作流。

枚举列表不等于可用媒体流

停止媒体轨道会结束当前采集,但本身不会撤销网站以后再次请求所需的权限。如果产品提供这两种操作,应使用彼此独立且清晰的控件。

enumerateDevices() 回答的是网页当前看到哪些设备记录;getUserMedia() 回答的是另一个问题:在适用的权限决定之后,浏览器能否打开请求的音视频来源并返回 MediaStream。成功枚举不代表采集成功。用户拒绝、浏览器或操作系统拦截、上下文不符合要求,或没有可用来源,都可能使请求失败;用户尚未响应时,请求也可能保持等待。

应将这些情况作为采集状态处理,而不是枚举错误。如果产品支持无摄像头或无麦克风的替代路径,就保留该路径;用户拒绝后,没有新的操作就不要重复请求。采集开始后,显示选中的来源及活动状态。设备断开时应明确提示,并由用户决定是否选择其他来源;静默切换可能改变实际采集内容,超出用户预期。

日志和支持界面应区分:报告的设备选项、权限状态、采集请求结果、已选媒体轨道,以及轨道仍活动或已结束。这些事实有助于识别空列表、用户拒绝、系统拦截或设备断开后的轨道结束。不要为了区分这些状态就保存媒体内容或完整设备清单。关于另一类需要权限的设备接口,可参阅Web Bluetooth 权限、设备选择与隐私。

虚拟摄像头带来的额外步骤

共享标签页或屏幕是需要用户选择的另一种采集方式,不是 enumerateDevices() 返回的摄像头设备,也不应称作虚拟摄像头。

虚拟摄像头是由已安装应用或操作系统集成提供的摄像头来源,可组合场景、演示内容、测试图案或其他获准输入。浏览器不会因为枚举设备就创建这个来源;列表里出现一个名称,也不证明对应应用正在运行或输出画面。

该来源有独立生命周期。如果流程需要,先启动获准的来源应用;之后用户再通过浏览器的正常权限流程选择或请求摄像头。浏览器权限仍然适用,实际采集也仍取决于来源是否可用。任务结束时停止媒体轨道,并按应用正常方式关闭或停用来源。这是两个不同操作:结束浏览器流不一定会退出来源应用,而关闭应用可能导致已选轨道结束或失败。

使用清晰名称,例如“演示摄像头”,并说明内容是实时画面、合成场景还是测试图。分享前检查实际显示内容:预制场景可能泄露账户信息或内部文档,物理摄像头也可能拍到私人空间。虚拟摄像头可用于合规的制作、培训、无障碍和测试,但不能替代同意或内容审查。

若来源没有出现,按链路逐步检查:来源应用是否运行并输出预期场景;操作系统是否向浏览器公开该来源;当前枚举结果是什么;最后再测试由用户发起的采集请求。每一步回答的问题不同。浏览器列表缺少项目,不代表可以绕过 API;更改报告列表也不保证产生可用媒体流。

设置与故障排查决策路径

用这条路径选择下一项检查,避免混淆发现设备、取得同意和实际采集。它可用于产品设置、客服指引或版本检查,每种状态都对应一项有限而明确的操作。

窄屏下可以使用同样的决策路径卡片:

  • 页面不在安全上下文,或接口不可用。 含义:当前环境无法执行常规媒体流程。操作:使用受支持的安全页面,或解释此环境限制。
  • 列表中没有设备。 含义:经过权限和策略筛选的视图没有匹配选项。操作:检查嵌入策略和系统来源,不要仅据此判断硬件不存在。
  • 有设备但标签为空。 含义:发现了选项,但没有公开有用名称。操作:只有在选择仍安全时继续,名称确有必要时再检查权限行为。
  • 用户拒绝请求。 含义:浏览器中没有获得采集授权。操作:保留已说明的替代方案并尊重选择。
  • 已授权但采集失败。 含义:权限并没有让来源变得可用。操作:检查系统隐私设置、来源应用、设备连接和具体请求错误。
  • 采集开始后又结束。 含义:已打开的轨道停止或失去来源。操作:显示已停止、更新界面状态,并先询问再切换来源。

新流程应从完成任务所需的最低能力开始。先解释用途,只请求必要类型,并测试用户拒绝的路径。再测试来源缺失或断开、列表变化和正常停止。设备连接或移除后,devicechange 事件可触发重新读取列表,但不会授予权限或自动重启采集。在移动端与桌面端保持含义一致,即使浏览器权限对话框不同。同步检查分析与日志:默认只记录运行流程必需的信息,不保存媒体内容或完整列表。

虚拟摄像头还要增加两项检查:外部来源应用确实输出预期场景;用户同意后,浏览器确实获得了已选媒体轨道。前者不证明后者。分享前向用户确认当前来源,并在整个会话中保留停止控件。结束时可调用 stream.getTracks().forEach(track => track.stop()) 停止该流中的每条轨道。可观察的用户结果比枚举数组非空更有意义。

BotBrowser 的枚举控制与限制

BotBrowser 文档说明,--bot-media-devices 用于控制 navigator.mediaDevices.enumerateDevices() 向网页报告音视频设备的方式。默认情况下,BotBrowser 返回配置文件中的设备列表,无需额外参数。当媒体流程依赖设备视图时,这有助于让报告列表与所选浏览器配置保持一致。BotBrowser 控制的是网页看到的枚举结果,但不会创建虚拟摄像头,不会授予浏览器或操作系统权限,也不保证选中来源能生成 MediaStream。

该控制针对报告的枚举结果。它不会安装或创建虚拟摄像头,不会启动来源应用,不会授予浏览器或操作系统权限,也不保证选中来源可以生成 MediaStream。网页和平台仍遵循正常的权限与采集规则。应分别验证设备列表、权限和媒体流,并且只描述实际检查过的结果。

换言之,配置文件设备列表可以让发现设备这一层更可预测;用户流程仍须负责同意、来源选择、采集失败处理和停止。产品界面与支持说明都应清楚划分这些边界。

Screen Capture 后续阅读

Screen Capture API 增加了由用户选择的显示表面;可在Screen Capture API:用户控制与隐私中对比它与设备枚举边界的生命周期。

实践结论

分别检查设备枚举、权限和媒体流可用性。仅将 BotBrowser 基于配置文件的枚举控制用于让报告视图与目标配置保持一致;在流程中明确用户同意、外部虚拟摄像头软件、操作系统访问和停止媒体流。

来源

#MediaDevices#虚拟摄像头#麦克风#隐私#浏览器工作流

本文属于指南: 什么是浏览器指纹?原理、风险、信号与隐私边界

在 BotBrowser 里跑一遍同样的检查

加载 profile,让刚读到的这些信号在浏览器内部保持一致,并在正式上线前先在自己的机器上确认结果。