`

javascript沙箱模式

 
阅读更多

沙箱模式常见于YUI3 core,它是一种采用同一构造器(Constructor)生成彼此独立且互不干扰(self-contained)的实例对象,而从避免污染全局对象的方法。

命名空间

JavaScript本身中没有提供命名空间机制,所以为了避免不同函数、对象以及变量名对全局空间的污染,通常的做法是为你的应用程序或者库创建一个唯一的全局对象,然后将所有方法与属性添加到这个对象上。

代码清单1 : 传统命名空间模式

01 /* BEFORE: 5 globals */

02 // constructors

03 function Parent() {}

04 function Child() {}

05 // a variable

06 var some_var = 1;

07 // some objects

08 var module1 = {};

09 module1.data = {a: 1, b: 2};

10 var module2 = {};

11 /* AFTER: 1 global */

12 // global object

13 var MYAPP = {};

14 // constructors

15 MYAPP.Parent = function() {};

16 MYAPP.Child = function() {};

17 // a variable

18 MYAPP.some_var = 1;

19 // an object

20 MYAPP.modules = {};

21 // nested objects

22 MYAPP.modules.module1 = {};

23 MYAPP.modules.module1.data = {a: 1, b: 2};

24 MYAPP.modules.module2 = {};

在这段代码中,你创建了一个全局对象MYAPP,并将其他所有对象、函数作为属性附加到MYAPP上。

通常这是一种较好的避免命名冲突的方法,它被应用在很多项目中,但这种方法有一些缺点。

需要给所有需要添加的函数、变量加上前缀。

因为只有一个全局对象,这意味着一部分代码可以肆意地修改全局对象而导致其余代码的被动更新。

全局构造器

你可以用一个全局构造器,而不是一个全局对象,我们给这个构造器起名为Sandbox(),你可以用这个构造器创建对象,你还可以为构造器传递一个回调函数作为参数,这个回调函数就是你存放代码的独立沙箱环境。

代码清单2:沙箱的使用

1 new Sandbox(function(box){

2     // your code here...

3 });

让我们给沙箱添加点别的特性。

1. 创建沙箱时可以不使用'new'操作符。

2. Sandbox()构造器接受一些额外的配置参数,这些参数定义了生成对象所需模块的名称,我们希望代码更加模块化。

拥有了以上特性后,让我们看看怎样初始化一个对象。

代码清单3显示了你可以在不需要‘new’操作符的情况下,创建一个调用了'ajax'和'event'模块的对象。

代码清单3:以数组的形式传递模块名

1 Sandbox(['ajax', 'event'], function(box){

2     // console.log(box);

3 });

代码清单4:以独立的参数形式传递模块名

1 Sandbox('ajax', 'dom', function(box){

2     // console.log(box);

3 });

代码清单5显示了你可以把通配符'*'作为参数传递给构造器,这意味着调用所有可用的模块,为了方便起见,如果没有向构造器传递任何模块名作为参数,构造器会把'*'作为缺省参数传入。

代码清单5:调用所用可用模块

1 Sandbox('*', function(box){

2     // console.log(box);

3 });

4  

5 Sandbox(function(box){

6     // console.log(box);

7 });

代码清单6显示你可以初始化沙箱对象多次,甚至你可以嵌套它们,而不用担心彼此间会产生任何冲突。

代码清单6:嵌套的沙箱实例

01 Sandbox('dom', 'event', function(box){

02     // work with dom and event

03     Sandbox('ajax', function(box) {

04     // another sandboxed "box" object

05     // this "box" is not the same as

06     // the "box" outside this function

07     //...

08     // done with Ajax

09     });

10     // no trace of Ajax module here

11 });

从上面这些示例可以看出,使用沙箱模式,通过把所有代码逻辑包裹在一个回调函数中,你根据所需模块的不同生成不同的实例,而这些实例彼此互不干扰独立的工作着,从而保护了全局命名空间。

现在让我们看看怎样实现这个Sandbox()构造器。

添加模块

在实现主构造器之前,让我们看看如何向Sandbox()构造器中添加模块。

因为Sandbox()构造器函数也是对象,所以你可以给它添加一个名为’modules'的属性,这个属性将是一个包含一组键值对的对象,其中每对键值对中Key是需要注册的模块名,而Value则是该模块的入口函数,当构造器初始化时当前实例会作为第一个参数传递给入口函数,这样入口函数就能为该实例添加额外的属性与方法。

在代码清单7中,我们添加了'dom','event','ajax'模块。

代码清单7:注册模块

01 Sandbox.modules = {};

02  

03 Sandbox.modules.dom = function(box) {

04     box.getElement = function() {};

05     box.getStyle = function() {};

06     box.foo = "bar";

07 };

08  

09 Sandbox.modules.event = function(box) {

10     // access to the Sandbox prototype if needed:

11     // box.constructor.prototype.m = "mmm";

12     box.attachEvent = function(){};

13     box.dettachEvent = function(){};

14 };

15  

16 Sandbox.modules.ajax = function(box) {

17     box.makeRequest = function() {};

18     box.getResponse = function() {};

19 };

实现构造器

代码清单8描述了实现构造器的方法,其中关键的几个要点:

1. 我们检查this是否为Sandbox的实例,若不是,证明Sandbox没有被new操作符调用,我们将以构造器方式重新调用它。

2. 你可以在构造器内部为this添加属性,同样你也可以为构造器的原型添加属性。

3. 模块名称会以数组、独立参数、通配符‘*’等多种形式传递给构造器。

4. 请注意在这个例子中我们不需要从外部文件中加载模块,但在诸如YUI3中,你可以仅仅加载基础模块(通常被称作种子(seed)),而其他的所有模块则会从外部文件中加载。

5. 一旦我们知道了所需的模块,并初始化他们,这意味着调用了每个模块的入口函数。

6. 回调函数作为参数被最后传入构造器,它将使用最新生成的实例并在最后执行。

代码清单8:实现Sandbox构造器

view source

print?

01 <script>

02 function Sandbox() {

03     // turning arguments into an array

04     var args = Array.prototype.slice.call(arguments),

05     // the last argument is the callback

06     callback = args.pop(),

07     // modules can be passed as an array or as individual parameters

08     modules = (args[0] && typeof args[0] === "string") ?

09     args : args[0],

10     i;

11     // make sure the function is called

12     // as a constructor

13     if (!(this instanceof Sandbox)) {

14         return new Sandbox(modules, callback);

15     }

16     // add properties to 'this' as needed:

17     this.a = 1;

18     this.b = 2;

19     // now add modules to the core 'this' object

20     // no modules or "*" both mean "use all modules"

21     if (!modules || modules === '*') {

22         modules = [];

23             for (i in Sandbox.modules) {

24                 if (Sandbox.modules.hasOwnProperty(i)) {

25                     modules.push(i);

26             }

27         }

28     }

29     // init the required modules

30     for (i = 0; i < modules.length; i++) {

31         Sandbox.modules[modules[i]](this);

32     }

33     // call the callback

34     callback(this);

35 }

36 // any prototype properties as needed

37 Sandbox.prototype = {

38     name: "My Application",

39     version: "1.0",

40     getName: function() {

41         return this.name;

42     }

43 };

44 </script>


分享到:
评论

相关推荐

    JavaScript 设计模式 安全沙箱模式

    沙箱模式常见于YUI3 core,它是一种采用同一构造器(Constructor)生成彼此独立且互不干扰(self-contained)的实例对象,而从避免污染全局对象的方法

    JavaScript模式中文[pdf] 百度云

     沙箱模式  静态成员  对象常量  链模式  method()方法  小结  第6章 代码复用模式  传统与现代继承模式的比较  使用类式继承时的预期结果  类式继承模式#1——默认模式  类式继承模式#2——借用构造函数...

    JavaScript模式 斯托扬·斯特凡洛夫 著

    沙箱模式 静态成员 对象常量 链模式 method()方法 小结 第6章 代码复用模式 传统与现代继承模式的比较 使用类式继承时的预期结果 类式继承模式#1——默认模式 类式继承模式#2——借用构造函数 类式继承模式#3——...

    DesignPatterns[removed]JavaScript设计模式

    JavaScript-Patterns some demos about JavaScript patterns 文件简介 singleton.js 单体模式 runobject.js ...沙箱模式 method.js 在Function对象上扩展method方法,从而更方便地扩展原型方法 instanceof.js

    iBen-js-framework

    iben js framework。javascript框架,采用沙箱模式加载模块,还在开发中。

    sval:用javascript编写的javascript解释器

    入侵模式和沙箱模式均可用 评估更高版本的ECMAScript的代码或在禁用eval , setTimeout和new Function的环境中评估代码很有用。 安装 节点 使用安装 。 npm install sval 浏览器 只需从。 或者,从下载,获得最小化...

    react-demo-app:用于React组件的沙箱

    这是使用Flux构建的React组件的沙箱。 所需的全局软件包: npm i webpack -g; npm i webpack-dev-server -g; 在克隆的根目录下安装本地软件包: npm i 安装后,从克隆的根目录运行webpack-dev-server 您的应用...

    本文件是涉及到javascript的高级部分学习,也就是难点部分的学习,之后我也会更新js的其他难点部分,感兴趣的小伙伴可以下载

    本文件主要涉及到:this指向问题,闭包,沙箱模式,函数柯里化,继承等知识点,适合已经学习完js基础的小伙伴(js基础可以去看我的前面的专栏:js每日一学),感兴趣的小伙伴可以下载下来自行阅读学习。 本文件是纯...

    sandbox-debugger:节点的沙箱调试器

    节点在调试模式下打开websocket时,沙盒服务器和客户端都通过代理通过管道传递websocket数据来工作。 运行沙箱服务器该服务器用作调试消息的关守。 npx sandbox-debugger-server 或者ᐅ docker run \ --name ...

    template.js:一个JavaScript模板引擎,简单,易用及其他功能,支持webpack,汇总,包裹,browserify,fis和gulp

    一款javascript模板引擎,简单,好用,支持webpack,汇总,包裹,browserify,fis和gulp特性JS原生语法,模版解析,编译,渲染支持所有浏览器及Node,支持TypeScript预编译支持主流打包工具自定义配置,修饰符,函数...

    vs没报错leetcode报错-sandbox:只是沙箱进行一些练习并尝试不同的技术

    只是我的个人沙箱来进行一些练习并尝试不同的技术。 参考书 算法和数据结构 HTTP Python C/C++ C# SQL 降价 HTML CSS JavaScript React 材料研究 算法和数据结构 HTML 和 CSS JavaScript Python C/C# 扩展,Python ...

    前沿沙箱:尝试前沿

    在开发模式下运行应用程序。 打开在浏览器中查看。 如果您在packages文件夹内进行更改,该站点将自动重新加载。 您将在控制台中看到构建错误。 看看我们的 创建您的自定义主题 npx frontity create-package your-...

    ObjectVsTask:使用 psiTurk 进行机械土耳其人实验

    对象与任务 描述 使用 psiTurk 进行的 Mechanical Turk 实验,用于检查对象表示与任务表示 快速开始 安装必要的元素。 您可以在查看我的自述。 本地测试。 确保您已更新config.txt文件... 打开服务器并在沙箱模式下hi

    ChromeStandaloneSetup64.exe

    Google Chrome支持多标签浏览,每个标签页面都在独立的“沙箱”内运行,在提高安全性的同时,一个标签页面的崩溃也不会导致其他标签页面被关闭。此外,Google Chrome基于更强大的JavaScript V8引擎,这是当前Web...

    nodember:全栈Javascript样板

    它演示了如何使用 Node 和 Ember、Express 和 MongoDB 制作全栈 JavaScript 应用程序。 架构是MVC-MVC和REST用于通信。 超越基础知识 Nodember 对 Web 开发中的常见需求以及它们在此堆栈中的实现方式进行了不断...

    codebox:通用代码沙箱

    HTML/JS 模式 Markdown 模式(也显示文档侧边栏) 使用: $ npm install$ npm install -g uglify-js$ npm install -g component$ component build -v && uglifyjs build/build.js -o build/build.min.js$ git ...

    di-modular:用于开发可扩展 JavaScript 应用程序的小型通用框架

    双模用于开发可扩展 JavaScript 应用程序的小型多功能框架。 DiModular 的灵感来自 Nicholas Zakas 提出的 ,也称为 Core-Module-Sandbox 模式。 但是,依赖注入容器不是“沙箱”,而是用于处理依赖关系和扩展核心...

    google chrome standalone enterprise msi

    快速 Google Chrome支持多标签浏览 每个标签页面都在独立的“沙箱”内运行 在提高安全性的同时 一个标签页面的崩溃也不会导致其他标签页面被关闭 此外 Google Chrome基于更强大的JavaScript V8引擎 这是当前Web...

    谷歌浏览器(Chromium) V19.0.1055.0 开发版

    Google Chrome支持多标签浏览,每个标签页面都在独立的“沙箱”内运行,在提高安全性的同时,一个标签页面的崩溃也不会导致其他标签页面被关闭。此外,Google Chrome基于更强大的JavaScript V8引擎,这是当前Web...

Global site tag (gtag.js) - Google Analytics