NodeJS - как передать асинхронные данные из модели с помощью module.exports? - PullRequest
0 голосов
/ 01 мая 2018

Я пытаюсь получить данные из документа в RethinkDB в NodeJS и передать результат в переменную, которую я хочу использовать в файле шаблона, но это всегда undefined, когда я пытаюсь напечатать переменную data как #{data} (я использую pug / jade), потому что это асинхронный вызов (я думаю).

'use strict';

var r = require('rethinkdb');

module.exports = function IndexModel() {
    data: {
        r.connect({host: '127.0.0.1', port: 28015}, function(err, conn) {
            r.db('mydb').table('mytable').run(conn).then(function(cursor) {
                cursor.toArray(function(err, result) {
                    if (err) throw err;
                    return JSON.stringify(result, null, 2);
                });
            });
        });
    }
};

Я подумал, что это должно быть потому, что nodejs хочет, чтобы это был объект, поэтому я попытался разобрать его как JSON.parse(JSON.stringify(result, null, 2)), но это выдает ту же ошибку.

Когда я делаю console.log(JSON.stringify(result, null, 2)), он печатает после ошибки.

[
  {
    "id": "307ad5e9-a0db-461b-a564-081d73f9b34f",
    "title": "hello"
  }
]

Это точная ошибка, если она необходима:

Cannot read property 'length' of undefined
    at eval (eval at wrap (C:\Users\Me\Project\node_modules\pug-runtime\wrap.js:6:10), <anonymous>:248:32)
    at eval (eval at wrap (C:\Users\Me\Project\node_modules\pug-runtime\wrap.js:6:10), <anonymous>:379:4)
    at template (eval at wrap (C:\Users\Me\Project\node_modules\pug-runtime\wrap.js:6:10), <anonymous>:389:211)
    at Object.exports.renderFile (C:\Users\Me\Project\node_modules\pug\lib\index.js:427:38)
    at Object.exports.renderFile (C:\Users\Me\Project\node_modules\pug\lib\index.js:417:21)
    at View.exports.__express [as engine] (C:\Users\Me\Project\node_modules\pug\lib\index.js:464:11)
    at C:\Users\Me\Project\node_modules\engine-munger\index.js:133:22
    at C:\Users\Me\Project\node_modules\engine-munger\index.js:154:17
    at C:\Users\Me\Project\node_modules\engine-munger\index.js:87:21
    at C:\Users\Me\Project\node_modules\engine-munger\index.js:189:13
    at FSReqWrap.oncomplete (fs.js:153:5)

Есть идеи, как мне решить эту вечную проблему? Спасибо!

Edit:

Похоже, что я не могу ничего вернуть из переменной data внутри какого-либо соединения rethinkdb или обещания, оно должно быть вне его, чтобы быть обнаруженным.

Ответы [ 2 ]

0 голосов
/ 01 мая 2018

Использование async/await может работать на вас

mymodule.js

module.exports = async function IndexModel() {
        let conn = await r.connect({host: '127.0.0.1', port: 28015});
        let cursor = await r.db('mydb').table('mytable').run(conn)
        try {
            let arr = await cursor.toArray();
            return arr
        } catch (e) {
            throw e;
        }
}

main.js

let indexModel = require('mymodule.js');

indexModel().then(result => {
    console.log(result.length)
})
0 голосов
/ 01 мая 2018

Попробуйте заменить ваш код следующим:

const r = require('rethinkdb');

module.exports = function indexModel() {
  return new Promise((resolve, reject) => {
    const params = {
      host: '127.0.0.1', 
      port: 28015
    };
  
    r.connect(params, (err, conn) => {
      // check availability
      if (error) return reject(error);
    
      r.db('mydb')
       .table('mytable')
       .run(conn)
       .then(cursor => {
          cursor.toArray((error, result) => {
            if (error) return reject(error);
            
            const data = JSON.stringify(result, null, 2);
            return resolve({
              data: data
            });
          });
        });
    });
  });
}
...