title: How can I "force" some kind of backpressure to avoid multiple executions in rxjava?
body: <p>I have a piece of code who's work is to update a local cache. There are two triggers to this cache update:</p>
  
  <ol>
  <li>At a fixed interval</li>
  <li>When requested</li>
  </ol>
  
  <p>So here's a basic example on how I did this.</p>
  
  <pre class="lang-java prettyprint-override"><code>forceReloadEvents = new SerializedSubject&lt;Long, Long&gt;(PublishSubject.&lt;Long&gt; create());
  dataUpdates = Observable
      .merge(forceReloadEvents, Observable.timer(0, pullInterval, TimeUnit.SECONDS))
      .flatMap(new Func1&lt;Long, Observable&lt;Boolean&gt;&gt;() {
          @Override
          public Observable&lt;Boolean&gt; call(Long t) {
              return reloadData(); // operation that may take long
          }
      })
      .publish();
  
  dataUpdates.subscribe();
  dataUpdates.connect();
  </code></pre>
  
  <p>Then later i have</p>
  
  <pre class="lang-java prettyprint-override"><code>public void forceReload() {
      final CountDownLatch cdl = new CountDownLatch(1);
  
      dataUpdates
          .take(1)
          .subscribe(
              new Action1&lt;Boolean&gt;() {
                  @Override
                  public void call(Boolean b) {
                      cdl.countDown();
                  }
              }
          );
  
      forceReloadEvents.onNext(-1L);
  
      try {
          cdl.await();
      } catch (InterruptedException e) {
          throw new RuntimeException(e);
      }
  }
  </code></pre>
  
  <p>This works but the problem is when I start to have multiple concurrent calls to <code>forceReload()</code> :  There will be no concurrent execution of <code>reloadData()</code> but the elements will queue up and the process will loop on reloading data until all the events sent to <code>forceReloadEvents</code> have been consumed even though <code>forceReload()</code> already completed due to previous events releasing the <code>CountDownLatch</code>.</p>
  
  <p>I wanted to use <code>onBackPressureDrop</code> but it seems there's no induced backpressure and nothing is dropped. What I'd like is some way to force  backpressure so that the merge understands that only one element can be processed at a time and that any subsequent event must be dropped until the current execution is done.</p>
  
  <p>I thought about using <code>buffer</code> or <code>throttleFirst</code> too but I don't want to force a specific time between each event and i'd rather have this auto-scaling depending on the time it takes to reload the cache. You can think of it as <code>throttleFirst</code> until <code>reloadData</code> has completed.</p>