복붙노트

[NODEJS] 거부에 전달하지 체인 약속

NODEJS

거부에 전달하지 체인 약속

해결법


  1. 1.아니 당신이 묘사하는 것은 체인이 아니라 단지 D1에 모든 콜백을 부착. 당신은 다음과 체인 뭔가하려는 경우 그러나, promise2에 대한 결과는 promise1 해결하는 방법 다음 콜백을 처리에 따라 달라집니다.

    아니 당신이 묘사하는 것은 체인이 아니라 단지 D1에 모든 콜백을 부착. 당신은 다음과 체인 뭔가하려는 경우 그러나, promise2에 대한 결과는 promise1 해결하는 방법 다음 콜백을 처리에 따라 달라집니다.

    워드 프로세서 상태 :

    그 때는 방법은 일반적으로 약속 / A 규격 환산시 보였다 (또는 심지어 엄격한 Promsises / A + 하나)이다. 그 수단은 콜백 promise2의 해상도되기 위해 동화됩니다 반환 약속 쉘, 그리고 각각의 결과가 경우에 promise2에 직접 전달됩니다 더 성공 / 오류 처리기가없는 경우 - 당신은 단순히 오류를 전파 할 핸들러를 생략 할 수 있도록이 .

    오류가 처리되는 경우에 고정 값이 충족 될 것이다 그러나, 생성 promise2이 보인다. 당신이 원하지 않는 경우, 당신은 시도 - 캐치 절처럼, 오류를 다시 던질 것이다. 또는 당신은 (BE-가-) 핸들러에서 약속을 거부 반환 할 수 있습니다. 확실하지 무슨 도장 방법 거부하는 것은, 그러나 :

    var d1 = d();
    
    var promise1 = d1.promise.then(
        function(wins) { console.log('promise1 resolved'); return wins;},
        function(err) { console.log('promise1 rejected'); throw err;});
    var promise2 = promise1.then(
        function(wins) { console.log('promise2 resolved'); return wins;},
        function(err) { console.log('promise2 rejected'); throw err;});
    var promise3 = promise2.then(
        function(wins) { console.log('promise3 resolved'); return wins;},
        function(err) { console.log('promise3 rejected'); throw err;});
    d1.reject(new Error());
    

    그는 할 수 없어야합니다. 오류 핸들러가없는 경우, 그는 단지 메시지를 인식합니다 (((생강)에서 존에서) 대리점에서) 남아있는 위젯이 없는지. 생강은이 경우에 대한 오류 핸들러를 설정하면 그러나, 그녀는 여전히 그녀는 존 또는 자신의 대리점에 남아있는 파란색 사람이없는 경우 그녀가 오두막을 소유에서 그에게 녹색 하나를 제공하여 밥 위젯을 제공하기 위해 약속을 이행 할 수 있습니다.

    metapher에 당신 오류 콜백을 번역하려면 핸들러의 리턴 ERR는 "단지 그에게 어떤 사람이 남아 있지 있다는 것을 메모를주고, 어떤 위젯이 남아 있지가있는 경우 - 위젯 원하는대로 좋은대로입니다"라는 것과 같다.

    ... 오류가 처리되는 것을 의미한다. 당신이하지 않으면 그냥 오류 콜백을 생략합니다. 그들은 꽤 쓸모없는 것 같다, 그래서 BTW, 당신의 성공 콜백은, 그들이 만들고있는 약속을 반환하지 않습니다. 수정은 다음과 같습니다

    var promise = db.query({parent_id: value});
    promise.then(function(query_result) {
        var first_value = {
            parent_id: query_result[0].parent_id
        }
        var promise = db.put(first_value);
        return promise.then(function(first_value_result) {
            var second_value = {
                reference_to_first_value_id: first_value_result.id
            }
            var promise = db.put(second_value);
            return promise.then(function(second_value_result) {
                return values_successfully_entered();
            });
        });
    });
    

    또는, 당신도 이전 콜백에서 액세스 결과 값으로 클로저를 필요로하지 않기 때문에 :

    db.query({parent_id: value}).then(function(query_result) {
        return db.put({
            parent_id: query_result[0].parent_id
        });
    }).then(function(first_value_result) {
        return db.put({
            reference_to_first_value_id: first_value_result.id
        });
    }.then(values_successfully_entered);
    

  2. 2.연기 lib 디렉토리를 사용하는 경우 @Jordan 덧글이 언급 첫째로, 당신의 첫 번째 예는 확실히 당신이 기대하는 결과를 생성합니다

    연기 lib 디렉토리를 사용하는 경우 @Jordan 덧글이 언급 첫째로, 당신의 첫 번째 예는 확실히 당신이 기대하는 결과를 생성합니다

    promise1 rejected
    promise2 rejected
    promise3 rejected
    

    둘째, 당신이 제안 출력을 생성 할 경우에도, 그것은 더 같은 비트 다른이, 당신의 두 번째 조각의 실행 흐름에 영향을주지 않습니다 :

    promise.then(function(first_value) {
        console.log('promise1 resolved');
        var promise = db.put(first_value);
        promise.then(function (second_value) {
             console.log('promise2 resolved');
             var promise = db.put(second_value);
             promise.then(
                 function (wins) { console.log('promise3 resolved'); },
                 function (err) { console.log('promise3 rejected'); return err; });
        }, function (err) { console.log('promise2 rejected'); return err;});
    }, function (err) { console.log('promise1 rejected'); return err});
    

    그리고, 첫 번째 약속의 경우 것이다 단지 출력을 거부되는 것을 :

    promise1 rejected
    

    그러나 (가장 흥미로운 부분에 점점) 비록 연기 라이브러리는 확실히 다른 약속 라이브러리의 대부분은 1, x는 2 (가정에 리드 대신 다른 약속 라이브러리를 사용하여 이러한 결과를 가지고 있음) 해결 X, 거부 반환, 3 × 거부 반환 .

    또한 혼란 무엇이, 그 다른 라이브러리는 자신의 행동에 더 정확합니다. 설명해 드리죠.

    "약속 제거"의 동기 세계 대응에 던져이다. 그래서 의미, deferred.reject 비동기 (새 오류 ()) 동기화 () 새로운 오류를 던져 같습니다. 귀하의 예제에서 당신은 당신의 동기 콜백에서 오류를 던지고하지 않는, 당신은 단지 때문에 오류가 성공의 가치와 성공 흐름으로 전환,이를 반환. 확실히 거절 더 전달하려면, 당신은 당신의 오류를 다시 던져해야합니다 :

    function (err) { console.log('promise1 rejected'); throw err; });
    

    이제 질문은, 왜 연기 할 라이브러리 거부로 오류를 반환 걸렸입니까?

    그 이유는, 연기 작품이 거부 조금 다르다. 규칙 lib에는 연기에 :이 오류의 인스턴스 해결할 때 약속을 당신이 deferred.resolve 않도록 경우에도 거부가 deferred.reject 역할을합니다 (() 새로운 오류) (새 오류 ()), 그리고 경우 이 약속은 오류의 인스턴스와 거부 할 수 있습니다, 예외가 말을 던질 것이다 deferred.reject (notAnError)을 수행하려고합니다. 다음 콜백에서 반환 된 오류가 약속을 거부하는 이유는 명확합니다.

    이 연기 논리 뒤에 몇 가지 유효한 이유는,하지만 여전히 그것을 던져, 자바 스크립트에서 작동하는 방법과 동등 아니다 인해 연기의이 동작은 버전 v0.7으로 변경 예정되어 있다고한다.

    짧은 요약:

    혼란을 방지하고 예상치 못한 결과는 단지 좋은 연습 규칙을 따라야합니다 :

    위의에 순종, 당신은 모두 연기 및 기타 인기 약속 라이브러리에서 모두 일관되고 예상 결과를 얻을 수 있습니다.


  3. 3.사용은 약속의 각 레벨에서 오류를 포장 할 수 있습니다. 나는 TraceError에서 오류를 체인 :

    사용은 약속의 각 레벨에서 오류를 포장 할 수 있습니다. 나는 TraceError에서 오류를 체인 :

    class TraceError extends Error {
      constructor(message, ...causes) {
        super(message);
    
        const stack = Object.getOwnPropertyDescriptor(this, 'stack');
    
        Object.defineProperty(this, 'stack', {
          get: () => {
            const stacktrace = stack.get.call(this);
            let causeStacktrace = '';
    
            for (const cause of causes) {
              if (cause.sourceStack) { // trigger lookup
                causeStacktrace += `\n${cause.sourceStack}`;
              } else if (cause instanceof Error) {
                causeStacktrace += `\n${cause.stack}`;
              } else {
                try {
                  const json = JSON.stringify(cause, null, 2);
                  causeStacktrace += `\n${json.split('\n').join('\n    ')}`;
                } catch (e) {
                  causeStacktrace += `\n${cause}`;
                  // ignore
                }
              }
            }
    
            causeStacktrace = causeStacktrace.split('\n').join('\n    ');
    
            return stacktrace + causeStacktrace;
          }
        });
    
        // access first error
        Object.defineProperty(this, 'cause', {value: () => causes[0], enumerable: false, writable: false});
    
        // untested; access cause stack with error.causes()
        Object.defineProperty(this, 'causes', {value: () => causes, enumerable: false, writable: false});
      }
    }
    

    용법

    throw new TraceError('Could not set status', srcError, ...otherErrors);
    

    산출

    기능

    TraceError#cause - first error
    TraceError#causes - list of chained errors
    
  4. from https://stackoverflow.com/questions/16371129/chained-promises-not-passing-on-rejection by cc-by-sa and MIT license