복붙노트

[REDIS] Node.js를 루핑 비동기 처리를위한 가장 좋은 패턴

REDIS

Node.js를 루핑 비동기 처리를위한 가장 좋은 패턴

나는 노드에 새로운 내가 JSON 기반의 웹 앱 제정신 디자인을 사용하고 있는지 확인하기 위해 노력하고있어.

나는 레디 스에 저장된 데이터의 무리를 가지고 그들이 레디 스에서 와서 결과를 스트리밍 노드를 통해 검색하고 있습니다. 여기에 내가 뭘하는지의 좋은 예이다 :

app.get("/facility", function(req, res) {
    rc.keys("FACILITY*", function(err, replies) {
        res.write("[");
        replies.forEach(function (reply, i) {
            rc.get(reply, function(err, reply) {
                res.write(reply);
                if (i == replies.length-1) {
                    res.write("]");
                    res.end();
                }
                else
                    res.write(",");
            });
        });
    });
});

기본적으로 나는 레디 스에서 키 세트를 얻고 다음 (JSON 이미 문자열이 레디 스의 나오고있다), 각각을 요구하는 반 수동으로 만든 JSON으로 결과를 스트리밍. 지금 이것은 잘 작동하지만 수 없습니다는 I == replies.length-1이 조금 어수선한이라고 생각하는 데 도움?

나는 레디 스에서 MGET 모든이 작업을 수행 할 수 있지만, 그건 정말 내가 그걸 얻기 위해 노력하고있어 포인트 아니다; 그것은 대해 forEach와 루프 출력을 스트리밍 정상적으로 루프가 완료와 함께 res.end와의 연결을 닫는 비동기 처리하는 방법을 가장 좋습니다.

내가 따라 할 수있는 더 우아한 패턴이이 최선의 방법인가, 또는인가?

해결법

  1. ==============================

    1.위의 코드는 당신이 무엇을 기대하지 않을 수 있습니다. 당신은 순서대로 각각 갔지 ()를 마련했습니다,하지만 그들은 순서대로 다시 전화하지 않을 수 있습니다 - 결과가 어떤 순서로 스트리밍 할 수 있도록. 당신이 메모리에 수집하는 대신 결과를 스트리밍하려면, 당신은 순서에 갔지 () 할 필요가있다.

    위의 코드는 당신이 무엇을 기대하지 않을 수 있습니다. 당신은 순서대로 각각 갔지 ()를 마련했습니다,하지만 그들은 순서대로 다시 전화하지 않을 수 있습니다 - 결과가 어떤 순서로 스트리밍 할 수 있도록. 당신이 메모리에 수집하는 대신 결과를 스트리밍하려면, 당신은 순서에 갔지 () 할 필요가있다.

    그 caolan의 비동기 라이브러리이 쉽게 많이하게 생각합니다. 다음은 순서 (경고, 테스트되지 않은)의 각 항목을 얻을하는 데 사용할 수있는 하나 개의 방법이있다 :

    app.get("/facility", function(req, res) {
        rc.keys("FACILITY*", function(err, replies) {
            var i = 0;
            res.write("[");
            async.forEachSeries(replies, function(reply, callback){
                rc.get(reply, function(err, reply) {
                    if (err){
                        callback(err);
                        return;
                    }
                    res.write(reply);
                    if (i < replies.length) {
                        res.write(",");
                    }
                    i++;
                    callback();
                });
            }, function(err){
                if (err) {
                    // Handle an error
                } else {
                    res.end(']');
                }
            });
        });
    });
    

    당신이 순서에 대한 상관 없어, 그냥 async.forEach ()를 사용하는 대신.

    당신이 순차적으로 반환하도록 결과를 수집하는 마음과 싶지 않을 경우, 당신은 (또한 경고, 테스트되지 않은)이 같은 async.map ()를 사용할 수 있습니다 :

    app.get("/facility", function(req, res) {
        rc.keys("FACILITY*", function(err, replies) {
            async.map(replies, rc.get.bind(rc), function(err, replies){
                if (err) {
                    // Handle an error
                } else {
                    res.end('[' + replies.join(',') + ']');
                }
            });
        });
    });
    
  2. ==============================

    2.당신은 같은 대해 forEach 등의 반복에 대한 몇 가지 편리한 방법을 제공하며, 비동기 라이브러리를 사용할 수 있습니다 :

    당신은 같은 대해 forEach 등의 반복에 대한 몇 가지 편리한 방법을 제공하며, 비동기 라이브러리를 사용할 수 있습니다 :

    // assuming openFiles is an array of file names and saveFile is a function
    // to save the modified contents of that file:
    
    async.forEach(openFiles, saveFile, function(err){
        // if any of the saves produced an error, err would equal that error
    });
    
  3. ==============================

    3.사람들은 그 말의 나는 많이 들었습니다. 이것은 내가 손으로 어떻게 할 것입니다 :

    사람들은 그 말의 나는 많이 들었습니다. 이것은 내가 손으로 어떻게 할 것입니다 :

    app.get("/facility", function(req, res, next) {
      rc.keys("FACILITY*", function(err, replies) {
        if (err) return next(err);
        var pending = replies.length;
        res.write("[");
        replies.forEach(function (reply) {
          rc.get(reply, function(err, reply) {
            res.write(reply);
            if (!--pending) {
              res.write("]");
              return res.end();
            }
            res.write(",");
          });
        });
      });
    });
    

    물론 손으로 그 일을하는 사람들은 도서관이나 다른 기능으로 추상화 한 이유입니다, 꽤하지 않습니다. 그러나 좋든 싫든, 그건 당신이 비동기 병렬 루프를 수행하는 방법이다. :)

    당신은 불쾌한 내장을 숨기기 위해 앞서 언급 한 비동기 라이브러리를 사용할 수 있습니다.

  4. from https://stackoverflow.com/questions/8579557/the-best-pattern-for-handling-async-looping-in-node-js by cc-by-sa and MIT license