Alexei
Alexei

Reputation: 15646

Why print not wait result of async function?

In my Flutter project:

Future<Position> getCurrentPosition({
    LocationAccuracy desiredAccuracy = LocationAccuracy.best,
    GeolocationPermission locationPermissionLevel =
        GeolocationPermission.location,
  }) async {

in my class:

import 'package:geolocator/geolocator.dart';
import 'package:logger/logger.dart';

class TestAsync {
  var _logger = Logger();

  Future<void> main() async {
    _logger.d("TestAsync: main: Fetching user order...");
    _logger.d(await createOrderMessage());
  }

  Future<String> createOrderMessage() async {
    _logger.d("TestAsync: createOrderMessage: BEFORE_WAIT ");
    var order = await fetchUserOrder();
    return 'TestAsync: createOrderMessage: AFTER_WAIT Your order is: $order';
  }

  Future<Position> fetchUserOrder() async {
    _logger.d("TestAsync: fetchUserOrder: ");
    for (int index = 0; index < 10; index++) {
      Geolocator()
          .getCurrentPosition(desiredAccuracy: LocationAccuracy.high)
          .then((value) {
            _logger.d("TestAsync: fetchUserOrder: index = $index then_value = $value");
      });
    }
  }
}

As you can see I use async function fetchUserOrder. And to call this function I use

 await fetchUserOrder();

So the result must be:

  1. Execute fetchUserOrder

  2. After finish fetchUserOrder only then print:

    TestAsync: createOrderMessage: AFTER_WAIT Your order is...

But the result is another

I/flutter (11975): │ 🐛 createState:
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   _SignInScreenState.initState (package:flutter_sample/screens/signin_screen.dart:29:13)
I/flutter (11975): │ #1   StatefulElement._firstBuild (package:flutter/src/widgets/framework.dart:4649:58)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 initState:
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   TestAsync.main (package:flutter_sample/service/TestAsync.dart:26:13)
I/flutter (11975): │ #1   _SignInScreenState.initState (package:flutter_sample/screens/signin_screen.dart:36:21)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 TestAsync: main: Fetching user order...
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   TestAsync.createOrderMessage (package:flutter_sample/service/TestAsync.dart:31:13)
I/flutter (11975): │ #1   TestAsync.main (package:flutter_sample/service/TestAsync.dart:27:21)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 TestAsync: createOrderMessage: BEFORE_WAIT 
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   TestAsync.fetchUserOrder (package:flutter_sample/service/TestAsync.dart:39:13)
I/flutter (11975): │ #1   TestAsync.createOrderMessage (package:flutter_sample/service/TestAsync.dart:33:23)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 TestAsync: fetchUserOrder: 
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   _SignInScreenState.build (package:flutter_sample/screens/signin_screen.dart:41:13)
I/flutter (11975): │ #1   StatefulElement.build (package:flutter/src/widgets/framework.dart:4628:28)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 build:
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   TestAsync.main (package:flutter_sample/service/TestAsync.dart:27:13)
I/flutter (11975): │ <asynchronous suspension>
I/flutter (11975): │ #1   _SignInScreenState.initState (package:flutter_sample/screens/signin_screen.dart:36:21)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 TestAsync: createOrderMessage: AFTER_WAIT Your order is: null
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   TestAsync.fetchUserOrder.() (package:flutter_sample/service/TestAsync.dart:44:21)
I/flutter (11975): │ #1   _rootRunUnary (dart:async/zone.dart:1198:47)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 TestAsync: fetchUserOrder: index = 1 then_value = Lat: 37.4219983, Long: -122.084
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   TestAsync.fetchUserOrder.() (package:flutter_sample/service/TestAsync.dart:44:21)
I/flutter (11975): │ #1   _rootRunUnary (dart:async/zone.dart:1198:47)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 TestAsync: fetchUserOrder: index = 0 then_value = Lat: 37.4219983, Long: -122.084
I/flutter (11975): └───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): ┌───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
I/flutter (11975): │ #0   TestAsync.fetchUserOrder.() (package:flutter_sample/service/TestAsync.dart:44:21)
I/flutter (11975): │ #1   _rootRunUnary (dart:async/zone.dart:1198:47)
I/flutter (11975): ├┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄┄
I/flutter (11975): │ 🐛 TestAsync: fetchUserOrder: index = 3 then_value = Lat: 37.4219983, Long: -122.084

:

As you can see the AFTER_WAIT Your order is print BEFORE

TestAsync: fetchUserOrder: index =

Why?

Upvotes: 0

Views: 52

Answers (2)

Alexei
Alexei

Reputation: 15646

I found solution:

 Future<String> createOrderMessage() async {
    _logger.d("TestAsync: createOrderMessage: BEFORE_WAIT ");
    // The "await" keyword only works within an async function.
    var order = await fetchUserOrder();
    // The next line will execute only after finish fetchUserOrder() because use "await and async".
    return 'TestAsync: createOrderMessage: AFTER_WAIT Your order is: $order';
  }

  Future<Position> fetchUserOrder() async {
    _logger.d("TestAsync: fetchUserOrder: START");
    for (int index = 0; index < 10; index++) {
      await Geolocator()
          .getCurrentPosition(desiredAccuracy: LocationAccuracy.high)
          .then((value) {
        _logger
            .d("TestAsync: fetchUserOrder: index = $index then_value = $value");
      });
    }
  }

This help:

await Geolocator()

Upvotes: 1

Rida Rezzag
Rida Rezzag

Reputation: 3943

you have to add await inside the Future in front any operation you wan it to complete first before jumping to next line

Upvotes: 1

Related Questions