深入理解Flash Player的应用程序域(Application Domains)(5)
Separate Domains: Preventing Conflicts 域分离:避免冲突
某些情形下,你可能不希望加载的子SWF内容被父应用程序域里的定义继承关系所影响。因为有可能你甚至不知道父域中存在哪些定义。不论哪种情况,最好都要避免主SWF和子SWF中的定义共享。在这种情况下,应该把子SWF的定义放到新的系统域的子域下。
系统域下的不同子应用程序域
由于父SWF和子SWF的定义之间没有继承关系,所以这时候即使存在相同的定义也不会引起冲突,因为二者属于不同的沙箱。
举个例子:比如你有个培训程序,通过加载外部SWF来代表不同的培训模块。这个程序已经有些年头了,许多开发者开发了成百上千个培训模块。这些模块,甚至培训主程序自身都是基于不同版本的基础代码库进行开发。所以主程序要保证自己使用的基础代码库不会对其他模块造成不兼容的情况。这就必须把这些培训模块加载到他们独立的系统域下的子域,而不是把他们加载到主应用程序域的子域下面。
trainingapplication.swf:
var moduleLoader:Loader = new Loader(); addChild(moduleLoader); // 把模块加载到系统域的子域下,与当前的应用程序域区分开 function loadModule(url:String):void { var context:LoaderContext = new LoaderContext(); context.applicationDomain = new ApplicationDomain(); moduleLoader.load(new URLRequest(url), context); }
不足的是,这种定义的划分方式还不是完全隔离的。由于在同一个安全域下的内容都处于一个相同的系统域下,任何对系统域内定义的修改都将影响同一个安全域下的所有应用程序域。即使是将子SWF加载到一个单独的系统域的子域下,父SWF对系统域的更改还是会对其造成影响。
我们可以通过改动XML.prettyIndent属性来验证这一点:不管处于应用程序域层级的哪个SWF对系统域里的定义作出改变,都会影响到相同安全域下的所有文件。
parent.swf:
trace(XML.prettyIndent); // 2 XML.prettyIndent = 5; trace(XML.prettyIndent); // 5 var loader:Loader = new Loader(); var context:LoaderContext = new LoaderContext(); // 新建一个独立的应用程序域 context.applicationDomain = new ApplicationDomain(); var url:String = "child.swf"; loader.load(new URLRequest(url), context);
child.swf:
trace(XML.prettyIndent); // 5
所以最佳实践是对定义做的改动应该在使用后及时还原,这样可以避免对其他文件的影响。
var originalPrettyIndent:int = XML.prettyIndent; XML.prettyIndent = 5; trace(myXML.toXMLString()); XML.prettyIndent = originalPrettyIndent;
同样的,你也必须留心类似这样的值有可能在你的程序之外被人所改动。
热门文章推荐
- [HLS]做自己的m3u8点播系统使用HTTP Live Streaming(HLS技术)
- [FMS]FMS流媒体服务器配置与使用相关的介绍
- [AS3]什么是M3U8,与HTML5的区别是什么
- AS2.0 让flash自适应全屏,并且不自动缩放
- [AS3]as3.0的sound类常用技巧整理
- [AS3]as3与ByteArray详解、ByteArray介绍、ByteArray用法
- 关于RTMP,RTMPT,RTMPS,RTMPE,RTMPTE协议的介绍
- [JS]分享浏览器弹出窗口不被拦截JS示例