简体   繁体   English

抽象JavaScript库的最佳方法是什么?

[英]The best way to abstract a JavaScript library?

What would be the best way to abstract away any given JavaScript framework (jQuery, MooTools etc.), that sits on the bottom of the framework stack? 什么是抽象出任何给定的JavaScript框架(jQuery,MooTools等)的最佳方法,它位于框架堆栈的底部? Essentially, I would like to have a situation where I could swap out the library, do changes only to one layer of the framework (not to every module, for example), and the whole thing could be up and running again. 从本质上讲,我希望有一种情况,我可以换出库,只对框架的一层进行更改(例如,不对每个模块进行更改),整个过程可能会重新启动并运行。

So, every module should call a framework function(s), which would then be routed to the library. 因此,每个模块都应调用一个框架函数,然后将其路由到库中。

You may want to use something like the Adapter Pattern . 您可能想要使用适配器模式之类的东西。 Create your own interface, exposing the methods that you will be using in your application, and then create an adapter for each toolkit that you would like to support (jQuery, MooTools, YUI, etc). 创建您自己的界面,公开您将在应用程序中使用的方法,然后为您想要支持的每个工具包(jQuery,MooTools,YUI等)创建一个适配器。 Your own interface would then route the method calls to the specific adapters. 然后,您自己的接口将方法调用路由到特定适配器。

If you were to support a new toolkit, all you'd have to do is to write a new adapter that translates methods from your own interface, to the methods of the specific toolkit. 如果您要支持新的工具包,那么您所要做的就是编写一个新的适配器,将您自己的接口中的方法转换为特定工具包的方法。

This is something that Ext JS currently does. 这是Ext JS目前所做的事情。 You can choose which adapter to use (jQuery, YUI, etc) behind the method calls of the framework. 您可以选择在框架的方法调用后面使用哪个适配器(jQuery,YUI等)。 For example: Ext.getCmp() would use the jQuery.$() when using the jQuery adapter. 例如: Ext.getCmp() jQuery.$()在使用jQuery适配器时将使用jQuery.$() However, it is often not a very easy one-to-one mapping. 但是,它通常不是一个非常简单的一对一映射。

Ext JS started its life as an extension to the Yahoo UI javascript library. Ext JS开始作为Yahoo UI javascript库的扩展。 At that time, Ext relied on YUI for all of its low-level cross-browser code. 那时,Ext依赖于YUI的所有低级跨浏览器代码。 Now that Ext is a standalone JavaScript library, you have the choice of substituting YUI for other JavaScript libraries such as Prototype, or jQuery. 现在Ext是一个独立的JavaScript库,您可以选择将YUI替换为其他JavaScript库,例如Prototype或jQuery。 The source files that map the low-level Ext API around other JavaScript libraries (or Ext's own base library) are known as adapters and they live in the source/adapter subdirectory. 将低级Ext API映射到其他JavaScript库(或Ext自己的基本库)的源文件称为适配器,它们位于源/适配器子目录中。 When you include Ext in your website you choose which adapter you want to use. 当您在网站中包含Ext时,您可以选择要使用的适配器。

From: Ext JS Manual: Source Overview 来自: Ext JS手册:来源概述

This would be writing a library for...libraries, if you are concerned about performance at all (and why wouldn't you be?) you should go a different route altogether. 这将是为...库编写一个库,如果你完全关心性能(为什么不是你?)你应该完全采用不同的方法。 Another abstraction layer on top of libraries with very different approaches (especially when you get into utilities, animations, etc.) would be very, very inefficient and time consuming. 库之上的另一个抽象层具有非常不同的方法(特别是当您进入实用程序,动画等时)将非常非常低效且耗时。

No kidding, it'd take you less time to port your code several times even in any decent size project before building (or more importantly, maintaining) a library abstraction layer like this would. 不开玩笑,在构建(或更重要的是,维护)像这样的库抽象层之前,即使在任何体面的大小项目中,也需要花费更少的时间来移植代码。

You will have to write adapters for each toolkit/library you might want to use for your framework, pretty much like ExtJS/Sencha has done (though theirs are probably not reusable). 您将不得不为您可能想要用于框架的每个工具包/库编写适配器,就像ExtJS / Sencha所做的那样(尽管它们可能不可重用)。

Start out by mapping out what methods your adapter should have, it will act as your frameworks low level API. 首先绘制出适配器应该具有的方法,它将作为框架的低级API。

Next step is to write an adapter for each possible toolkit/library. 下一步是为每个可能的工具包/库编写一个适配器。 Some libraries will be hard to write adapters for like YUI, since they load code dynamically. 有些库很难为YUI编写适配器,因为它们会动态加载代码。 You might have to compile a single .js file with needed functionality first. 您可能必须首先编译具有所需功能的单个.js文件。

Add a new toolkit/library, write a new adapter according to your mapping. 添加一个新的工具包/库,根据您的映射编写一个新的适配器。

This may have been a reasonable idea if the frameworks had equivalent functionality. 如果框架具有相同的功能,这可能是一个合理的想法。 Unfortunately they don't; 不幸的是他们没有; they do different things, and they do them differently. 他们做不同的事情,他们做的不同。 There is cross-over between them, but your wrapper would miss out on a lot because you'd only be able to do your wrapping on stuff that was in both. 它们之间有交叉,但你的包装器会错过很多,因为你只能对两者中的东西进行包装。 You'd end up with the lowest common denominator; 你最终会得到最低的共同点; the worst of both worlds. 两个世界中最糟糕的。

My advice is to take the time to learn both libraries - MooTools and JQuery are both very good libraries, and it's good to know them both. 我的建议是花时间学习两个库 - MooTools和JQuery都是非常好的库,并且知道它们两者都很好。 Even if you then only use one of them in your project, you will at least be able to make an informed choice before you start. 即使您只在项目中使用其中一个,您至少也可以在开始之前做出明智的选择。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM