代码之家  ›  专栏  ›  技术社区  ›  Vivin Paliath

编写代码完成和代码检查友好的javascript库

  •  3
  • Vivin Paliath  · 技术社区  · 15 年前

    我最近创建了自己的javascript库,最初使用了以下模式:

    var myLibrary = (function () {
    
      var someProp = "...";
    
      function someFunc() {
        ...
      }
    
      function someFunc2() {
        ...
      }
    
      return {
         func: someFunc,
         fun2: someFunc2,
         prop: someProp;
      }
    
    }());
    

    问题是我不能真正使用代码完成,因为ide不知道函数literal返回的属性(顺便说一下,我正在使用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也有同样的问题。不过,我在其他项目中似乎没有这个问题。

    5 回复  |  直到 14 年前
        1
  •  3
  •   kodisha    15 年前

    我使用的想法与雅虎模块模式和我的自动完成工作。谷歌雅虎模块模式。

    http://www.yuiblog.com/blog/2007/06/12/module-pattern/

    http://ajaxian.com/archives/a-javascript-module-pattern


    TEST = function() {
        var SOME_CONSTANT='asd';
    
        function privateStuff(){
            var a = 'asd';
            return a;
        }
    
        return{
            someArray:[],
    
            someMethod: function(foo, bar){
    
                var foo = *1
            }
            ,
    
            myProperty:'test'
        }
    }();
    
    TEST.*2
    

    我用*1和*2标记了我尝试自动完成的地方。

    在*1中,我得到了一些_constant和privatestuff方法,如果我把它放在这里(autocomplete),我就可以访问return{}块中的所有方法和属性。

    当我在*2上尝试自动完成时,我得到了return{}块中的所有方法和属性。 有些_常量和privatestuff方法在那里是不可见的,因为它们是“私有的”。

    对我来说,自动完成的水平相当不错。

        2
  •  1
  •   nahum silva    15 年前

    我想如果你读到一些关于道格拉斯·克罗克福德的东西会很好。他是雅厚御框架的建筑师。在那之后,你可以更好地了解如何构建一个伟大的框架。对于参数有两个选项。1.-通过对象示例发送

    { option :{ var1 : "value" , var2:"value"}, var3 : "value" }
    

    你可以检查这个选项是否存在。

    第二个不好的是检查参数是否未定义。

    function foo(var1,var2){
       var var1_this = null;
         if(var1 != undefined)
          var1_this = var1;
    }
    

    还有一个评论为什么要构建一个新的javascript框架?使用prototype、jquery、mootols、yui。为什么要重新发明轮子?

        3
  •  1
  •   Community CDub    8 年前

    这是对 mwilcox's post .

    这个例子实际上是可行的。自从 myLibrary 定义时没有 var ,它将自动放入全局命名空间中,并可作为全局命名空间进行访问。通过自执行函数创建的闭包,私有变量和方法仍然可以在 MyLabor 方法。你可以把它放进萤火虫或犀牛身上试试。

    现在,我不倾向于隐藏我的变量,即我使用伪经典模式或原型模式并在 打算 带有 _ :

    // Pseudoclassical pattern
    function Hello() {}
    Hello.prototype = {
        method1: function() {},
        method2: function() {},
        _pseudeoPrivate: function() {}
    };
    
    /* Prototypal pattern. To create multiple instances of this object,
       you need a helper function such as
        function beget(o) {
            var F = function() {};
            F.prototype = o;
            return new F;
        }
        var instance = beget(world);
    */
    var world = {
        method1: function() {},
        method2: function() {}
    };
    

    为了防止代码污染全局命名空间,我有一个构建过程,它将模块包装在一个闭包中,并将公共api导出到命名空间。jquery也使用这种技术。你可以在他们的源代码(看intro.js&outro.js)中看到 Github .

    这将允许您使用允许ide(或带有vim的ctag)查看api的模式,同时还可以防止全局名称空间的污染。

        4
  •  0
  •   Felix    15 年前

    我的图书馆是这样写的:

    function MyLibrary() {
        // code
    }
    MyLibrary.prototype.memberFunc = function() {
        // code
    }
    MyLibrary.prototype.memberVar = 5;
    
    new MyLibrary();
    

    这样,在geany(使用ctag) MyLibrary 被很好地识别(例如,在大多数情况下,membervar被识别为一个函数)并且自动完成似乎起作用。我不知道IDEA9,但你可以这样试试(我有预感它比CTAG更进化一些)。

        5
  •  0
  •   mwilcox    15 年前

    我建议您不要使用私有变量,但我知道您希望将它们隐藏起来,不让intellisense知道。我就是这样做的:

    (function(){
        var privateVar = "shhhh!";
        var privateMethod = function(){}
    
    
        myLibray = {
            prop:42,
            foo: function(){
                return privateMethod()
            },
            bar: function(){
                return privateVar;
            }
        }
    
    })();
    

    这样你就可以在一个封闭的私人物品和你的图书馆应该是可访问的。

    [编辑]。我笨拙地没有将mylibrary包含在匿名函数中,并且它看不到私有变量。哎呀。]

    顺便说一下,我认为私有变量不好的原因是: http://clubajax.org/javascript-private-variables-are-evil/