Linter: Lint against invalid use of `Future.value` or `Completer.complete`

Created on 1 Jun 2021  路  2Comments  路  Source: dart-lang/linter

Describe the rule you'd like to see implemented

The optional parameters to Future.value, Completer.complete (and perhaps other functions that I'm not aware of) should be considered required when T excludes null.

For instance, both Future<int>.value() or Future<int>.value(null) are valid at compile-time because the parameter is declared to be nullable for backwards compatibility.
The SDK implementation will cast those values though, so they are guaranteed to throw at runtime.

I think we should have a lint to warn us about those invocations. It should apply to Future.value and Completer.complete when

  • the library making the call is opted into null-safety
  • T is resolved to a type that excludes null
  • the argument is absent, or not assignable to T while being assignable to T?

Examples

Future<int>.value(); // LINT!
Future<int?>.value(); 
Future<int>.value(null); // LINT!
Future<int?>.value(null);

int? someVariable;
String? anotherVariable;
Future<int>.value(someVariable); // LINT!
Future<int?>.value(someVariable);
Future<int>.value(anotherVariable); // already a compile-time error, let's not lint it as well

var completer = Completer<int>();
completer.complete(); // LINT
completer.complete(null); // LINT

var nullableCompleter = Completer<int?>();
nullableCompleter.complete();
nullableCompleter.complete(null);
// @dart=2.11
Future<int>.value(); // ok

Additional context

I'm not sure if there are other SDK methods which could benefit from this lint, or if we want to make it an annotation that third-party code could use as well, e.g.

external factory Future.value([@nullableForBackwardsCompatibility T? value]);

See also: The language discussion at https://github.com/dart-lang/language/issues/1299

I am happy to implement the simple form of this lint myself if there isn't anything like it yet.

enhancement lint request

Most helpful comment

I think we'd implement this as a Hint (default opt-in) since I think there is no false positive. https://github.com/dart-lang/sdk/issues/45319

All 2 comments

Another one is the tear-off, which I faced:

var completer = Completer<int>();

stream.listen(
  (_) {},
  onDone: completer.complete,
)

I think we'd implement this as a Hint (default opt-in) since I think there is no false positive. https://github.com/dart-lang/sdk/issues/45319

Was this page helpful?
0 / 5 - 0 ratings