Расширение прототипа улова для отслеживания новых реликвий - PullRequest
0 голосов
/ 28 февраля 2019

Я хочу расширить общий прототип catch объекта Promise, чтобы я мог автоматически регистрировать ошибку при выходе из мониторинга приложения при каждом попадании в блок catch.Но у меня возникают проблемы с извлечением объекта ошибки из объекта Promise при попытке расширить улов.

Таким образом, вместо того, чтобы делать это в каждом then (). Catch ()

axios.get('sample/url')
    .then(response => { stuff })
    .catch(error => {
        newrelic.noticeError(error);
    });

Я хочу расширить прототип Promise, но не смог получить из него объект Error.

(function (Promise) {
    const originalCatch = Promise.prototype.catch;

    Promise.prototype.catch = function () {
        console.log('> > > > > > called .catch on %o with arguments: %o', this, arguments);

        if (typeof newrelic !== 'undefined') {
            newrelic.noticeError(arguments[0]);
        } else {
            console.error(arguments);
        }

        return originalCatch.apply(this, arguments);
    };
})(Promise);

Ответы [ 2 ]

0 голосов
/ 28 февраля 2019

Вы можете напрямую вызвать ваш обратный вызов через Promise, чтобы аргумент был оценен:

(function (Promise) {
    const originalCatch = Promise.prototype.catch;

    Promise.prototype.catch = function () {
        console.log('> > > > > > called .catch on %o with arguments: %o', this, arguments);

        if (typeof newrelic !== 'undefined') {
            originalCatch.apply(this, [newrelic.noticeError]);
               //^--- changed here.
        } else {
            console.error(arguments);
        }

        return originalCatch.apply(this, arguments);
    };
})(Promise);

Пример рабочего кода: https://jsfiddle.net/7qgjr6fw/3/

0 голосов
/ 28 февраля 2019

Аргументом catch является функция обратного вызова, а не ошибка.

Вы ищете

Promise.prototype.catch = (function(originalCatch) {
    return function(onRejected) {
        console.log('> > > > > > called .catch on %o with arguments: %o', this, arguments);
        return originalCatch.call(this, error => {
            if (typeof newrelic !== 'undefined') {
                newrelic.noticeError(error);
            } else {
                console.error(error);
            }
            return onRejected(error);
       });
    };
})(Promise.prototype.catch);

Кстати, я бы рекомендовал не вмешиваться в Promise.prototype,Перехват каждого вызова catch даст вам довольно много ложных срабатываний (которые вы на самом деле не хотели регистрировать), а также ложных отрицаний (которые вы должны были перехватить), потому что обработчик ошибок был установлен с использованием then или нет catch был вызван вообще.Лучше четко указать, куда вы хотите, чтобы ошибки попадали в мониторинг, с помощью простого многоразового

function monitorError(error) {
    if (typeof newrelic !== 'undefined') {
        newrelic.noticeError(error);
    } else {
        console.error(error);
    }
}

, который вы можете явно вводить или добавлять в цепочки обещаний с помощью простого

.catch(monitorError)
...