UNPKG

@zkochan/pnpm

Version:

Fast, disk space efficient package manager

111 lines (90 loc) 2.73 kB
/** @license MIT License (c) copyright 2010-2016 original author or authors */ /** @author Brian Cavalier */ /** @author John Hann */ import Stream from '../Stream' import * as dispose from '../disposable/dispose' /** * Given a stream of streams, return a new stream that adopts the behavior * of the most recent inner stream. * @param {Stream} stream of streams on which to switch * @returns {Stream} switching stream */ export function switchLatest (stream) { return new Stream(new Switch(stream.source)) } export { switchLatest as switch } function Switch (source) { this.source = source } Switch.prototype.run = function (sink, scheduler) { var switchSink = new SwitchSink(sink, scheduler) return dispose.all([switchSink, this.source.run(switchSink, scheduler)]) } function SwitchSink (sink, scheduler) { this.sink = sink this.scheduler = scheduler this.current = null this.ended = false } SwitchSink.prototype.event = function (t, stream) { this._disposeCurrent(t) // TODO: capture the result of this dispose this.current = new Segment(t, Infinity, this, this.sink) this.current.disposable = stream.source.run(this.current, this.scheduler) } SwitchSink.prototype.end = function (t, x) { this.ended = true this._checkEnd(t, x) } SwitchSink.prototype.error = function (t, e) { this.ended = true this.sink.error(t, e) } SwitchSink.prototype.dispose = function () { return this._disposeCurrent(this.scheduler.now()) } SwitchSink.prototype._disposeCurrent = function (t) { if (this.current !== null) { return this.current._dispose(t) } } SwitchSink.prototype._disposeInner = function (t, inner) { inner._dispose(t) // TODO: capture the result of this dispose if (inner === this.current) { this.current = null } } SwitchSink.prototype._checkEnd = function (t, x) { if (this.ended && this.current === null) { this.sink.end(t, x) } } SwitchSink.prototype._endInner = function (t, x, inner) { this._disposeInner(t, inner) this._checkEnd(t, x) } SwitchSink.prototype._errorInner = function (t, e, inner) { this._disposeInner(t, inner) this.sink.error(t, e) } function Segment (min, max, outer, sink) { this.min = min this.max = max this.outer = outer this.sink = sink this.disposable = dispose.empty() } Segment.prototype.event = function (t, x) { if (t < this.max) { this.sink.event(Math.max(t, this.min), x) } } Segment.prototype.end = function (t, x) { this.outer._endInner(Math.max(t, this.min), x, this) } Segment.prototype.error = function (t, e) { this.outer._errorInner(Math.max(t, this.min), e, this) } Segment.prototype._dispose = function (t) { this.max = t dispose.tryDispose(t, this.disposable, this.sink) }