差不多是3、4年前的事情,不算是经典的前端安全问题,不过实际的界面效果就跟被攻击了一样,算是非常规的前端安全问题
看起来诡异的现象
前同事,前端大佬F君,在群里跟我们分享一个问题,就是他们的门户网站,嵌入了合作方的广告iframe后,界面打开就直接滚动到这广告的位置了
类似于上图,界面打开后,在无任何手动操作的情况下,直接滚动到了广告的位置
肯定是这个广告iframe搞的鬼,F君分析他们的iframe源码,想具体找到他们是使用的什么代码去操作的这个,但苦于他们的源码内容比较多且压缩过,一时找不到是哪块代码的影响
问题定位
首先确定这个iframe是与主站跨域的,这样的话iframe就无法拿到主站的window信息去操作滚动等事项,而且主站也没有对外暴露接收postMessage的方法
排除滚动的原因,那就只有一种可能了,就是iframe内的元素获取焦点,直接把界面给“定位”
下来了
基于这个猜测,我跟F君说,估计是这个iframe里面有隐藏的input,通过input的获取焦点事件,把界面滚动下来了
F君基于这个思路又找了一会,发现果然是这个原因!他找到了一个隐藏的很深的input,异步将这个input获取焦点,就能实现他们的目的
之所以说隐藏的很深,并不是dom节点隐藏的深,是因为他们在广告逻辑的js隐藏角落里,动态创建了一个input,然后focus,然后将该input销毁,几乎不留任何痕迹
类似于下面的代码,这个是我看了他们的源码之后梳理出来的界面定位主逻辑
<body>
我是广告内容
<script>
/**
* 个人模拟的广告iframe代码,被外层主界面嵌套后,会把主界面拉到当前的位置
* 与主界面跨域的话也能实现效果
* 需要加异步,不加异步的话不行
*/
setTimeout(() => {
let myInput = document.createElement('input');
myInput.style.opacity = 0
document.body.appendChild(myInput);
myInput.focus();
document.body.removeChild(myInput)
}, 100)
</script>
</body>
如何防御
既然找到了问题,就想如何防御这个效果的出现,我们两个基于技术的角度想了一会,发现从技术角度上没法去防御这个问题,因为iframe是跨域的,主站也没有去写代码影响iframe的内容
于是乎,F君找到了公司商务,把事情的原委说了一下,让他们通过商务途径解决了这个问题
后记
我在工作中,也经常与合作方打交道,因为有利益共赢的关系,他们也会将内容、效率、安全、合规等工作内容做的很好,甚至很多方面比我们更专业
基于经验,我们心里多少会把他们认为自己人,从而放松一些
谁能想到,他们会有一些犯贱的动作,打着擦边球,做着损人利己的事情
前端安全,最重要是在防人心,防人之心不可无
现在换个角度一想,input获取焦点实现定位,这个技术思路获取可以在项目轻松实现一些正规的业务