За последние 24 часа нас посетили 17693 программиста и 1673 робота. Сейчас ищут 1530 программистов ...

Странное поведение require в node.js приложении

Тема в разделе "JavaScript и AJAX", создана пользователем alexpride1993, 11 окт 2017.

  1. alexpride1993

    alexpride1993 Новичок

    С нами с:
    28 мар 2016
    Сообщения:
    56
    Симпатии:
    20
    Всем привет! Надеюсь я не ошибся разделом, нода хоть и нода но в неком смысле тоже яваскрипт) Помогите пожалуйста разобраться со странным (по крайней мере по сравнению с пыхом) поведением функции require в приложении. Ситуация следующая: есть node.js приложение со следующей структурой: в корне есть файл app.js, через который приложение запускается и две директории с модулями. В каждой директории есть конфигурационный файл модуля, подключаемый в файле самого модуля. Для наглядности попробую показать псевдографикой:
    Код (Text):
    1.  
    2. +app.js
    3. |
    4. [module1]-----+config.js
    5. |             +module1.js
    6. |
    7. [module2]-----+config.js
    8.               +module2.js
    Теперь к проблеме: в процессе подключения и инициализации модулей конфиги затирают ранее подключенные, и в результате получается бред. Мне кажется что проблема связана с поведением require, но я не понимаю как ее исправить, опыта общения с node.js у меня не так много и с подобным сталкиваюсь в первый раз.
    Прилагаю код приложения:
    app.js
    Код (Text):
    1.  
    2. let app = {
    3.    services : {}
    4. };
    5.  
    6. async function bootstrap(app) {
    7.    app.services.module1    = require('./module1/module1')(app);
    8.    app.services.module2    = require('./module2/module2')(app);
    9. }
    10.  
    11. bootstrap(app);
    config.js
    Код (Text):
    1.  
    2. module.exports = {
    3.    "dbHost"   : "foo",
    4.    "dbUser"   : "bar",
    5.    "dbPass"   : "buz",
    6.    "dbBase"   : "blah"
    7. };
    module(оба инициализируются практически одинаково, показываю на примере модуля 1)
    Код (Text):
    1.  
    2. function Module1(app) {
    3.  
    4.     let self = this;
    5.     self.app = app;
    6.     self.config = require('./config');
    7.  
    8.    
    9.     self.init = async function() {
    10.  
    11.       self.db1 = new (require('./../database.js'))();
    12.  
    13.       await self.db1.connect({
    14.          host   : self.config.Db1Host,
    15.          user   : self.config.Db1User,
    16.          password: self.config.Db1Pass,
    17.          database: self.config.Db1Base
    18.       });
    19.  
    20.       self.db2 = new (require('./../database.js'))();
    21.  
    22.       await self.db2.connect({
    23.          host   : self.config.Db2Host,
    24.          user   : self.config.Db2User,
    25.          password: self.config.Db2Pass,
    26.          database: self.config.Db2Base
    27.       });
    28.    
    29. };
    30.  
    31.     self.init();
    32.  
    33. }
    34.  
    35. module.exports = Module1;
    Расстановка console.log в обоих файлах показывает что у обоих модулей сначала подключаются свои конфиги (проверка вставка лога в условно 7-ю строку каждого модуля, для модуля 1 выводится конфиг модуля 1, а для модуля 2 конфиг модуля 2, но потом, если ввести еще один console.log в функцию инициализации второго модуля то он покажет что self.config переопределился и стал конфигом из первого модуля. WTF???)
     
  2. romach

    romach Старожил

    С нами с:
    26 окт 2013
    Сообщения:
    2.904
    Симпатии:
    719
    Не затирает оно ничего, require один раз грузит модуль и затем его отдает везде где запрашивают. Очевидно, у вас где-то в коде теряется контекст и соответственно затирается.
     
    alexpride1993 нравится это.
  3. alexpride1993

    alexpride1993 Новичок

    С нами с:
    28 мар 2016
    Сообщения:
    56
    Симпатии:
    20
    Вы были правы! Контекст не то что теряется, он сливается воедино после первого коннекта к базе данных! 0_o Все методы и свойства модулей смешиваются и происходит переопределение конфигов. Остается только разобраться какого лешего это происходит, ведь контексты объектов нигде друг с другом не пересекаются, а класс database это просто промисифицированная обертка над mysql.
    Код (Text):
    1.  
    2. const Mysql = require('mysql');
    3.  
    4. function DataBase()
    5. {
    6.  
    7.    let self = this;
    8.    self.connection = null;
    9.  
    10.    self.connect = function(conParams)
    11.    {
    12.       return new Promise((resolve, reject) => {
    13.  
    14.          let connection = Mysql.createConnection(conParams);
    15.          connection.connect((error) => {
    16.             if (error) {
    17.                reject(error);
    18.             }
    19.             else
    20.             {
    21.                self.connection = connection;
    22.                resolve();
    23.             }
    24.          });
    25.  
    26.       });
    27.    }
    28.  
    29. //code
    30.  
    31. }
    32.  
    33. module.exports = DataBase;
     
  4. alexpride1993

    alexpride1993 Новичок

    С нами с:
    28 мар 2016
    Сообщения:
    56
    Симпатии:
    20
    UPD: Допер наконец! Переделал app.js с:
    Код (Text):
    1.  
    2. app.services.module1    = require('./module1/module1')(app);
    3. app.services.module2    = require('./module2/module2')(app);
    на:
    Код (Text):
    1.  
    2. app.services.module1    = new (require('./module1/module1'))(app);
    3. app.services.module2    = new (require('./module2/module2'))(app);
    и все заработало как нужно.
     
    romach нравится это.