等待回调在节点中完成

时间:2016-11-10 13:26:17

标签: javascript json node.js callback

我使用Elasticsearch JS客户端和节点来学习ES和Javascript。我在这样定义的SublimeText2中使用Javascript构建系统来运行JS代码:

{
  "cmd": ["C:\\Program Files\\nodejs\\node.exe", "$file"],
  "selector": "source.js"
}

写这个以将数据提交给ES进行索引:

"use strict";

const es = require('elasticsearch');
const path = require('path');
const fs = require('fs');

function es_connect(url, loglevel) {
    if (typeof loglevel === 'undefined') { // somehow default function params feature from ES6 is not available in installable node/js
        loglevel == 'error';
    }
    return new es.Client({host: url, log:loglevel});
}

function get_content(fname) {
    const raw = fs.readFileSync(path.join('data', fname));
    const content = JSON.parse(raw);
    console.log('Found ' + content.objects.length + ' objects.');
    return content;
}

function index_json_list(fname, index, doc_type, url) {
    var content = get_content(fname);
    var client = es_connect(url);
    var results = [];

    function result_cb(err, resp) {
        console.log('Pushing error ' + err + ' and response ');
        console.log(resp);
        results.push({error:err, response:resp});
    };

    content.objects.forEach(function(x) {
        console.log('___Submitting ');
        console.log(x);
        client.index({
                index: index,
                type: doc_type,
                body: x
        },
        result_cb);
    });

    results.forEach(function(x){
        console.log('indexing result: ' + x);
    })

    console.log('results');
    console.log(results);
}


index_json_list('us_presidents.json', 'officials', 'president', 'http://localhost:9200/');

数据来源:https://github.com/dariusk/corpora/blob/master/data/humans/us_presidents.json

输出:

Found 66 objects.
___Submitting 
{ website: '',
  startdate: '2009-01-20',
  role_type_label: 'President',
....
  leadership_title: null }

results
[]

Pushing error undefined and response 
{ _index: 'officials',
  _type: 'president',
  _id: 'AVhOXERCNHzrCLGOfUu1',
  _version: 1,
  result: 'created',
  _shards: { total: 2, successful: 1, failed: 0 },
  created: true }
Pushing error undefined and response 
{ _index: 'officials',
  _type: 'president',
  _id: 'AVhOXERBNHzrCLGOfUu0',
  _version: 1,
  result: 'created',
  _shards: { total: 2, successful: 1, failed: 0 },
  created: true }
...

问题:

  1. 很明显为什么打印results输出空数组,但问题是如何等待这些回调完成? (我不是指同步等待,而是以异步回调的方式)。它可以使用promises完成,但我还没有学到承诺,现在想学习如何做到这一点"回调"方式。

  2. 是否有某种方法可以在JSON对象上进行字符串连接,而不是像[object Object]那样获取表示,而是使用对象文字? (如果我调用console.log(obj)我得到对象文字的字符串表示,而不是[object Object]"简写")。使用.toString()并不好。

1 个答案:

答案 0 :(得分:1)

  1. async提供异步原语/工作流api,用于使用基于回调的方法处理异步请求。 async为集合提供了近1种performing异步操作。

    他们的模型是每个操作都传递一个回调。当操作完成(成功或错误)时,该操作将调用回调。 async允许您注册一个回调,以便在所有操作完成后执行。

  2. 您可以通过跟踪需要执行的异步操作数量以及完成时间来自行推送。

    var numOps = content.objects.length;

    然后在回调中你可以检查这是否是要执行的最后一个回调。

    function result_cb(err, resp) {
       results.push({error:err, response:resp});
       if (results.length === numOps) {
          // all operations have succeeded! `results` is completed
       }
    }
    

    如果查看async源代码,他们会做类似的事情来维护异步状态。

    1. 您可以创建自定义格式化程序功能,也可以使用内置标准库函数记录对象:https://stackoverflow.com/a/10729284/594589