使用动态scritp标签解决跨域读数据的问题
来到TX后第一个比较正式的任务就是做一个活动页面。页面就不说了,活动页面嘛,那个线条啊只能大块大块地切图了。然后就是因为数据量并不多,所以采用了用静态页然后通过JS去读数据的做法。然后就碰到了跨域的问题了。
我想肯定有很多朋友也会碰到这样的情况,对方只给出一个链接让你去取数据,通过传递不同的参数,返回不同的数据。如果是在本域的话,用AJAX是很方便的,但AJAX不能跨域。而iframe的方法也不实用,只能跨小域,还需要在双方页面加相应的函数,页面里多了那么一块也让人感觉不舒服。所以决定用动态script标签的方法来解决这个问题。
在这里想说一句,国内的业内环境真是…,网上查出来的技术文章几乎都是同样的几篇转来转去,而且也说得不清不楚的很费解。还是BI上环境好些,呵呵。下面的代码并非我原创,也是参考来的,但我一定讲解清楚,让每一个看这文章的人都能明白具体是如何实现的。
由于浏览器安全的问题,一些跨域的请求都会被拒绝,当然,你也可以设置为添加到信任站点就能访问,但你不可能要求你的每个用户都去这样添加。但是,也有个例外,JS是可以跨域的,比如说我们用jquery的时候,可以加载code.google.com里面的jquery包,同样也能应用到jquery的框架;再比如说一些流量统计的代码,都是加一段JS在页面,我们就能应用到写在里面的函数了。所以,当我们把我们所以跨域读取的地址写在script标签的src里的时候,不管是什么后缀名的文件,都会被当做一个JS来读取。所以呢,这个页面的输出要采用JS的格式。
在这里先说两点,第一是这个方法名字虽然是叫动态script标签,但是你静态地直接写在页面里也是可以的,前提是你不需要动态地传递参数;第二是在很多文章里会把此方法跟json扯上关系,其实这跟json没有任何关系,只是因为用json来处理某些返回值时比较方便罢了。下面还是用json格式的来说明好了,因为这样的应用可能会比较多一点。
首先我们新建一个页面,可以是ASP、PHP或者CGI,或者TXT也都可以,但是让他的输出像这样:
var MyJSON = { 'info': [{'name' : 'moondy','sex' : '男','age' : '28'}] };
这里定义了一个json,你也可以这样定义:
var name="moondy"; var sex="男"; var age="28";
喜欢怎样写就怎样写了,只是在有多组数据的时候,用json比较方便了。关键是要用var ,这样才能当做一个JS的变量来读取,此方法的主要思想,就是在你的页面动态地加入了一句变量的定义,而你就可以直接在JS中引用这个变量了。下面是JS部分:
var element = document.createElement("script"); function createScript(compId,dataId){ element.src = "http://www.moondyzone.com/json.php";//这里是你需要跨域读取的URL element.type = "text/javascript"; element.language = "javascript"; } function writeContent(){ alert(MyJSON[0].name);//可以看到读取了相应的数据,json的操作跟数组类似了。这里就可以直接读取上面var定义的变量了。 } window.onload = function(){ createScript(1,2);//这里的这个参数是在需要动态传递参数的时候用的,本例中没有用到,看具体的需要了。 document.getElementsByTagName("head")[0].appendChild(element); } if(document.all){ element.onreadystatechange = function(){//IE用 var state = element.readyState; if (state == "loaded" || state == "interactive" || state == "complete") { writeContent(); } }; } else { element.onload = function() {//FF用 writeContent(); }; }
在这里就没有做DEMO了,本人在实际项目中应用都没有问题的了。另外也可以跟据不同的需求进行修改,比如说例子中element.onreadystatechange 是在加载完成后运行,可以自行改为点击触发之类的也都可以咯。不过有一点要注意,动态改变外域的URL时需要刷新页面,直接重写script标签中的src在IE中会读不到。
4条留言 立即发表评论
JSONP
Moondy兄,这样做是有内存泄漏的…
多谢天堂兄啦。的确是存在着问题,但在服务端处理得好的话是不会有安全问题的。哎,这本身就是一个头疼的问题
小弟有抄一些资料…
http://lixinlixin2008.javaeye.com/blog/461294