If the completion handler parameter has a default
argument, mark the resulting async function as
`@discardableResult`, as the caller may not care
about the result.
rdar://79190170
The async refactoring may perform recursive AST
walks in cases such as transforming the body of
a hoisted closure. Make sure this can be handled
by the logic tracking the ASTWalker in the
SourceEntityWalker, such that we don't crash when
later converting the call to a completion callback.
rdar://78693050
Previously we were unconditionally dropping a
return statement if it was the last node, which
could cause us to inadvertently drop the result
expression as well. Instead, only drop bare
'return' statements.
rdar://77789360
It's possible the user has already written an
explicit return for the call to the completion
handler. In that case, avoid adding another return.
rdar://77789360
Previously we would drop comments between nodes in
a BraceStmt, as we printed each node out individually.
To remedy this, always make sure we scan backwards
to find any preceding comments attached to a node,
and also keep track of any SourceLocs which we
don't print, but may have comments attached which
we want to preserve.
rdar://77401810
Convert function to async currently only adds "async" to the function and runs the convert call refactoring on the body.
This was intentional, but it turns out to be somewhat confusing. Instead, run the same refactoring as the add async alternative refactoring but just replace rather than add.
Resolves rdar://77103049
When converting a function with a completion handler
that has a Void success parameter, e.g
`(Void?, Error?) -> Void`, or more likely a
`Result<Void, Error>` parameter, make sure to omit
the `-> Void` from the resulting async function
conversion.
In addition, strip any Void bindings from an async
function call, and any explicit Void return values
from inside the async function.
Resolves rdar://75189289
The replacement range was `FunctionDecl::getRange`, which does not
include attributes. This would cause attributes to be duplicated when
converting a function to async. Override the start with the attribute
start instead so that they are replaced as well.
Resolves rdar://74063741
Adds three refactorings intended to help users migrate their existing
code to use the new async language features:
1. Convert call to use async alternative
2. Convert function to async
3. Add async alternative function
A function is considered to have an async alternative if it has a void
return type and has a void returning closure as its last parameter. A
method to explicitly mark functions as having an async alternative may
be added to make this more accurate in the future (required for eg.
a warning about a call to the non-async version of a function in an
async context).
(1) converts a call to use the new `await` async language syntax. If the
async alternative throws, it will also add `try`. The closure itself is
hoisted out of the call, see the comments on
`AsyncConversionStringBuilder` for specifics.
(2) converts a whole function to `async`, using (1) to convert any calls
in the function to their async alternatives. (3) is similar to (2), but
instead *adds* a function and replaces calls to its
completion/handler/callback closure parameter with `return` or `throws`.
Resolves rdar://68254700