Никогда не выполненное обещание вызывает утечку памяти?

У меня есть Promise, Я создал его, чтобы отменить запрос AJAX, если это необходимо. Но так как мне не нужно отменять этот AJAX, я никогда не разрешал его, и AJAX успешно завершился.

Упрощенный фрагмент:

var defer = $q.defer();
$http({url: 'example.com/some/api', timeout: defer.promise}).success(function(data) {
    // do something
});

// Never defer.resolve() because I don't need to cancel that ajax. What happens to this promise after request?

Никогда не выполняются такие обещания, которые вызывают утечку памяти? Есть ли у вас какие-либо советы о том, как управлять Promise жизненный цикл?

1 ответ

Решение

Ну, я предполагаю, что вы не сохраняете явную ссылку на него, так как это заставит его остаться выделенным.

Самый простой тест, о котором я мог подумать, - это на самом деле выделить много обещаний, а не выполнить их:

var $q = angular.injector(["ng"]).get("$q");
setInterval(function () {
    for (var i = 0; i < 100; i++) {
        var $d = $q.defer();
        $d.promise;
    }
}, 10);

А потом смотрю саму кучу. Как мы видим в инструментах профилирования Chrome, это накапливает необходимую память для выделения 100 обещаний, а затем просто "остается там" на уровне менее 15 мегабайт для всей страницы JSFIddle.

введите описание изображения здесь

С другой стороны, если мы посмотрим на $q исходный код

Мы можем видеть, что нет никакой ссылки с глобальной точки зрения на какое-либо конкретное обещание, а только на обещание его обратных вызовов. Код очень читабелен и понятен. Давайте посмотрим, что если у вас есть ссылка из обратного вызова на обещание.

var $q = angular.injector(["ng"]).get("$q");
console.log($q);
setInterval(function () {
    for (var i = 0; i < 10; i++) {
        var $d = $q.defer();
        (function ($d) { // loop closure thing
            $d.promise.then(function () {
                console.log($d);
            });
        })($d);
    }
}, 10);

введите описание изображения здесь

Так что после первоначального распределения - кажется, что он может справиться и с этим:)

Мы также можем увидеть некоторые интересные шаблоны GC, если оставим его последний пример еще на несколько минут. Мы видим, что это занимает некоторое время - но он способен убрать обратные вызовы.

введите описание изображения здесь

Короче говоря - по крайней мере, в современных браузерах - вам не нужно беспокоиться о нерешенных обещаниях, если у вас нет внешних ссылок на них

Другие вопросы по тегам