window.location.origin移动端不生效的兼容问题及处理方法
window.location.origin兼容性问题及URL相对路径提取正确方案 问题根因
window.location.origin确实存在移动端老旧浏览器兼容性问题:
- iOS 10及以下版本的Safari、安卓4.4及以下版本的原生Webview/浏览器未实现该属性,在这些环境中读取
window.location.origin会返回undefined - 当调用字符串
replace方法传入undefined作为匹配值时,无法匹配到URL中的域名部分,自然无法完成剥离,这就是移动端运行失效的核心原因。
兼容处理方案
方案1:补全location.origin的Polyfill
在业务代码入口处提前注入以下兼容逻辑,后续原有代码即可正常运行:
if (!window.location.origin) { window.location.origin = `${window.location.protocol}//${window.location.hostname}${window.location.port ? `:${window.location.port}` : ''}`; }
这段逻辑完全遵循标准origin的拼接规则:协议 + // + 主机名 + 非默认端口(存在时拼接),和现代浏览器的原生返回值完全一致。
方案2:更鲁棒的相对路径提取写法(推荐)
不推荐直接用字符串替换的方式提取相对路径,容易受origin大小写、默认端口显式声明等边缘情况影响导致匹配失败,优先用URL解析的方式实现:
const fullUrl = 'http://www.example.com/map/123'; const urlInstance = new URL(fullUrl); // 拼接路径、查询参数、哈希,得到完整相对路径 const relativePath = urlInstance.pathname + urlInstance.search + urlInstance.hash; console.log(relativePath); // 输出 /map/123
如果需要兼容连URL API都不支持的超老旧移动环境,可以用纯字符串截断实现,完全不依赖origin属性:
function getRelativeUrl(fullUrl) { const protocolSplitPos = fullUrl.indexOf('//'); // 传入的本身就是相对路径,直接返回 if (protocolSplitPos === -1) return fullUrl; const pathStartPos = fullUrl.indexOf('/', protocolSplitPos + 2); return pathStartPos === -1 ? '/' : fullUrl.slice(pathStartPos); }
补充说明
- 目前iOS 11+、安卓Chrome 60+等主流现代移动浏览器已经完全支持
window.location.origin,如果业务不需要覆盖5年以前的老旧移动设备,直接使用原生属性不会有问题。 - 字符串替换匹配origin的写法容错性差,只要传入的URL字符串和当前origin存在端口显式声明、协议/域名大小写差异,就会出现替换失败,优先选择解析类方案更可靠。
内容的提问来源于stack exchange,提问作者gordie
相关产品推荐
相关产品推荐

