Observable Cache

Source Code: https://gist.github.com/4115023

Given: An async operation that returns a value e.g web/service call or complex calculation
When: I request the value multiple times
Then: I only perform the operation once and cache the value

When: I haven’t requested the value
Then: Don’t perform the operation

When: I clear the cached value
Then: requesting the value again performs the async operation again

My current solution:


    public class Cache<T> : IDisposable
    {
        private readonly IConnectableObservable<T> _source;
        private IDisposable _connection;

        public Cache(IObservable<T> source)
        {
            _source = Observable.Create<T>(o => source.Subscribe(o))
                                .Replay(1, Scheduler.Immediate);
        }

        public IObservable<T> GetValue()
        {
            return Observable.Create<T>(o =>
                                         {
                                             var subscription = _source.Subscribe(o);
                                             _connection = _source.Connect();
                                             return subscription;
                                         });
        }

        public void Clear()
        {
            if (_connection != null)
            {
                _connection.Dispose();
                _connection = null;
            }
        }

        public void Dispose()
        {
            Clear();
        }
    }

Advertisements

One thought on “Observable Cache

  1. Nice, I have used something very similar but using AsyncSubject which has the useful behaviour of allowing only one value and caching and returning that for all subsequent subscriptions. Combine that with a ConcurrentDictionary to hold the subjects and you can do the same thing for multiple keyed values (e.g. caching data for different urls).

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s