js 如何拦截 location.href,让页面的 location.href 都失效或者可以自定义跳转到其他页面? - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
推荐关注
Meteor
JSLint - a Javascript code quality tool
jsFiddle
D3.js
WebStorm
推荐书目
Javascript 权威指南第 5 版
Closure: The Definitive Guide
zictos
V2EX    Javascript

js 如何拦截 location.href,让页面的 location.href 都失效或者可以自定义跳转到其他页面?

  •  
  •   zictos 2021-01-29 11:08:38 +08:00 6626 次点击
    这是一个创建于 1774 天前的主题,其中的信息可能已经有所发展或是发生改变。
    alert()和 window.open()都可以拦截,只需要重新赋值即可,比如添加一行 alert=0,那么所有的 alert 就失效了。甚至可以自定义只拦截包括某些字符串的 alert 对话框,具体可以搜索“js 拦截 alert”。

    html 的 a 标签也可以拦截, 具体可以搜索“js 阻止 a 标签跳转”。

    但是 location.href 是一个属性,只要修改属性就会触发页面跳转,设置为任何值都无法让它失效。并且 href 属性也无法删除。难道没其他办法了呢?或者能不能获取到 location.href 这个事件并拦截,然后再自定义做自己想做的事。
    26 条回复    2021-02-05 18:40:00 +08:00
    cjd6568358
        1
    cjd6568358  
       2021-01-29 11:55:16 +08:00
    Object.defineProperty
    ho121
        2
    ho121  
       2021-01-29 11:59:05 +08:00 via Android
    把 location 干掉?
    KuroNekoFan
        3
    KuroNekoFan  
       2021-01-29 12:00:30 +08:00
    ....为什么要在 very bad practise 的路上渐行渐远呢
    musi
        4
    musi  
       2021-01-29 12:05:10 +08:00
    具体可以搜索“js proxy”
    weixiangzhe
        5
    weixiangzhe  
       2021-01-29 12:05:35 +08:00
    我查一了 proxy,貌似也是不行 https://stackoverflow.com/questions/45965893/how-do-i-apply-get-proxy-on-window-location-in-Javascript

    关注一下,可以整 就可以写个油猴脚本,在手机上阻止部分网页打开 app 了
    zictos
        6
    zictos  
    OP
       2021-01-29 12:11:55 +08:00
    @weixiangzhe #5 其实我就是想阻止手机上打开 app,比如手机网页打开淘宝一般是用下面的代码:
    window.location.href = 'taobao://m.taobao.com'

    taobao://是淘宝注册的 scheme,所以会打开淘宝,后面的 m.taobao.com 就是要打开的网页地址,如果输入 taobao://detail.tmall.com/item.htm?id=616270509106 就会打开一个天猫的服装商品页面
    zjm947373
        7
    zjm947373  
       2021-01-29 12:15:18 +08:00
    一楼正解
    weixiangzhe
        8
    weixiangzhe  
       2021-01-29 12:17:30 +08:00
    @zictos , 我之前找了一下,貌似没有整,看看楼下怎么说吧,不过现在还有 universal link, schema 是 https 的
    Quarter
        9
    Quarter  
       2021-01-29 12:49:02 +08:00 via iPhone
    可以重新给 window.location 赋值么,不太清楚
    zictos
        10
    zictos  
    OP
       2021-01-29 12:55:07 +08:00
    @Quarter #9 不能, 给 window.location 赋值也是默认会直接跳转, 跟 window.location.href 的效果是一样的。况且如果整个 window.location 都不能用了,对整个网页的影响会比较大
    mxT52CRuqR6o5
        11
    mxT52CRuqR6o5  
       2021-01-29 13:12:27 +08:00
    @zjm947373
    @cjd6568358
    并不行
    Cannot redefine property
    rekulas
        12
    rekulas  
       2021-01-29 13:31:35 +08:00
    干掉也能恢复
    var i = document.createElement('iframe');
    i.style.display = 'none';
    document.body.appendChild(i);
    window.alert = i.contentWindow.alert;

    这只是其中一种手段
    除非你把大部分函数都禁了 不然总有办法
    sleepm
        13
    sleepm  
       2021-01-29 13:41:00 +08:00
    js Service Worker fetch event
    no1xsyzy
        14
    no1xsyzy  
       2021-01-29 13:43:03 +08:00
    https://stackoverflow.com/a/35558822/6202760 都不行
    但是你可以通过 onbeforeunload 来阻止跳转
    https://stackoverflow.com/a/2647601/6202760
    虽然
    no1xsyzy
        15
    no1xsyzy  
       2021-01-29 13:44:27 +08:00
    @no1xsyzy 虽然我不清楚这种不发生页面跳转的是否会生效……

    @sleepm fetch event 不能阻止自定义 scheme,除非你想替换页面上的每一个 js
    zictos
        16
    zictos  
    OP
       2021-01-29 13:45:44 +08:00
    @cjd6568358 #1
    defineProperty 可以修改 userAgent, 但是不能修改 location.href, 提示 Cannot redefine property: href


    下面是修改 userAgent 的代码, 修改后 userAgent 字符串就变成"new_ua"了:
    Object.defineProperty(navigator, 'userAgent', {
    value: 'new_ua',
    writable: false
    });
    console.log(navigator.userAgent);
    zjsxwc
        17
    zjsxwc  
       2021-01-29 13:45:49 +08:00
    js 做不到,只能在浏览器层面搞,比如安卓 webview 有 shouldOverrideUrlLoading 来处理

    https://stackoverflow.com/questions/16669046/android-webview-shouldoverrideurlloading-method
    azcvcza
        18
    azcvcza  
       2021-01-29 13:52:21 +08:00
    在浏览器里的 js 是有极限的,例如没办法在 onbeforeunload 里去阻塞关闭
    ciqulover
        19
    ciqulover  
       2021-01-29 13:54:17 +08:00 via iPhone
    对于 window.location 你想任何方式 re-define property 都是不可能的,这个对象你用页面同等级的 js 动不了他分毫。
    不过如果是浏览器插件就可以,如果目标脚本是异步加载,可以直接劫持掉请求,如果内联 script 就用 MutationObserver 。
    4 楼说的 jsproxy 可以参考一下。
    zictos
        20
    zictos  
    OP
       2021-01-29 13:54:24 +08:00
    @rekulas #12 如果很少有人去禁用的话, 那网站开发者在写 js 的时候就根本不会考虑 alert 被禁用的情况。虽然不能保证 100%的网站都有效,起码也可以保证 99%的网站有效
    sleepm
        21
    sleepm  
       2021-01-29 14:27:12 +08:00
    document.addEventListener('click', function(event) {
    target = event.target;
    if(target.nodeName == "A"){
    event.preventDefault();
    }else{
    console.log(target.nodeName);
    }
    });
    粗暴..
    poly1911
        22
    poly1911  
       2021-01-29 17:15:50 +08:00
    Proxy
    ysc3839
        23
    ysc3839  
       2021-01-29 17:33:30 +08:00
    这个问题应该从浏览器层面解决的。但不知道为什么 Chrome 有打开外部程序前提示的功能,却不给 Chrome Android 启用。
    顺便吐槽一下,Chrome Android 给人感觉问题很多,经常出现卡死的情况,不是说浏览器已经是多进程模型,标签页出现问题不会导致整个程序卡死了吗?
    shenyuzhi
        24
    shenyuzhi  
       2021-01-29 22:04:13 +08:00 via iPhone
    浏览器 api 不是普通的 js 对象。不建议做骚操作。
    anson2017
        25
    anson2017  
       2021-02-05 18:37:11 +08:00
    window.location.href = null
    zictos
        26
    zictos  
    OP
       2021-02-05 18:40:00 +08:00
    @anson2017 #25 不行,会跳转到当前页面所在路径下的 null 页面,是一个不存在的页面
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     5122 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 37ms UTC 01:17 PVG 09:17 LAX 17:17 JFK 20:17
    Do have faith in what you're doing.
    ubao msn snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86