avoid-passing-async-when-sync-expected
Same as avoid-passing-async-when-sync-expected in Dart Code Metrics
- Group
- Suspicious
- Path
lint/suspicious/avoid-passing-async-when-sync-expected- Default
- On (recommended)
- Origin
- Dart Code Metrics
- Rule
- 108 of 512
Flags an async closure passed to a proven synchronous callback parameter.
Invalid
// Bad: passing async function to sync parameter
void processSync(void Function() callback) {
callback();
}
void example() {
processSync(() async {
await Future.delayed(Duration(seconds: 1));
print('Done');
});
}
class Handler {
void setup(void Function(String) handler) {
handler('test');
}
void badSetup() {
setup((value) async {
await processAsync(value);
});
}
}
void executeCallback(String Function(int) fn) {
print(fn(42));
}
void misuse() {
executeCallback((n) async {
await delay();
return '$n';
});
}
// More violations
void performAction(void Function(String, int) callback) {
callback('test', 42);
}
void badAction() {
performAction((name, count) async {
await Future.delayed(Duration(milliseconds: 100));
print('$name: $count');
});
}
class DataLoader {
void loadData(String Function() fetcher) {
final data = fetcher();
print(data);
}
void loadBad() {
loadData(() async {
await Future.delayed(Duration(seconds: 1));
return 'data';
});
}
}
void namedCallback({required void Function() callback}) {}
void badNamed() {
namedCallback(callback: () async {});
}void example() { processSync(() async { void badSetup() { setup((value) async {void misuse() { executeCallback((n) async {void badAction() { performAction((name, count) async { void loadBad() { loadData(() async {void badNamed() { namedCallback(callback: () async {});Valid
// Good: passing sync function to sync parameter
void processSync(void Function() callback) {
callback();
}
void example() {
processSync(() {
print('Done');
});
}
class Handler {
void setup(void Function(String) handler) {
handler('test');
}
void goodSetup() {
setup((value) {
processSync(value);
});
}
}
void executeCallback(String Function(int) fn) {
print(fn(42));
}
void goodUse() {
executeCallback((n) {
return '$n';
});
}
// OK: async callback passed to async parameter
void processAsync(Future<void> Function() callback) async {
await callback();
}
void asyncToAsync() {
processAsync(() async {
await Future.delayed(Duration(seconds: 1));
print('Done');
});
}
// OK: extracting async logic separately
void separated(void Function() callback) {
callback();
}
void _asyncWork() async {
await Future.delayed(Duration(seconds: 1));
}
void extract() {
separated(() {
_asyncWork(); // fire and forget (or capture result)
});
}
// Good: passing sync callbacks to sync parameters
void performAction(void Function(String, int) callback) {
callback('test', 42);
}
void goodAction() {
performAction((name, count) {
print('$name: $count');
});
}
// Good: using named function for sync callback
class DataLoader {
String _fetchData() {
return 'data';
}
void loadData(String Function() fetcher) {
final data = fetcher();
print(data);
}
void loadGood() {
loadData(_fetchData);
}
}
// Good: sync arrow function
void processItems(void Function(String) handler) {
handler('item');
}
void goodProcess() {
processItems((item) => print('Processing: $item'));
}
void shadowedCallee() {
void processSync(Future<void> Function() callback) {}
processSync(() async {});
}
void namedAsync({required Future<void> Function() callback}) {}
void goodNamed() {
namedAsync(callback: () async {});
}Configure avoid-passing-async-when-sync-expected
Set its severity in falcon.json. See the configuration guide.
{
"linter": {
"rules": {
"suspicious": {
"avoid-passing-async-when-sync-expected": "error"
}
}
}
}Or silence one occurrence with a suppression comment; the reason is required.
// falcon-ignore lint/suspicious/avoid-passing-async-when-sync-expected: <reason>More suspicious rules
- avoid-passing-bloc-to-blocbloc
Rejects direct Bloc and Cubit arguments to other blocs.
- avoid-passing-bloc-to-widgetbloc
Rejects direct Bloc and Cubit arguments to Flutter widget constructors.
- avoid-passing-build-context-to-blocsbloc
Keeps Flutter
BuildContextarguments outside Bloc and Cubit APIs. - avoid-print
avoid_printrecommendedflutterFlags calls and callback arguments resolving to
dart:core'sprint. - avoid-referencing-subclasses
Keeps base classes independent from their transitive subclasses.
- avoid-returning-null-for-void
avoid_returning_null_for_voidrecommendedFlags
return null;(and=> nullbodies) in synchronousvoidfunctions and asynchronousFuture<void>functions. - avoid-shadowed-extension-methods
Flags extension instance methods and accessors hidden by their target's members.
- avoid-shadowing
Flags local bindings and parameters that hide an enclosing type's member.