3

Недавно я сделал свою собственную библиотеку 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 жалуется и предупреждает, что правильное количество параметров не отправляется. Как мне это сделать?

EDIT

Я начинаю задаваться вопросом, является ли это проблема, потому что Idea9 JQuery имеет те же проблемы. Однако у меня, похоже, нет этой проблемы в других проектах.

+2

Я знаю, правильно? Мы все должны кодироваться в сборке! Вверните все остальное! –

+0

Я уверен, что это его личная библиотека. – mwilcox

+0

На самом деле это основа проверки, которая использует другой подход - аннотации через пользовательские атрибуты (которые действительны в HTML5). Экспериментальная и доказательная концепция. –

ответ

3

Я использую IDEA с шаблоном модуля yahoo, и мои автозаполнения работают. Google для шаблона модуля yahoo.

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 я получить SOME_CONSTANT и метод privateStuff, и если я ставлю это. (Автозаполнение) я получить доступ ко всем методам и свойствам внутри возврата {} блок

при попытке автозаполнение на * 2 I получить все методы и свойства внутри return {} block. Метод SOME_CONSTANT и privateStuff там невидим, потому что они «частные».

Для меня этот уровень автозаполнения вполне подходит.

+0

Пример кода OPs уже использует шаблон модуля. –

+0

Я действительно не видел его возвращения {} блоков :). Я отредактировал свой ответ. – kodisha

+0

Не решает мою проблему (это может быть проблема с идеей), но она, как правило, отвечает на мой вопрос! :) –

0

Я рекомендую не использовать частные переменные, но я понимаю, что вы хотите, чтобы они были скрыты от 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/

+0

Это работает? Не исчезнут ли локальные вары в закрытии после? –

+0

Я не уверен, как это сработает.'privateVar' и' privateMethod' не будут доступны для 'myLibrary', не так ли? –

+0

Это не сработает. 'privateVar' и' privateMethod' будут в их собственном маленьком мире; ничто не сможет получить к ним доступ. – Matt

1

Я думаю, будет здорово, если вы читали что-то о Дуглас Crockford. Он архитектор в структуре yahou YUI. И после этого вы сможете лучше понять, как построить отличную инфраструктуру. А для параметра есть 2 варианта. 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. зачем изобретать колесо?

+0

Возможно узнать. То есть, когда изобретать колесо хорошо. –

+0

также не забывайте, что ваше приложение должно использовать Prototype, jQ и прочее для материалов низкого уровня, если вы пишете новые, скажем, визуализацию фреймворка, вы должны использовать Prototype в качестве базовой фреймворка, а все диаграммы и прочее должны быть в другом FW, который построен поверх прототипа, jQ и т. Д. – kodisha

+0

Да, я не пытаюсь изобретать колесо до jQuery или Prototype. Я работал над системой проверки. –

0

Я пишу свои библиотеки, как это:

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

new MyLibrary(); 

Таким образом, в Geany (который использует Ctags) MyLibrary хорошо известен (по большей части, к примеру, memberVar распознаются как функция) и автодополнение похоже работа. Я не знаю об IDEA9, но вы можете попробовать это так (у меня есть подозрение, что это немного более развито, чем CTAGS).

+0

Я тоже видел этот узор. Существуют ли какие-либо преимущества для этого метода по сравнению с одноэлементным шаблоном? –

+0

Возможность использования нескольких экземпляров одного и того же объекта? :) Кроме того, код является намного более читаемым ИМО. – Felix

+0

Конечно :) Мне интересно, если бы в этом случае было бы иметь несколько экземпляров! Я буду продолжать работать над этим, чтобы выяснить, что происходит. –

1

Это ответ на комментарии к mwilcox's post.

Этот пример на самом деле будет работать. Поскольку myLibrary определен без var, он автоматически помещается в глобальное пространство имен и доступен как таковой. Через закрытие, созданное функцией самоисполнения, частные переменные и методы по-прежнему доступны в методах myLibrary. Вы можете легко попробовать это, поставив его в Firebug или Rhino.

В эти дни, я не склонен скрывать свои переменные, то есть я использую псевдоклассической шаблон или прототипичный шаблон и префикса моего предназначен частные методы с _:

// 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() {} 
}; 

Чтобы предотвратить мой код из загрязняя глобальное пространство имен, у меня есть процесс сборки, который включает мои модули в закрытие и экспортирует public api в пространство имен. Этот метод также используется jQuery. Вы можете видеть это в своем исходном коде (посмотрите на intro.js & outro.js) на Github.

Это позволит вам использовать шаблон, который позволяет вашей среде IDE (или ctags with vim) видеть ваш api, а также предотвращает загрязнение глобального пространства имен.