Шаблон модуля CommonJS

я взял это из

Архитектура Flux

var AppDispatcher = require('../dispatcher/AppDispatcher');
var EventEmitter = require('events').EventEmitter;
var TodoConstants = require('../constants/TodoConstants');
var assign = require('object-assign');

var CHANGE_EVENT = 'change';

var _todos = {}; // collection of todo items

/**
 * Create a TODO item.
 * @param {string} text The content of the TODO
 */
function create(text) {
  // Using the current timestamp in place of a real id.
  var id = Date.now();
  _todos[id] = {
    id: id,
    complete: false,
    text: text
  };
}

/**
 * Delete a TODO item.
 * @param {string} id
 */
function destroy(id) {
  delete _todos[id];
}

var TodoStore = assign({}, EventEmitter.prototype, {

  /**
   * Get the entire collection of TODOs.
   * @return {object}
   */
  getAll: function() {
    return _todos;
  },

  emitChange: function() {
    this.emit(CHANGE_EVENT);
  },

  /**
   * @param {function} callback
   */
  addChangeListener: function(callback) {
    this.on(CHANGE_EVENT, callback);
  },

  /**
   * @param {function} callback
   */
  removeChangeListener: function(callback) {
    this.removeListener(CHANGE_EVENT, callback);
  },

  dispatcherIndex: AppDispatcher.register(function(payload) {
    var action = payload.action;
    var text;

    switch(action.actionType) {
      case TodoConstants.TODO_CREATE:
        text = action.text.trim();
        if (text !== '') {
          create(text);
          TodoStore.emitChange();
        }
        break;

      case TodoConstants.TODO_DESTROY:
        destroy(action.id);
        TodoStore.emitChange();
        break;

      // add more cases for other actionTypes, like TODO_UPDATE, etc.
    }

    return true; // No errors. Needed by promise in Dispatcher.
  })

});

где это говорит

В приведенном выше коде следует отметить несколько важных моментов. Для начала мы поддерживаем приватную структуру данных под названием _todos. Этот объект содержит все отдельные элементы списка дел. Поскольку эта переменная находится вне класса, но внутри модуля, она остается закрытой — ее нельзя изменить напрямую извне модуля. Это помогает нам сохранить отдельный интерфейс ввода-вывода для потока данных, делая невозможным обновление хранилища без использования действия.

Жирная часть мне непонятна. Как интерпретатор js может знать, что весь этот код находится внутри замыкания модуля, а не в глобальной области видимости? С чего начинается закрытие модуля и где заканчивается?

Насколько я знаю

Областью действия переменной, объявленной с помощью var, является ее текущий контекст выполнения, который является либо объемлющей функцией, либо, для переменных, объявленных вне какой-либо функции, глобальным.

Любое объяснение?


person Nemus    schedule 11.02.2016    source источник


Ответы (2)


На самом деле вам не хватает последней строки из цитаты, которую вы цитируете:

module.exports = TodoStore;

CommonJS — это API для определения модулей, использующих следующие соглашения:

  • Каждый файл определяет модуль и выполняется в изолированной среде; то есть переменные, которые он определяет, не будут доступны извне модуля.
  • Чтобы разрешить импорт других модулей, модулю доступна глобальная переменная require, позволяющая импортировать другие модули.
  • Точно так же переменная module становится доступной для модуля, чтобы он мог установить свой атрибут exports, чтобы определить, что должен экспортировать ваш модуль; значение, которое вы установили для module.exports в своем модуле a.js, — это именно то, что вернет require('./a').

Каждая среда JS, реализующая CommonJS, должна знать эти правила. Это включает в себя, конечно, Node.js, а также сборщики, такие как Browserify и Webpack, которые будут упаковывать ваши коды так, чтобы эти соглашения соблюдались.

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

P.S. : обратите внимание, что вы также можете использовать переменную exports для определения своего экспорта, и что ее использование немного отличается от module.exports. Подробнее см. в этом вопросе и ответе на StackOverflow.

person Arthur    schedule 11.02.2016
comment
так что это соглашение CommonJS. Спасибо - person Nemus; 11.02.2016

Общий шаблон JS использует функцию конструктора для определения ваших утилит.

Он определяется в форме класса.

var moduleName = function() {

  // private variables

  // public functions
  this.method1 = function() {
    // logic1 goes here
  };

  this.method2 = function() {
    // logic2 goes here
  };

};

Итак, мы собираемся экспортировать класс в другие модули, используя

    module.exports = moduleName;

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

Как это использовать?

    var module = require('moduleName');  //importing the module created above

Здесь определение модуля извлекается, выполняется и затем доступно в переменной «модуль».

Это имя переменной может быть любым

    var objectOfModule = new module(); //instance is created

    objectOfModule .method1(); //use1

    console.log(objectOfModule .method2()); //use2

Спасибо.

person Dhana    schedule 11.05.2017