-
Notifications
You must be signed in to change notification settings - Fork 213
An async function declared to return FutureOr<T> can't directly return a T #606
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
The important bit isn't if the
It would be breaking for a method marked |
Oh, right, good point. In principle, I feel like it's fair game for a function declared to return In practice, since the current behavior is to always return a FutureOr<int> foo() async => 42;
var x = await foo(); and that code should still work even if I think cases where it would break:
Are there others? Anyway, even though it'd be breaking, I think it's still maybe worth considering for, say, Dart 3 or something. (dart-sync-async was breaking too.) Alternatively maybe we could add new syntax to opt-in to such behavior (e.g. |
There could be places where the value flows through a references that is statically As long as we only did this if the return type was declared a |
Side note: I very highly recommend never using a If you do, your API clients must always either check whether it is a value or a future, and have two code paths, or use (It's fine to accept a |
As for the change to The return type is not what determines the body's behavior, it's the It would be highly confusing if FutureOr<int> tricky() async {
if (test) await something();
return 2;
} Here you want the function to return the integer 2 if the |
Hi @lrhn What about something like an async block: FutureOr<int> tricky() {
if (test) async {
await something();
}
return 2;
} That way async semantics don't change, await still wraps the result of |
I don't see how that The From a compiler perspecitive, it's fine. We already have to handle synchronous completions specially to avoid completing the returned future immediately. We could allow returning a value instead. I just don't want to. Returning |
Why? The alternative is relying on a custom implementation of |
Part of the proposal is to make it easier for the API clients to make this check without having to use FutureOr<int> transformResult() {
final someFutureOr = getSomethingFromAPIOrCache();
if (someFutureOr is Future) async {
return transform(await someFutureOr());
}
return transform(someFutureOr);
}
Handling a FutureOr as extra work on the library is fine, and we can work around checking the types and using For example users expect: callFunctionThatTakesFutureOrFunction(() async {
if (condition) {
return 2
}
return await something();
}); To return synchronously when condition is true, since it obviously does not need to be a Future. |
This could also link with #1874 which could allow macros to implement a custom Like: FutureOr<T> futureOr;
T result = @maybeAwait(futureOr); which decomposes into: FutureOr<T> futureOr;
T result = futureOr is T ? futureOr : await futureOr; |
I'd recommend just always doing
No. I expect them to pass either a function returning Mixing synchronous and asynchronous computations in a way that preserves synchronousness was, and is, not a goal. (I guess I'm saying that I don't agree with the goal this request, and making it a language feature that you can create a |
Currently declaring an
async
function as returningFutureOr<T>
is allowed but seems misleading and useless (it's no different than returningFuture<T>
) except maybe in the case of overriding a method already declared to returnFutureOr<T>
. That is, if I have:then
foo() is Future<int>
is true and andfoo() is int
is not, and the only way to extract the value is viaawait
/then()
.Motivation:
I want to have a function:
with the expectation that calling
foo(false)
will return anint
. (The intent is avoid forcingawait
/then()
onto the caller.)A workaround is to transform the code to avoid using
async
:Could the compiler do such a transformation automatically?
The text was updated successfully, but these errors were encountered: