39

I want to create a script where I start an emulator and after the system is fully booted, I want to install an .apk.

How can I know when the emulator is fully booted so I can run the install command? Here http://developer.android.com/guide/developing/tools/adb.html it is said that adb wait-for-device install <app>.apk is not correct.

So how can I achieve this? Is it possible? Is my only option to sleep for a few minutes until I can be sure that the emulator is started?

Catalin Morosan
  • 7,897
  • 11
  • 53
  • 73

7 Answers7

47

adb shell getprop init.svc.bootanim

This will tell you whether or not the boot animation is running. It's what we use on our headless build server to check if the emulator is up. The sys.boot_completed from dac2009 is what lead me to find that flag. We use init.svc.bootanim instead because boot_completed has a tendency of triggering too early.

neuron
  • 1,224
  • 12
  • 14
25
while [ "`adb shell getprop sys.boot_completed | tr -d '\r' `" != "1" ] ; do sleep 1; done

This code gets the information from sys.boot_completed if the system boot is complete, removes a newline and compares the resulting value to 1. If its unequal 1/ not booted completly/ it will just sleep 1 second and tries again.

Just put your adb install... after this line of code.

Sebo
  • 443
  • 6
  • 14
  • This has worked for me when i am checking this for one emulator. But if i want this to check for multiple emulator it gives me error "more than one emulator". How to solve it? – Tarek Salah uddin Mahmud Nov 03 '16 at 17:45
  • In this case you need to specify the device that you want to use the adb with. Instead of adb shell. Use adb -s DEVICE_IDENTIFIER. The DEVICE_IDENTIFIER is the id you are seeing when you call adb devices. If you want to wait for all the emulators to have started. – Sebo Nov 07 '16 at 08:17
  • That trailing newline had me going in circles. Thanks! – Big McLargeHuge Aug 07 '19 at 20:52
  • 1
    A simpler approach that avoids parsing would be to perform the check and sleep on the target. `adb wait-for-device shell 'while [[ -z $(getprop sys.boot_completed) ]]; do sleep 1; done;'` – Lucas Aug 20 '20 at 14:40
14

Im not sure if this works on all devices, but it works on the ones I have tested.

If you go into the shell, you can type getprop, and get a list of phone properties. There should be one called "sys.boot_completed".

If you type "getprop sys.boot_completed" it will respond "1" if the system is booted, and an empty string if the system is not booted.

dac2009
  • 3,521
  • 1
  • 22
  • 22
  • I've encountered at least one device in the field that doesn't set that property, but if it is present and it is set, then you know your device is booted. You can also look for dev.bootcomplete but I've also encountered a device in the field that doesn't set that either. – Edward Falk Mar 25 '13 at 23:17
  • I tested `sys.boot_completed` against `init.svc.bootanim` and found that `sys.boot_completed` is the more conservative of the two approaches. If your emulator has the option to check sys.boot_completed, use it! – Gi0rgi0s Oct 04 '17 at 15:39
6

Just run emulator with -delay-adb flag and then run adb wait-for-device. adb will exit when the emulator booted.

Torbik
  • 489
  • 3
  • 10
  • This hasn't been added to the [documentation](https://developer.android.com/studio/run/emulator-commandline.html) yet, but it's mentioned here: https://androidstudio.googleblog.com/2019/05/emulator-2907-canary.html. In my testing however it hangs indefinitely. – Big McLargeHuge Aug 28 '19 at 23:14
1

Using the boot state provided from service.bootanim.exit may produce unstable results, if you try to install an app right after.

Especially if you use it to check after rebooting with adb shell su 0 setprop ctl.restart zygote

service.bootanim.exit is the "google" icon shown on white background when the emulator is booting. When it has completed, next state is the "Phone is starting" screen, where app install is not immediately possible.

I found monitoring the switch from no network to LTE or WIFI to happen after the UI is done rendering. This way the emulator is ready for user input, including app loading.

adb shell dumpsys connectivity | sed -e '/[0-9] NetworkAgentInfo.*CONNECTED/p' -n 

Emulator network changes states from no network, to LTE and finally WIFI after UI has completed loading. Tested on Android 10 with Google API support.

Without sed you get an overload of info. Try grep for either WIFI or LTE if you want a found/not found response.

Pebermynte Lars
  • 414
  • 3
  • 14
0

You may parse the stdout output of the emulator if you start it with "-logcat VERBOSE" and wait for a message which indicates that the emulator is booted.

I didn't saw any good message right now in the output, but you may write an app which is listening for "android.intend.action.BOOT_COMPLETED" and writes something to the log.

Refer http://developer.android.com/guide/developing/tools/emulator.html for more info.

Luminger
  • 2,144
  • 15
  • 22
-2

You can set a broadcast receiver which can notify that the device boot is complete

android:name="android.intent.action.BOOT_COMPLETED"
Brad Larson
  • 170,088
  • 45
  • 397
  • 571
DeRagan
  • 22,827
  • 6
  • 41
  • 50
  • 2
    This is not what I am asking. I'm talking about making a script on my home computer to install the application on the emulator to be able to automate the testing process. – Catalin Morosan Sep 03 '10 at 09:03
  • Oops!..your title read "Detect when Android emulator is fully booted" and i thought this would be the best possible approach. Any how even if you want to run a script from your system you need to know when the stimulator boot is complete. May be you can start some kind of service from the broadcast that can call a URL in your Local IIS which can fire your script... – DeRagan Sep 03 '10 at 09:33