Flash跨域的完全解決方案
什麼是跨域?跨域簡單的說就是訪問其他域名的檔案或資源,比如a.com的Flash去訪問b.com的資源,那麼就會引起跨域的問題,因為a.com和b.com不是同一個域名。
為什麼有跨域問題?其實不僅僅是Flash,Javascript等一些指令碼也有跨域的問題,這個主要是自身的安全機制所決定的,因為跨域訪問一些檔案或資源有一定的危險性,他超過了網站自身的範圍,對於站外的資源無法稽核其安全性,在網路病毒木馬日益猖獗的今天,跨域限制訪問是其安全策略的一個重要解決手段。
跨域有什麼問題?跨域的問題有很多,最直接的就是所訪問的檔案被限制了,這樣一來,你的Flash就不能正常工作了,所以是讓人很頭疼的一件事情。
現在的Flash已經不僅僅是作為一個動畫了,更多的有了資料互動,所以和外界的通訊來作為一個互動性比較強的媒介來展現,跨域也是其中必須解決的一個問題。
恩,那也許有人說了,既然有跨域的問題,那我把資源都放在同一個域名下不就可以了?恩,的確可以這樣做,但是有時候我們也會遇到訪問外部資源的情況,而且在一個比較正規的專案中,Flash和Html往往是分開放的,很多公司也是這樣,為了便於維護和管理,所以跨域的問題就容易出現。
囉嗦一大堆,下面,就從我實際的專案中來告訴大家該怎樣解決跨域問題,相信有了此文,大家今後再遇到跨域問題就能迎刃而解了。
1 Flash自身的安全機制設定
Flash中,在IDE執行是沒有任何安全限制的,但是釋出出去的話,就會有不少限制,Flash有2中釋出方式,一個是僅訪問網路,一個是僅訪問本地,大家可以在檔案-釋出設定-Flash選項卡中看到,注意必須是在Fla檔案有效時才會有哦,如果當前編輯的是as檔案是木有這個選擇選單的:
這裡就已經限制了Flash的安全級別,如果是隻訪問本地,那麼Flash中所有的對Web的訪問都將禁止,而只訪問網路的話,對本地的檔案訪問都將禁止,所以大家根據實際的用途來選擇,如果你希望你的Flash放到Web上,那麼就選擇只訪問網路,這樣的話你測試就務必放在WebService中測試了,本地執行就會出現各種問題(如果有資料通訊的話),例如:測試URL http://127.0.0.1/123.swf
2 ActionScript程式碼設定:
這裡我就曾經被絆了幾個小時,大家要注意一下,AS2和AS3是不太一樣的
AS2寫法:System.security.allowDomain("*");//針對不同http資源
System.security.allowInsecureDomain("*");//針對需要安全驗證的資源,比如https
AS3寫法:flash.system.Security.allowDomain("*");
flash.system.Security.allowInsecureDomain("*");
上面就是嚴格的寫法,AS3還好說,大家要注意一下AS2,AS2是木有flash.system這個包的,但是你import flash.system並不會報錯,所以如果你把AS3的程式碼複製進去執行雖然一切正常,但是實際是木有任何效果的。一定要注意!
上面的程式碼就是說允許URL下的某些程式(swf,js等)去訪問swf中的介面和函式,如果只想讓特定的URL訪問,就把*改成該URL即可,如果多個URL,就用逗號分隔就可以了,注意allowInsecureDomain是允許帶驗證的URL程式去訪問,比如https打頭的,如果你只是普通http下的訪問的話就不需要了。
3 html的設定:
如果你需要和頁面的JS通訊,那麼html裡就必須有這樣一個引數:
<param name="allowScriptAccess" value="always" />
引數always表示始終允許指令碼訪問,如果是never,就表示始終不允許
4 載入外部資源:
如果你要讀取一個外部檔案,比如swf,picture,mp3等等,那麼就需要一個跨域策略檔案,這個其實就是一個xml檔案,具體內容是:
<?xml version="1.0"?>
<cross-domain-policy>
<allow-access-from domain="www.123.com" />
<allow-access-from domain="*.myhome.com" />
</cross-domain-policy>
這就是跨域策略檔案,allow-access-from domain表示允許訪問的URl,如果有多個依次新增,如果允許所有就一個 allow-access-from domain = "*"就可以了
需要說明一下這個檔案該怎麼用,如果你的Flash在a.com下,你需要訪問b.com的資源,那麼把這個xml放在b.com的根目錄就可以自動訪問了,當然,你也可以訪問其他目錄的策略檔案。
flash.system.Security.loadPolicyFile(URL:String)
通過這個loadPolicyFile就可以主動去載入一個安全策略檔案了,注意上面是AS3的寫法,AS2不一樣哦,參考上面的寫法。
5 各個瀏覽器的跨域問題:
IE就不說了,這個基本沒啥問題,包括Flash自己生成的Html就對IE的支援做的很好,這裡就說說Chrome和FF的問題:
在前面一個文章裡,我說了對於FLash,IE是認object標籤的,但是FF和Chrome是認embed標籤的,所以這個很重要,如果在除錯的時候,發現firebug等工具提示"...... is not a Function",我們就要從以下地方查詢原因:
1 addCallback是否成功註冊
2 allowScriptAccess是否允許always,預設不允許
3 Flash是否完全載入完畢
一般來說,第三點是我們最容易遇到的,如果你的Flash沒有載入完畢就去呼叫函式的話,是找不到這個函式的,解決方法請參考前一篇文章。
這裡需要注意另外一個錯誤提示,就是"Error calling method onNPObject",如果出現這個錯誤,就要小心了:
1 安全策略問題,請參考上面所有的解決方案
2 自身函式錯誤
如果排除了所有的安全策略問題還是出現這個錯誤,那麼就可能是所呼叫的函式內部出現了錯誤,我們可以用個空函式來檢查問題,如果空函式沒有問題,就一步步查詢究竟函式體內哪裡出現問題了。
以上就是跨域安全策略所能遇到的大部分問題,都具有代表性,也是工作中經常遇到了,希望大家都能夠解決這樣一個頭疼的問題。