Fix implicit casts (#97)
- Add an explicit `StackTrace` on arguments to `onError` callback
arguments since they are statically `Function` so no type inference
flows into argument types.
- Add a couple explicit casts.
- Add explicit types on some completers in test code.
- Use `Queue.of` constructor to allow type inference to flow.
- Fix a broken argument type on `DelegatingFuture`.
- Add some missing generic type arguments on fields or arguments.
diff --git a/analysis_options.yaml b/analysis_options.yaml
index f217697..1f502a5 100644
--- a/analysis_options.yaml
+++ b/analysis_options.yaml
@@ -1,5 +1,7 @@
include: package:pedantic/analysis_options.yaml
analyzer:
+ strong-mode:
+ implicit-casts: false
errors:
todo: ignore
# Lint provided by pkg:pedantic – should fix this!
diff --git a/lib/src/cancelable_operation.dart b/lib/src/cancelable_operation.dart
index bac8f9b..cbbb8d0 100644
--- a/lib/src/cancelable_operation.dart
+++ b/lib/src/cancelable_operation.dart
@@ -50,7 +50,7 @@
value.then((value) {
controller.add(value);
controller.close();
- }, onError: (error, stackTrace) {
+ }, onError: (error, StackTrace stackTrace) {
controller.addError(error, stackTrace);
controller.close();
});
@@ -104,7 +104,7 @@
completer._cancel();
}
}
- }, onError: (error, stackTrace) {
+ }, onError: (error, StackTrace stackTrace) {
if (!completer.isCanceled) {
if (onError != null) {
completer.complete(Future.sync(() => onError(error, stackTrace)));
@@ -170,7 +170,7 @@
///
/// If [value] is a [Future], this will complete to the result of that
/// [Future] once it completes.
- void complete([value]) {
+ void complete([FutureOr<T> value]) {
if (_isCompleted) throw StateError('Operation already completed');
_isCompleted = true;
@@ -180,16 +180,17 @@
return;
}
+ final future = value as Future<T>;
if (_isCanceled) {
// Make sure errors from [value] aren't top-leveled.
- value.catchError((_) {});
+ future.catchError((_) {});
return;
}
- value.then((result) {
+ future.then((result) {
if (_isCanceled) return;
_inner.complete(result);
- }, onError: (error, stackTrace) {
+ }, onError: (error, StackTrace stackTrace) {
if (_isCanceled) return;
_inner.completeError(error, stackTrace);
});
diff --git a/lib/src/delegate/future.dart b/lib/src/delegate/future.dart
index 8c5dd04..984caf6 100644
--- a/lib/src/delegate/future.dart
+++ b/lib/src/delegate/future.dart
@@ -33,7 +33,8 @@
_future.then(onValue, onError: onError);
@override
- Future<T> whenComplete(FutureOr action) => _future.whenComplete(action);
+ Future<T> whenComplete(FutureOr Function() action) =>
+ _future.whenComplete(action);
@override
Future<T> timeout(Duration timeLimit, {FutureOr<T> Function() onTimeout}) =>
diff --git a/lib/src/future_group.dart b/lib/src/future_group.dart
index a6abff0..402ae46 100644
--- a/lib/src/future_group.dart
+++ b/lib/src/future_group.dart
@@ -76,7 +76,7 @@
if (!_closed) return null;
if (_onIdleController != null) _onIdleController.close();
_completer.complete(_values);
- }).catchError((error, stackTrace) {
+ }).catchError((error, StackTrace stackTrace) {
if (_completer.isCompleted) return null;
_completer.completeError(error, stackTrace);
});
diff --git a/lib/src/result/release_sink.dart b/lib/src/result/release_sink.dart
index 78d0f42..5d8267a 100644
--- a/lib/src/result/release_sink.dart
+++ b/lib/src/result/release_sink.dart
@@ -8,9 +8,9 @@
/// Used by [Result.releaseSink].
class ReleaseSink<T> implements EventSink<Result<T>> {
- final EventSink _sink;
+ final EventSink<T> _sink;
- ReleaseSink(EventSink<T> sink) : _sink = sink;
+ ReleaseSink(this._sink);
@override
void add(Result<T> result) {
diff --git a/lib/src/result/result.dart b/lib/src/result/result.dart
index e04da9f..e604782 100644
--- a/lib/src/result/result.dart
+++ b/lib/src/result/result.dart
@@ -85,7 +85,8 @@
/// Errors have been converted to an [ErrorResult] value.
static Future<Result<T>> capture<T>(Future<T> future) {
return future.then((value) => ValueResult(value),
- onError: (error, stackTrace) => ErrorResult(error, stackTrace));
+ onError: (error, StackTrace stackTrace) =>
+ ErrorResult(error, stackTrace));
}
/// Captures each future in [elements],
@@ -111,7 +112,7 @@
}
});
} else {
- results.add(Result<T>.value(element));
+ results.add(Result<T>.value(element as T));
}
}
if (pending == 0) {
diff --git a/lib/src/stream_sink_completer.dart b/lib/src/stream_sink_completer.dart
index 3b31576..ebfd717 100644
--- a/lib/src/stream_sink_completer.dart
+++ b/lib/src/stream_sink_completer.dart
@@ -27,7 +27,7 @@
final StreamSink<T> sink = _CompleterSink<T>();
/// Returns [sink] typed as a [_CompleterSink].
- _CompleterSink<T> get _sink => sink;
+ _CompleterSink<T> get _sink => sink as _CompleterSink<T>;
/// Convert a `Future<StreamSink>` to a `StreamSink`.
///
diff --git a/test/result/result_captureAll_test.dart b/test/result/result_captureAll_test.dart
index ba8305a..8e79872 100644
--- a/test/result/result_captureAll_test.dart
+++ b/test/result/result_captureAll_test.dart
@@ -138,7 +138,7 @@
var all = Result.captureAll<int>(cs.map((c) => c.future));
var rnd = Random(seed);
var throwFlags = rnd.nextInt(1 << n); // Bit-flag for throwing.
- bool throws(index) => (throwFlags & (1 << index)) != 0;
+ bool throws(int index) => (throwFlags & (1 << index)) != 0;
var expected = List.generate(n, (x) => throws(x) ? err(x) : res(x));
expect(all, completion(expected));
diff --git a/test/result/result_flattenAll_test.dart b/test/result/result_flattenAll_test.dart
index 890b2d0..c0a8603 100644
--- a/test/result/result_flattenAll_test.dart
+++ b/test/result/result_flattenAll_test.dart
@@ -7,7 +7,7 @@
final someStack = StackTrace.current;
Result<T> res<T>(T n) => Result<T>.value(n);
-Result err(n) => ErrorResult('$n', someStack);
+Result<T> err<T>(n) => ErrorResult('$n', someStack);
/// Helper function creating an iterable of results.
Iterable<Result<int>> results(int count,
@@ -22,7 +22,7 @@
}
void main() {
- void expectAll(result, expectation) {
+ void expectAll<T>(Result<T> result, Result<T> expectation) {
if (expectation.isError) {
expect(result, expectation);
} else {
diff --git a/test/result/result_test.dart b/test/result/result_test.dart
index 92fc6b0..adbc445 100644
--- a/test/result/result_test.dart
+++ b/test/result/result_test.dart
@@ -173,7 +173,7 @@
test('capture stream', () {
var c = StreamController<int>();
var stream = Result.captureStream(c.stream);
- var expectedList = Queue.from(
+ var expectedList = Queue.of(
[Result.value(42), Result.error('BAD', stack), Result.value(37)]);
void listener(Result actual) {
expect(expectedList.isEmpty, isFalse);
@@ -197,7 +197,7 @@
Result<int>.value(37)
];
// Expect the data events, and an extra error event.
- var expectedList = Queue.from(events)..add(Result.error('BAD2', stack));
+ var expectedList = Queue.of(events)..add(Result.error('BAD2', stack));
void dataListener(int v) {
expect(expectedList.isEmpty, isFalse);
@@ -260,7 +260,7 @@
});
test('handle unary', () {
- ErrorResult result = Result.error('error', stack);
+ var result = ErrorResult('error', stack);
var called = false;
result.handle((error) {
called = true;
@@ -270,7 +270,7 @@
});
test('handle binary', () {
- ErrorResult result = Result.error('error', stack);
+ var result = ErrorResult('error', stack);
var called = false;
result.handle((error, stackTrace) {
called = true;
@@ -281,7 +281,7 @@
});
test('handle unary and binary', () {
- ErrorResult result = Result.error('error', stack);
+ var result = ErrorResult('error', stack);
var called = false;
result.handle((error, [stackTrace]) {
called = true;
@@ -292,7 +292,7 @@
});
test('handle neither unary nor binary', () {
- ErrorResult result = Result.error('error', stack);
+ var result = ErrorResult('error', stack);
expect(() => result.handle(() => fail('unreachable')), throwsA(anything));
expect(() => result.handle((a, b, c) => fail('unreachable')),
throwsA(anything));
diff --git a/test/stream_completer_test.dart b/test/stream_completer_test.dart
index 2cf6728..0cd210a 100644
--- a/test/stream_completer_test.dart
+++ b/test/stream_completer_test.dart
@@ -74,9 +74,9 @@
});
test('cancel new stream before source is done', () async {
- var completer = StreamCompleter();
+ var completer = StreamCompleter<int>();
var lastEvent = -1;
- var controller = StreamController();
+ var controller = StreamController<int>();
StreamSubscription subscription;
subscription = completer.stream.listen((value) {
expect(value, lessThan(3));
diff --git a/test/stream_zip_test.dart b/test/stream_zip_test.dart
index f462996..19c3dec 100644
--- a/test/stream_zip_test.dart
+++ b/test/stream_zip_test.dart
@@ -15,9 +15,9 @@
/// Make a [Stream] from an [Iterable] by adding events to a stream controller
/// at periodic intervals.
-Stream mks(Iterable iterable) {
+Stream<T> mks<T>(Iterable<T> iterable) {
var iterator = iterable.iterator;
- var controller = StreamController();
+ var controller = StreamController<T>();
// Some varying time between 3 and 10 ms.
var ms = ((++ctr) * 5) % 7 + 3;
Timer.periodic(Duration(milliseconds: ms), (Timer timer) {
@@ -221,7 +221,8 @@
controller..add(7)..add(8)..add(9);
// Transformer that puts error into controller when one of the first two
// streams have sent a done event.
- var trans = StreamTransformer.fromHandlers(handleDone: (EventSink s) {
+ var trans =
+ StreamTransformer<int, int>.fromHandlers(handleDone: (EventSink s) {
Timer.run(() {
controller.addError('BAD-6');
});
diff --git a/test/utils.dart b/test/utils.dart
index b09d06b..a99fe9b 100644
--- a/test/utils.dart
+++ b/test/utils.dart
@@ -22,10 +22,10 @@
// TODO(nweiz): Use the version of this in test when test#418 is fixed.
/// A matcher that runs a callback in its own zone and asserts that that zone
/// emits an error that matches [matcher].
-Matcher throwsZoned(matcher) => predicate((callback) {
+Matcher throwsZoned(matcher) => predicate((void Function() callback) {
var firstError = true;
runZoned(callback,
- onError: expectAsync2((error, stackTrace) {
+ onError: expectAsync2((error, StackTrace stackTrace) {
if (firstError) {
expect(error, matcher);
firstError = false;
@@ -89,7 +89,7 @@
Future get done => _doneCompleter.future;
final _doneCompleter = Completer();
- final Function _onDone;
+ final void Function() _onDone;
/// Creates a new sink.
///