Нужно ли отписываться каждый раз, когда я подписываюсь - PullRequest
0 голосов
/ 03 апреля 2019

Я пытаюсь определить, что делать со следующим кодом

let sub = myObservable.subscribe(
    v => doThing(v),
    e => handle(e),
    () => sub.unsubscribe(),
)

Проблема 1. Этот код неверен, поскольку myObservable завершается синхронно, NPE будет выбрасываться при завершении.2. Хотя я подозреваю, что отписаться от звонка здесь - хорошая практика.Я не могу помочь, но чувствую, что в этом нет необходимости, потому что я не видел, чтобы это было сделано где-то еще.

Я прочитал эту статью https://blog.angularindepth.com/why-you-have-to-unsubscribe-from-observable-92502d5639d0, но на самом деле это оставляет меня более смущенным, чем когда я начинал.

Если я сделаю

let subA = myObservable.pipe(take(1)).subscribe()
let subB = myObservable.pipe(takeUntil(foo)).subscribe()

Мне больше не нужно отписываться от subA и subB?

как насчет subC здесь?

let subC = myObservable.pipe(finalize(() => cleanupOtherResources())).subscribe()

Или мне нужно добавить все подписки в список в каждом классе, который вызывает subscribe() для любого BehaviorSubject и сразу отписаться от них?

Спасибо!

1 Ответ

1 голос
/ 04 апреля 2019

Лучше всего отказаться от подписки.takeUntil подходит для использования, если вы знаете, что метод очистки вашего класса фактически генерирует наблюдаемую очистку.дубль не всегда гарантирует, что наблюдаемое излучило.Могут быть случаи, когда вы знаете, что наблюдаемое определенно будет излучать хотя бы один раз, но все еще существует вероятность того, что утечка была создана.

Проблема с предположением, что наблюдаемое завершится, состоит в том, что вы не знаетеесли внутренности сервиса возвращают заметные изменения.Если вы предполагаете, что наблюдаемое является http-запросом и завершается в конце запроса, тогда будущий рефакторинг, который изменяет наблюдаемое на обработчик кэша, теперь создал утечку памяти, потому что вы не отписались.

Отмена подпискитакже отменяет любые текущие запросы.

Проблема с такими утверждениями, как

let sub = myObservable.subscribe(
    v => doThing(v),
    e => handle(e),
    () => sub.unsubscribe(),
)

Если myObservable генерирует мгновенно, как BehaviorSubject, тогда sub не определено.Я хотел бы избежать такой отмены подписки и использовать takeUntil с темой.

const finalise$ = new Subject();

myObservable.pipe(takeUntil(finalise$)).subscribe(
    v => doThing(v),
    e => handle(e),
    () => { finalise$.next(); },
);

Этот код гарантированно безопасен для отмены подписки.

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