protected BucketedRollingCounterStream(IHystrixEventStream <Event> stream, int numBuckets, int bucketSizeInMs, Func <Bucket, Event, Bucket> appendRawEventToBucket, Func <Output, Bucket, Output> reduceBucket) : base(stream, numBuckets, bucketSizeInMs, appendRawEventToBucket) { Func <IObservable <Bucket>, IObservable <Output> > reduceWindowToSummary = (window) => { var result = window.Aggregate(EmptyOutputValue, (arg1, arg2) => reduceBucket(arg1, arg2)).Select(n => n); return(result); }; counterSubject = new BehaviorSubject <Output>(EmptyOutputValue); _sourceStream = bucketedStream // stream broken up into buckets .Window(numBuckets, 1) // emit overlapping windows of buckets .FlatMap((w) => reduceWindowToSummary(w)) // convert a window of bucket-summaries into a single summary .OnSubscribe(() => { _isSourceCurrentlySubscribed.Value = true; }) .OnDispose(() => { _isSourceCurrentlySubscribed.Value = false; }) .Publish().RefCount(); // multiple subscribers should get same data }
protected RollingDistributionStream(IHystrixEventStream <Event> stream, int numBuckets, int bucketSizeInMs, Func <LongHistogram, Event, LongHistogram> addValuesToBucket) { var emptyDistributionsToStart = new List <LongHistogram>(); for (var i = 0; i < numBuckets; i++) { emptyDistributionsToStart.Add(CachedValuesHistogram.GetNewHistogram()); } Func <IObservable <Event>, IObservable <LongHistogram> > reduceBucketToSingleDistribution = (bucket) => { var result = bucket.Aggregate(CachedValuesHistogram.GetNewHistogram(), (arg1, arg2) => addValuesToBucket(arg1, arg2)).Select(n => n); return(result); }; _rollingDistributionStream = stream .Observe() .Window(TimeSpan.FromMilliseconds(bucketSizeInMs), NewThreadScheduler.Default) // stream of unaggregated buckets .SelectMany((d) => reduceBucketToSingleDistribution(d)) // stream of aggregated Histograms .StartWith(emptyDistributionsToStart) // stream of aggregated Histograms that starts with n empty .Window(numBuckets, 1) // windowed stream: each OnNext is a stream of n Histograms .SelectMany((w) => ReduceWindowToSingleDistribution(w)) // reduced stream: each OnNext is a single Histogram .Map((h) => CacheHistogramValues(h)) // convert to CachedValueHistogram (commonly-accessed values are cached) .Publish().RefCount(); }
protected BucketedCounterStream(IHystrixEventStream <Event> inputEventStream, int numBuckets, int bucketSizeInMs, Func <Bucket, Event, Bucket> appendRawEventToBucket) { this.numBuckets = numBuckets; this.bucketSizeInMs = bucketSizeInMs; _reduceBucketToSummary = (eventsObservable) => { var result = eventsObservable.Aggregate(EmptyBucketSummary, (arg1, arg2) => appendRawEventToBucket(arg1, arg2)).Select(n => n); return(result); }; IList <Bucket> emptyEventCountsToStart = new List <Bucket>(); for (var i = 0; i < numBuckets; i++) { emptyEventCountsToStart.Add(EmptyBucketSummary); } bucketedStream = Observable.Defer(() => { return(inputEventStream .Observe() .Window(TimeSpan.FromMilliseconds(bucketSizeInMs), NewThreadScheduler.Default) // bucket it by the counter window so we can emit to the next operator in time chunks, not on every OnNext .SelectMany((b) => { return _reduceBucketToSummary(b); }) .StartWith(emptyEventCountsToStart)); // start it with empty arrays to make consumer logic as generic as possible (windows are always full) }); }
protected BucketedCumulativeCounterStream(IHystrixEventStream <Event> stream, int numBuckets, int bucketSizeInMs, Func <Bucket, Event, Bucket> reduceCommandCompletion, Func <Output, Bucket, Output> reduceBucket) : base(stream, numBuckets, bucketSizeInMs, reduceCommandCompletion) { this.counterSubject = new BehaviorSubject <Output>(EmptyOutputValue); this.sourceStream = bucketedStream .Scan(EmptyOutputValue, (arg1, arg2) => reduceBucket(arg1, arg2)) .Skip(numBuckets) .OnSubscribe(() => { isSourceCurrentlySubscribed.Value = true; }) .OnDispose(() => { isSourceCurrentlySubscribed.Value = false; }) .Publish().RefCount(); // multiple subscribers should get same data }
protected RollingConcurrencyStream(IHystrixEventStream <HystrixCommandExecutionStarted> inputEventStream, int numBuckets, int bucketSizeInMs) { List <int> emptyRollingMaxBuckets = new List <int>(); for (int i = 0; i < numBuckets; i++) { emptyRollingMaxBuckets.Add(0); } rollingMaxStream = inputEventStream .Observe() .Map((arg) => GetConcurrencyCountFromEvent(arg)) .Window(TimeSpan.FromMilliseconds(bucketSizeInMs)) .SelectMany((arg) => ReduceStreamToMax(arg)) .StartWith(emptyRollingMaxBuckets) .Window(numBuckets, 1) .SelectMany((arg) => ReduceStreamToMax(arg)) .Publish().RefCount(); }