Safari 14.1.2报错Can't find variable: MediaRecorder问题咨询
问题核心触发原因
你遇到的报错核心有两类触发原因:
- 版本支持的隐性限制
Safari 14版本仅将MediaRecorder作为实验性特性提供,默认处于关闭状态,直到Safari 14.1(桌面端)、iOS 14.5(iOS端)才默认开放该API。此外iOS端所有第三方浏览器都基于WKWebView内核实现,低版本系统的WKWebView也默认关闭MediaRecorder能力,需要应用侧单独配置开启。
另外MediaRecorder要求运行环境必须为HTTPS或者localhost,非安全上下文下API不会暴露,也会触发变量不存在的报错。 - MIME类型不兼容的连锁报错
你代码中使用的video/webm格式是Chrome/Edge等浏览器支持的格式,Safari全系不支持webm容器,错误的MIME类型传参也可能导致实例化失败,部分旧版本Safari会先抛出变量不存在的错误而非格式不支持的提示。
具体解决步骤
- 第一步:先做兼容性前置判断
不要直接实例化MediaRecorder,先做全局存在性判断,不存在时直接给出用户引导,避免执行后续逻辑:
if (!window.MediaRecorder) { // 可自定义降级逻辑,比如引导用户升级浏览器、切换浏览器 alert('当前环境不支持录制功能,请升级到最新版Safari或使用Chrome/Edge浏览器'); return; }
- 第二步:适配各浏览器支持的MIME类型
不要写死webm格式,先通过MediaRecorder.isTypeSupported()方法匹配当前环境支持的格式,再传入构造函数:
// 视频录制匹配MIME类型的示例 function getSupportedVideoMime() { const candidateTypes = [ 'video/mp4;codecs=h264', // 适配Safari 'video/webm;codecs=vp9', 'video/webm;codecs=vp8' // 适配Chrome、Edge等 ]; for (const type of candidateTypes) { if (MediaRecorder.isTypeSupported(type)) return type; } throw new Error('当前环境无支持的视频录制格式'); } // 音频录制匹配MIME类型的示例 function getSupportedAudioMime() { const candidateTypes = [ 'audio/mp4', // 适配Safari 'audio/webm;codecs=opus' // 适配Chrome、Edge等 ]; for (const type of candidateTypes) { if (MediaRecorder.isTypeSupported(type)) return type; } throw new Error('当前环境无支持的音频录制格式'); } // 实例化调用示例 this.videoRecorder = new MediaRecorder(mediaStream, { mimeType: getSupportedVideoMime(), audioBitsPerSecond: 128000 }); this.audioRecorder = new MediaRecorder(mediaStream, { mimeType: getSupportedAudioMime(), audioBitsPerSecond: 128000 });
- 第三步:低版本Safari兼容方案
如果必须兼容14.0~14.4版本的Safari,可以选择两种方案:- 引导用户手动开启实验性特性:路径为 Safari - 设置 - 高级 - 实验性特性 - 开启「MediaRecorder」
- 引入MediaRecorder polyfill,基于WebAssembly实现录制能力,无需依赖原生API。
- 第四步:检查运行环境
确认页面运行在HTTPS或者localhost下,非安全上下文下原生MediaRecorder不会暴露。如果是内嵌在App中的WebView页面,需要端侧配置开启WKWebView的MediaRecorder相关权限。
内容的提问来源于stack exchange,提问作者Paul McKay
相关产品推荐
相关产品推荐

