Index: corelib/src/implementation/future_implementation.dart |
=================================================================== |
--- corelib/src/implementation/future_implementation.dart (revision 8248) |
+++ corelib/src/implementation/future_implementation.dart (working copy) |
@@ -24,16 +24,22 @@ |
/** |
* Listeners waiting to receive the value of this future. |
*/ |
- final List<Function> _listeners; |
+ final List<Function> _successListeners; |
/** |
* Exception handlers waiting for exceptions. |
*/ |
final List<Function> _exceptionHandlers; |
+ /** |
+ * Listeners waiting to be called when the future completes. |
+ */ |
+ final List<Function> _completionListeners; |
+ |
FutureImpl() |
- : _listeners = [], |
- _exceptionHandlers = []; |
+ : _successListeners = [], |
+ _exceptionHandlers = [], |
+ _completionListeners = []; |
factory FutureImpl.immediate(T value) { |
final res = new FutureImpl(); |
@@ -66,11 +72,11 @@ |
return isComplete && _exception === null; |
} |
- void then(void onComplete(T value)) { |
+ void then(void onSuccess(T value)) { |
if (hasValue) { |
- onComplete(value); |
+ onSuccess(value); |
} else if (!isComplete) { |
- _listeners.add(onComplete); |
+ _successListeners.add(onSuccess); |
} else if (!_exceptionHandled) { |
throw _exception; |
} |
@@ -87,8 +93,25 @@ |
} |
} |
+ void onComplete(void complete(Future<T> future)) { |
+ if (_isComplete) { |
+ try { |
+ complete(this); |
+ } catch (final e) {} |
+ } else { |
+ _completionListeners.add(complete); |
+ } |
+ } |
+ |
void _complete() { |
_isComplete = true; |
+ |
+ for (Function listener in _completionListeners) { |
Jennifer Messerly
2012/06/04 20:11:17
shouldn't this come after we run _exceptionHandler
Bob Nystrom
2012/06/04 20:20:40
+1
sam.mccall
2012/06/04 21:35:57
Yeah, that's probably less surprising. When e.g. a
|
+ try { |
+ listener(this); |
+ } catch (final e) {} |
+ } |
+ |
if (_exception !== null) { |
for (Function handler in _exceptionHandlers) { |
// Explicitly check for true here so that if the handler returns null, |
@@ -101,11 +124,11 @@ |
} |
if (hasValue) { |
- for (Function listener in _listeners) { |
+ for (Function listener in _successListeners) { |
listener(value); |
} |
} else { |
- if (!_exceptionHandled && _listeners.length > 0) { |
+ if (!_exceptionHandled && _successListeners.length > 0) { |
throw _exception; |
} |
} |
@@ -133,14 +156,14 @@ |
Future transform(Function transformation) { |
final completer = new Completer(); |
- handleException((e) { |
- completer.completeException(e); |
- return true; |
- }); |
- then((v) { |
+ this.onComplete((f) { |
Jennifer Messerly
2012/06/04 20:11:17
do you need "this." here?
sam.mccall
2012/06/04 21:35:57
Nope, oops
|
+ if (!f.hasValue) { |
+ completer.completeException(f.exception); |
+ return; |
+ } |
var transformed = null; |
try { |
- transformed = transformation(v); |
+ transformed = transformation(f.value); |
} catch (final e) { |
completer.completeException(e); |
return; |
@@ -152,23 +175,22 @@ |
Future chain(Function transformation) { |
final completer = new Completer(); |
- handleException((e) { |
- completer.completeException(e); |
- return true; |
- }); |
- then((v) { |
+ onComplete((f) { |
+ if (!f.hasValue) { |
+ completer.completeException(f.exception); |
+ return; |
+ } |
var future = null; |
try { |
- future = transformation(v); |
+ future = transformation(f.value); |
} catch (final e) { |
completer.completeException(e); |
return; |
} |
- future.handleException((e) { |
- completer.completeException(e); |
- return true; |
+ future.onComplete((g) { |
+ if (g.hasValue) completer.complete(g.value); |
+ else completer.completeException(g.exception); |
Jennifer Messerly
2012/06/04 20:22:28
This is interesting ... it almost suggests we shou
sam.mccall
2012/06/04 21:35:57
Yeah, I can't see any obvious other uses, so I'm n
Jennifer Messerly
2012/06/04 22:12:49
sgtm
|
}); |
- future.then((b) => completer.complete(b)); |
}); |
return completer.future; |
} |