编写一个代码完成和代码检查友好的 Javascript 库
我最近制作了自己的 Javascript 库,最初使用了以下模式:
var myLibrary = (function () {
var someProp = "...";
function someFunc() {
...
}
function someFunc2() {
...
}
return {
func: someFunc,
fun2: someFunc2,
prop: someProp;
}
}());
这样做的问题是我无法真正使用代码完成,因为 IDE 不知道函数文字返回的属性(我正在使用顺便说一下 IntelliJ IDEA 9)。
我查看了 jQuery 代码并尝试执行此操作:
(function(window, undefined) {
var myLibrary = (function () {
var someProp = "...";
function someFunc() {
...
}
function someFunc2() {
...
}
return {
func: someFunc,
fun2: someFunc2,
prop: someProp;
}
}());
window.myLibrary = myLibrary;
}(window));
我尝试了此操作,但现在我遇到了不同的问题。 IDE 也没有真正识别 myLibrary
。
我现在解决问题的方法是这样的:
var myLibrary = {
func: function() { },
func2: function() { },
prop: ""
};
myLibrary = (function () {
var someProp = "...";
function someFunc() {
...
}
function someFunc2() {
...
}
return {
func: someFunc,
fun2: someFunc2,
prop: someProp;
}
}());
但这看起来有点笨拙,而且我无法确切地弄清楚 jQuery 是如何做到这一点的。我的另一个问题是如何处理具有任意数量参数的函数。
例如,jQuery.bind
可以采用 2 或 3 个参数,并且 IDE 似乎没有抱怨。我尝试对我的库做同样的事情,其中一个函数可以采用 0 个参数或 1 个参数。但是,IDE 会抱怨并警告未发送正确数量的参数。我该如何处理这个问题?
编辑
我开始怀疑这是否是 Idea9 问题,因为 jQuery 也有同样的问题。不过我在其他项目中似乎没有这个问题。
I recently made my own Javascript library and I initially used the following pattern:
var myLibrary = (function () {
var someProp = "...";
function someFunc() {
...
}
function someFunc2() {
...
}
return {
func: someFunc,
fun2: someFunc2,
prop: someProp;
}
}());
The problem with this is that I can't really use code completion because the IDE doesn't know about the properties that the function literal is returning (I'm using IntelliJ IDEA 9 by the way).
I've looked at jQuery code and tried to do this:
(function(window, undefined) {
var myLibrary = (function () {
var someProp = "...";
function someFunc() {
...
}
function someFunc2() {
...
}
return {
func: someFunc,
fun2: someFunc2,
prop: someProp;
}
}());
window.myLibrary = myLibrary;
}(window));
I tried this, but now I have a different problem. The IDE doesn't really pick up on myLibrary
either.
The way I'm solving the problem now is this way:
var myLibrary = {
func: function() { },
func2: function() { },
prop: ""
};
myLibrary = (function () {
var someProp = "...";
function someFunc() {
...
}
function someFunc2() {
...
}
return {
func: someFunc,
fun2: someFunc2,
prop: someProp;
}
}());
But that seems kinda clunky, and I can't exactly figure out how jQuery is doing it. Another question I have is how to handle functions with arbitrary numbers of parameters.
For example, jQuery.bind
can take 2 or 3 parameters, and the IDE doesn't seem to complain. I tried to do the same thing with my library, where a function could take 0 arguments or 1 argument. However, the IDE complains and warns that the correct number of parameters aren't being sent in. How do I handle this?
EDIT
I'm starting to wonder if this is an Idea9 issue because jQuery has the same problem. I don't seem to have this problem in other projects though.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
我正在将 IDEA 与 yahoo 模块模式一起使用,并且我的自动完成功能有效。 Google for yahoo 模块模式。
http://www.yuiblog.com/blog/2007/06 /12/module-pattern/
http://ajaxian.com/archives /a-javascript-module-pattern
与 *1 和 *2 我标记了我尝试自动完成的地方。
在 *1 中,我得到 SOME_CONSTANT 和 privateStuff 方法,如果我将其放入。(自动完成),当我在 *2 上尝试自动完成时,我可以访问 return {} 块内的所有方法和属性,
我将获得 return {} 块内的所有方法和属性{} 堵塞。
SOME_CONSTANT 和 privateStuff 方法在那里不可见,因为它们是“私有的”。
对我来说,自动完成的水平相当不错。
I'm using IDEA with yahoo module pattern and my autocomplete works. Google for yahoo module pattern.
http://www.yuiblog.com/blog/2007/06/12/module-pattern/
http://ajaxian.com/archives/a-javascript-module-pattern
with *1 and *2 i marked places where i tried auto complete.
in *1 i get SOME_CONSTANT and privateStuff method, and if i put this.(autocomplete) i get access to all the methods and properties inside of return {} block
when i try autocomplete on *2 i get all the methods and properties inside return {} block.
SOME_CONSTANT and privateStuff method are invisibile there, because they are "private".
For me that level of autocomplete is quite fine.
我想如果你读到一些关于道格拉斯·克罗克福德的文章将会很棒。他是yahou YUI框架的架构师。之后,您可以更好地了解如何构建出色的框架。对于参数有 2 个选项。 1.- 通过对象发送示例
并且您可以检查该选项是否存在。
第二个不太好的是检查参数是否未定义。
只是评论为什么要构建一个新的 javascript 框架?使用 Prototype、JQuery、Mootols、YUI。为什么要重新发明轮子?
I think will be great if you read something about Douglas Crockford. He is THE architect in yahou YUI framework. And after that you can have a better idea to how build a great framework. And for the parameter there are 2 options. 1.- send via object example
And the you can check if the option exist.
The second one not to great is check if the parameter is undefined.
and just a comment why build a new javascript framework? use Prototype, JQuery, Mootols, YUI. why reinventing the wheel?
这是对 mwilcox 的帖子。
这个例子实际上会起作用。由于
myLibrary
是在没有var
的情况下定义的,因此它会自动放入全局命名空间中并可以这样访问。通过自执行函数创建的闭包,私有变量和方法仍然可以在myLibrary
方法中访问。您可以通过将其放入 Firebug 或 Rhino 中轻松地进行尝试。这些天,我不倾向于隐藏我的变量,即我使用伪经典模式或原型模式,并在我的预期私有方法前加上
_
:以防止我的代码为了避免污染全局命名空间,我有一个构建过程,它将我的模块包装在一个闭包中,并将公共 api 导出到命名空间。 jQuery 也使用了这种技术。您可以在
这将允许您使用一种模式,允许您的 IDE(或带有 vim 的 ctags)查看您的 api,同时还可以防止全局命名空间的污染。
This is in reply to the comments to mwilcox's post.
That example will actually work. Since
myLibrary
is defined withoutvar
, it is automatically put into the global namespace and accessible as such. Through the closure created by the self-executing function, the private variables and methods are still accessible in themyLibrary
methods. You can easily try this out by putting it into Firebug or Rhino.These days, I do not tend to hide my variables, i.e. I use the Pseudoclassical pattern or the Prototypal pattern and prefix my intended private methods with an
_
:To prevent my code from polluting the global namespace, I have a build process that wraps my modules in a closure and exports the public api to the namespace. This technique is also used by jQuery. You can see that in their source code (look at intro.js & outro.js) on Github.
This would allow you to use a pattern that allows your IDE (or ctags with vim) to see your api, whilst also preventing the pollution of the global namespace.
我这样编写我的库:
这样,在 Geany(使用 CTAGS)中,
MyLibrary
被很好地识别(例如,在大多数情况下,memberVar 被识别为函数)并且自动完成似乎可以工作。我不了解 IDEA9,但你可以尝试这种方式(我有预感它比 CTAGS 更先进一点)。I write my libraries like this:
This way, in Geany (which uses CTAGS)
MyLibrary
is well recognized (for the most part, for example, memberVar is recognized as a function) and autocompletion seems to work. I don't know about IDEA9, but you could try it this way (I have a hunch it's a bit more evolved than CTAGS).我建议您不要使用私有变量,但我知道您希望它们对智能感知隐藏。我就是这样做的:
这样你就可以将你的私人物品放在一个闭包中,并且你的图书馆应该可以访问。
[编辑。我笨拙地没有将 myLibrary 包含在匿名函数中,它看不到私有变量。哎呀。 ]
顺便说一句,我的私有变量不好的原因: http://clubajax.org/ javascript-private-variables-are-evil/
I recommend that you don't use private variables, but I understand you want them hidden from the intellisense. This is how I would do it:
This way you can have your private stuff in a closure and your library should be accessible.
[ edited. I clumsily did not include myLibrary in the anonymous function and it could not see the private vars. oops. ]
BTW, my reasons for private variables being bad: http://clubajax.org/javascript-private-variables-are-evil/