Javascript: используйте «new Function ()» для запуска кода в строке и доступа к определениям классов

#javascript #function #class #scope #eval

#javascript #функция #класс #область видимости #оценка

Вопрос:

Мой фактический код плотный, поэтому я пытаюсь свести это к минимальному примеру.

У меня есть MainUI.js который содержит:

 var MainUI = function(){
  'use strict';
  
  var singleton = null;

  class MainUI {
    makeSomethingHappen(){
      console.log("MAGIC!");
    }
  }

  return {
    getSingleton: function(){
      if (singleton == null) singleton = new MainUI();

      return singleton;
    }
  };
}();
 

Тогда у меня есть test.js который содержит:

 function test(code){
  var uis = MainUI.getSingleton();

  retValue = new Function("ui", "use strict'"   code)(uis);
}
 

Все это выполняется из index.html который содержит:

 <html>
  <script type="text/javascript" src="MainUI.js"></script>
  <script type="text/javascript" src="test.js"></script>

  <body onload="test('ui.makeSomethingHappen();');">
  </body>
</html>
 

Но когда я вызываю

 test("ui.makeSomethingHappen();");
 

или даже

 test("console.log('NARF!');");
 

Я получаю исключение с сообщением

 MainUI is not defined
 

Одноэлементный метод доступа и MainUI работают во всем моем коде за пределами «new Function ()», поэтому я знаю, что он работает (даже если я допустил опечатку, создав минимальный тест).

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

Комментарии:

1. конструктор функции не имеет доступа к локальной переменной. Он выполняет код в глобальной области видимости. Зачем вообще использовать конструктор функций здесь? Почему бы не передать обратный вызов?

2. Я передаю переменную в качестве аргумента для вызова функции: «(uis)». Я также не понимаю, как доступ к переменной объясняет ошибку определения класса. Не могли бы вы объяснить, как обратный вызов будет решать мой случай?

3. Если вы передадите (ui) => ui.doSomething() его как обратный вызов и внутри test него вызовете callback(mainUI) , вам не нужно будет возиться с попытками создать корректный код JS — вы также получите полную поддержку инструментов для обратного вызова, включая подсветку синтаксиса, компоновку, рефакторинг из вашего редактора и т. Д.

4. Это был лишь минимальный пример. Я не буду знать, что это за код во время компиляции, потому что он будет отправлен в виде текста из внешнего источника. Вот почему я передаю полезные экземпляры классов для использования кода.

5. Основываясь на минимальном коде, который вы показали, проблема не new Function() в том, что это связано с var uis = MainUI.getSingleton(); тем, что на MainUI это ссылаются, и ваша ошибка говорит о M ainUI. new Function Ссылается на строку "mainUI"

Ответ №1:

Убедитесь, что MainUI.js script ссылка указана правильно и что на нее ссылаются до test.js script того, как она будет использоваться.