private void refresh ( ) { try { // Invoke underlying getTuples unsynchronized. // This way it won't block tuple access, in case it is a long // running or expensive function. final CompletableFuture < ? extends Collection < ResolverTuple > > fut = underlying . getTuples ( ) ; // Publish future, needs synchronization, so close() method can cancel properly. synchronized ( this ) { // We create the whenCompleteAsync continuation with synchronization locked, // because the update code will want to clear the currentFut member-variable. // We must ensure it is set before. currentFut = fut . whenCompleteAsync ( this :: update , SCHEDULER ) ; if ( closed ) // Close may have set close bit while we were creating future. fut . cancel ( false ) ; } } catch ( Exception ex ) { synchronized ( this ) { exception = ex ; } reschedule ( FAILURE_RESCHEDULE_DELAY ) ; } }
Attempt to refresh the resolver result .