Created
May 29, 2019 13:50
-
-
Save diamond-darrell/1cfb3080303309cbea7021c9c7234c1a to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import {merge, MonoTypeOperatorFunction, Observable, Operator, Subject, Subscriber, TeardownLogic} from "rxjs"; | |
import {OnDestroy} from "@angular/core"; | |
const __ngOnDestroySource__ = Symbol("__ngOnDestroySource__"); | |
const __ngOnDestroy__ = Symbol("__ngOnDestroy__"); | |
interface EnhancedOnDestroy extends OnDestroy { | |
[__ngOnDestroySource__]: Subject<string>; | |
[__ngOnDestroy__]: () => void; | |
} | |
export function cancelOnDestroy<T>(instance: OnDestroy, | |
manualDestroy?: Observable<any>): MonoTypeOperatorFunction<T> { | |
return (source: Observable<T>) => source.lift(new CancelOnDestroyOperator(instance, manualDestroy)); | |
} | |
class CancelOnDestroyOperator<T> implements Operator<T, T> { | |
constructor(private instance: OnDestroy, private manualDestroy?: Observable<any>) { | |
if (instance.ngOnDestroy) { | |
if (!(<EnhancedOnDestroy>instance)[__ngOnDestroySource__]) { | |
(<EnhancedOnDestroy>instance)[__ngOnDestroySource__] = new Subject(); | |
(<EnhancedOnDestroy>instance)[__ngOnDestroy__] = instance.ngOnDestroy; | |
instance.ngOnDestroy = function (this: EnhancedOnDestroy) { | |
this[__ngOnDestroy__].apply(this, arguments); | |
this[__ngOnDestroySource__].next(); | |
this[__ngOnDestroySource__].complete(); | |
}; | |
} | |
} | |
} | |
call(subscriber: Subscriber<T>, source: any): TeardownLogic { | |
return source.subscribe(new CancelOnDestroySubscriber(subscriber, <EnhancedOnDestroy>this.instance, this.manualDestroy)); | |
} | |
} | |
class CancelOnDestroySubscriber<T> extends Subscriber<T> { | |
constructor(destination: Subscriber<T>, | |
private _instance: EnhancedOnDestroy, | |
private manualDestroy?: Observable<any>) { | |
super(destination); | |
const sources = manualDestroy | |
? merge(manualDestroy, _instance[__ngOnDestroySource__]) | |
: _instance[__ngOnDestroySource__].asObservable(); | |
this.add(sources.subscribe( | |
() => { | |
destination.unsubscribe(); | |
} | |
)); | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment