Refactor Future.await to remove boiler and make it correct in the face of infinity
This commit is contained in:
parent
43031cb94b
commit
824d202b4a
1 changed files with 11 additions and 13 deletions
|
|
@ -843,6 +843,7 @@ class DefaultPromise[T](val timeout: Timeout) extends Promise[T] {
|
|||
|
||||
/**
|
||||
* Must be called inside _lock.lock<->_lock.unlock
|
||||
* Returns true if completed within the timeout
|
||||
*/
|
||||
@tailrec
|
||||
private def awaitUnsafe(waitTimeNanos: Long): Boolean = {
|
||||
|
|
@ -861,26 +862,23 @@ class DefaultPromise[T](val timeout: Timeout) extends Promise[T] {
|
|||
}
|
||||
|
||||
def await(atMost: Duration) = {
|
||||
_lock.lock()
|
||||
if (try { awaitUnsafe(atMost.toNanos min timeLeft()) } finally { _lock.unlock }) this
|
||||
else throw new FutureTimeoutException("Futures timed out after [" + NANOS.toMillis(timeoutInNanos) + "] milliseconds")
|
||||
}
|
||||
|
||||
def await = {
|
||||
_lock.lock()
|
||||
try {
|
||||
if (timeout.duration.isFinite) {
|
||||
if (awaitUnsafe(timeLeft())) this
|
||||
else throw new FutureTimeoutException("Futures timed out after [" + NANOS.toMillis(timeoutInNanos) + "] milliseconds")
|
||||
} else {
|
||||
if (!atMost.isFinite && !timeout.duration.isFinite) { //If wait until infinity
|
||||
while (_value.isEmpty) { _signal.await }
|
||||
this
|
||||
} else { //Limited wait
|
||||
val time = if (!atMost.isFinite) timeLeft() //If atMost is infinity, use preset timeout
|
||||
else if (!timeout.duration.isFinite) atMost.toNanos //If preset timeout is infinite, use atMost
|
||||
else atMost.toNanos min timeLeft() //Otherwise use the smallest of them
|
||||
if (awaitUnsafe(time)) this
|
||||
else throw new FutureTimeoutException("Future timed out after [" + NANOS.toMillis(time) + "] ms")
|
||||
}
|
||||
} finally {
|
||||
_lock.unlock
|
||||
}
|
||||
} finally { _lock.unlock }
|
||||
}
|
||||
|
||||
def await = await(timeout.duration)
|
||||
|
||||
def isExpired: Boolean = if (timeout.duration.isFinite) timeLeft() <= 0 else false
|
||||
|
||||
def value: Option[Either[Throwable, T]] = {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue