Предоставление динамически созданных функций на объектах с помощью компилятора замыкания

Я пытаюсь аннотировать свой javascript, чтобы закрытие не переименовывало все символы, так как я также работаю с ванильным javascript.

/**
* @constructor
* @expose
* @type{foo}
*/

foo = function (el, args) {
"use strict";
var s = "Hello World";
/*
* @expose
* @this {foo}
* @type {function}
*/
this.introduce = function () {
    return s;
 };
};

Однако сгенерированный вывод, когда я запускаю его через компилятор закрытия с расширенной оптимизацией,

foo = function() {
 this.a = function() {
 return"Hello World"

} };

Как мне попросить закрыть, чтобы сохранить ввод имени, так как это будет вызываться из внешнего javascript.


person Gokul    schedule 27.07.2012    source источник


Ответы (1)


Следующие параметры могут использоваться для предотвращения переименования символов Closure Compiler:

Если вы не хотите определять методы в прототипе функции, как показано в вашем примере, вы можете экспортировать конструктор foo с помощью goog.exportSymbol и использовать @expose для экспорта методов.

/**
 * @param {Element} el
 * @param {...*} args
 * @constructor
 */
var foo = function (el, args) {
  "use strict";

  /** @private */
  this.msg_ = "Hello World";

  /**
   * @this {foo}
   * @return {string}
   * @expose
   */
  this.introduce = function () {
    return this.msg_;
  };
};
goog.exportSymbol('foo', foo);

Определив методы в прототипе функции, goog.exportSymbol можно использовать для экспорта как конструктора, так и имен методов.

/**
 * @param {Element} el
 * @param {...*} args
 * @constructor
 */
var foo = function (el, args) {
  "use strict";

  /** @private */
  this.msg_ = 'Hello World!';
};
goog.exportSymbol('foo', foo);

/**
 * @return {string}
 */
foo.prototype.introduce = function () {
  return this.msg_;
};
goog.exportSymbol('foo.prototype.introduce', foo.prototype.introduce);

См. эти связанные вопросы stackoverflow:

person Christopher Peisert    schedule 27.07.2012
comment
Когда я использую аннотацию @expose для методов прототипа, она отлично работает без использования goog.exportSymbol. Однако аннотация expose, похоже, не работает с функциями, добавляемыми непосредственно к объекту, а не к прототипу. Я хотел бы использовать его в первом случае, чтобы я мог использовать закрытие вместо того, чтобы пытаться иметь переменные-члены повсюду. - person Gokul; 27.07.2012
comment
Ответ обновлен, чтобы объяснить @expose и предоставить рабочие примеры с использованием методов, определенных непосредственно в конструкторе, а также в прототипе функции. - person Christopher Peisert; 27.07.2012
comment
Не используйте аннотацию @expose. Он хрупкий. groups.google.com/forum/#!msg/ закрытие-компилятор-обсудить/ - person Daniel Steigerwald; 20.08.2014
comment
@expose больше не рекомендуется. Его заменяют @nocollapse и @export. Компилятор предупредит о любом использовании @expose. - person Chad Killingsworth; 17.04.2015