DAS: Use correct nullability in add_return_type

Fixes https://github.com/dart-lang/sdk/issues/54865

The nullability of return types of async and generator functions is not
based on the nullability of the returned or yielded values.

Change-Id: Ieae534dbf64135129b9891b7db047f5617401021
Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/501121
Commit-Queue: Samuel Rawlins <srawlins@google.com>
Reviewed-by: Keerti Parthasarathy <keertip@google.com>
This commit is contained in:
Sam Rawlins
2026-05-13 08:35:17 -07:00
committed by dart-scoped@luci-project-accounts.iam.gserviceaccount.com
parent 57da93ad4f
commit 6fdfcc7ed4
2 changed files with 43 additions and 5 deletions
@@ -18,8 +18,7 @@ class AddReturnType extends ResolvedCorrectionProducer {
AddReturnType({required super.context});
@override
CorrectionApplicability get applicability =>
CorrectionApplicability.automatically;
CorrectionApplicability get applicability => .automatically;
@override
AssistKind get assistKind => DartAssistKind.addReturnType;
@@ -98,18 +97,18 @@ class AddReturnType extends ResolvedCorrectionProducer {
if (body.isGenerator) {
return typeProvider.streamElement.instantiate(
typeArguments: [baseType],
nullabilitySuffix: baseType.nullabilitySuffix,
nullabilitySuffix: .none,
);
} else {
return typeProvider.futureElement.instantiate(
typeArguments: [baseType],
nullabilitySuffix: baseType.nullabilitySuffix,
nullabilitySuffix: .none,
);
}
} else if (body.isGenerator) {
return typeProvider.iterableElement.instantiate(
typeArguments: [baseType],
nullabilitySuffix: baseType.nullabilitySuffix,
nullabilitySuffix: .none,
);
}
return baseType;
@@ -184,6 +184,45 @@ String f() {
''');
}
Future<void> test_topLevelFunction_block_async() async {
await resolveTestCode('''
^f(String? s) async {
return s;
}
''');
await assertHasAssist('''
Future<String?> f(String? s) async {
return s;
}
''');
}
Future<void> test_topLevelFunction_block_asyncStar() async {
await resolveTestCode('''
^f(String? s) async* {
yield s;
}
''');
await assertHasAssist('''
Stream<String?> f(String? s) async* {
yield s;
}
''');
}
Future<void> test_topLevelFunction_block_syncStar() async {
await resolveTestCode('''
^f(String? s) sync* {
yield s;
}
''');
await assertHasAssist('''
Iterable<String?> f(String? s) sync* {
yield s;
}
''');
}
Future<void> test_topLevelFunction_expression() async {
await resolveTestCode('''
^f() => '';