使用 neo4j 和 bluebird 时,对象 #<Object> 没有方法 'http'

Object #<Object> has no method 'http' when using neo4j and bluebird

我正在使用 this Neo4J 库,我想改用 promises。所以我尝试使用蓝鸟的承诺。我创建了以下代码...

    var db = new neo4j.GraphDatabase('....'),
        Promise = require('bluebird'),
        Cypher = Promise.promisify(db.cypher);

    var query = [
        'MATCH (node)',
        'OPTIONAL MATCH (node)-[rel]->( )',
        'RETURN DISTINCT node as node, collect(rel) as links'
    ].join('\n');

    var i = 0
    var onSuccess = function (results) {
            res.json(parseGraphResponse(results));
        },
        onFail = function (err) {
            console.log("Error " + err);
        };
    Cypher({
        query: query
    }).then(onSuccess).catch(onFail);

但是,现在我得到了以下捕获到 onError 的错误...

TypeError: Object # has no method 'http'

这个版本工作正常...

    db.cypher({
        query: query
    }, function (err, results) {
        if (err) {
            console.log("Error " + err);
            return;
        }
        res.json(parseGraphResponse(results));
    });

多一点调查表明它在这段代码上爆炸了...

GraphDatabase.prototype.cypher = function(opts, cb, _tx) {
  ...
  // Blows up here....
  return this.http({
        method: method,
        path: path,
        headers: headers,
        body: body,
        raw: true
      }, (function(_this) {
        return function(err, resp) {
          ...
        }
      })
}

我打赌这会解决它:

Cypher = Promise.promisify(db.cypher.bind(db));

为了将来参考,调试方法是将错误消息解释为 this 没有 http 方法,但你知道 db 有,所以 this 不能设置为 db。事实上,传递 db.cypher 会丢失 thisdb 的引用。

除了答案,我还建议添加以下...

if(db.cypher)
  Promise.promisify(db.cypher.bind(db));

if 将在数据库关闭时防止失败。在我的例子中,当我无法访问服务器时,我使用 XML 文件来模拟数据。