When testing Android applications, manually or automatically, there are several scenarios that need to be validated. Some scenarios may require a specific setup that takes a long time to be performed ⏳
Suppose you need to test a feature of your app while the device battery is running low. If the battery is full, you’ll need to wait several hours before it is discharged. The worst scenario would be if you are testing it using an Android Virtual Device (AVD), how would you discharge the battery of an emulator?
Another setup that can be required with a certain frequency is to clear the application data before launching it. Obviously, this takes significantly less time than fully discharging a battery. But if you need to manually navigate to the app info screen and press the clear data button before each test, you will reach the end of the day with several valuable minutes, maybe hours, spent doing this repetitive action.
This article will show you how these kinds of actions can be performed as simply as running a command in a terminal, saving you time, and improving your productivity.
Table of Contents – Useful ADB Commands For Android Testing
- What is ADB
Android Debug Bridge, or simply ADB, is a tool included in Android SDK that allows us to send commands from a computer host to an Android device. By using ADB it is also possible to copy files to/from the device, and probably the most useful of its features, run shell commands in the Android device 📱
Before using ADB, we need to enable USB debugging in Developer options in the Android device. To do that, launch the Settings application and navigate to About phone (or About emulated device, if you’re using an AVD). Perform several touches on the Build number until the message “You are now a developer!” appears. This will enable developer options that is where we need to go now.
Return to the main screen of the Settings application and go to System -> Advanced -> Developer options. Find the option USB debugging and enable it. Now just connect the device to your computer using a USB cable and you are ready to run ADB commands! let’s start learning about the commands.
The first command you should learn is the one to list the connected devices, so you can check if your device was correctly recognized by the ADB server. To do that run the command:
$ adb devices List of devices attached emulator-5554 device
Having found our device in the command output, we are good to proceed to more interesting commands.
Do you have any idea about how to discharge the AVD battery yet? 🔋 Probably not if it is a virtual device with no real battery. But fortunately we can use the following command to simulate any scenario we want, like setting the level to 1% only:
$ adb shell dumpsys battery set level 1
You could also try to connect/disconnect an AC charger:
# Connect AC charger $ adb shell dumpsys battery set ac 1 # Disconnect AC charger $ adb shell dumpsys battery set ac 0
Or if you prefer, try with a USB cable instead:
# Connect USB cable $ adb shell dumpsys battery set usb 1 # Disconnect USB cable $ adb shell dumpsys battery set usb 0
After running each of those commands you can reset the battery options using:
$ adb shell dumpsys battery reset
ADB commands are way more powerful than just faking battery parameters- we can also do more things like taking screenshots and recording videos of the device screen. Let’s start recording a video of our device screen by running the following command:
$ adb shell screenrecord /sdcard/Movies/video.mp4
This will record the device screen and save the video file to the path / SDcard / Movies / video.mp4. To stop recording press Ctrl + C to finish the command. In order to take a screenshot of some screen of our app we just need to navigate to the desired screen, and then run the command:
$ adb shell screencap -p /sdcard/Pictures/screenshot.png
The command above will take a screenshot of the current screen and save it at the path / SDcard / Pictures / screenshot.png. If you tried running the command, you may have noticed that no output text is displayed, so how can we check if the screenshot was really captured? Fortunately, we can use ADB to several commands that are well known by users who are familiar with Unix commands, like the ls which we will use to list the files from the Pictures folder:
$ adb shell ls /sdcard/Pictures/ screenshot.png
As you can see in the command output, the screenshot was correctly saved in this folder 📂 But you may have noticed that the screenshot was saved in the Android device storage. How can we access it using our computer? By simply copy the file using the ADB pull command:
$ adb pull /sdcard/Pictures/screenshot.png ~/Desktop/screenshot.png /sdcard/Pictures/screenshot.png: 1 file pulled, 0 skipped. 16.0 MB/s (132917 bytes in 0.008s)
The screenshot file was now copied from the device storage to the computer desktop. Now let’s suppose that you opened it on the computer, made some changes in the image file, and want to copy it back from the computer to the Android device. What you need to do is run the ADB push command instead:
$ adb push ~/Desktop/screenshot.png /sdcard/Pictures/screenshot.png /home/heitor/Desktop/screenshot.png: 1 file pushed, 0 skipped. 25.0 MB/s (132917 bytes in 0.005s)
As mentioned before, we are able to execute Unix-like commands using ADB shell, and we already used the ls to list the files in a directory. Now let’s use some other commands that may help a lot when we are dealing with files. We may want to have a specific folder to save our screenshots, separating them from the other pictures. For this, run the following command to create a new directory, after that run the ls in order to check if it was created correctly:
$ adb shell mkdir /sdcard/Pictures/my_screenshots $ adb shell ls /sdcard/Pictures/ my_screenshots screenshot.png
As we can see in the command output, the directory was created but the screenshot that we have taken before is still placed inside the Pictures folder. We can use this command to move it to the new location:
$ adb shell mv /sdcard/Pictures/screenshot.png /sdcard/Pictures/my_screenshots/
If instead of moving the file you wanted to copy, then you could have used the cp command instead:
$ adb shell cp /sdcard/Pictures/screenshot.png /sdcard/Pictures/my_screenshots/
And after copying and moving the files, you can just delete them by using the rm command:
# Delete a file $ adb shell rm /sdcard/Pictures/screenshot.png # Add the -r flag to delete directories $ adb shell rm -r /sdcard/Pictures/my_screenshots
As you may imagine, we can do much more with ADB. The next commands are even more important to testers once they allow us to obtain data about the android device such as logs, application, and Android versions, which are very important when reporting issues or tracking bugs.
Probably the most important one of them is the log, which is how the developer will use it to understand what went wrong with the application ❌ The log can be obtained using logcat:
$ adb logcat
The command above will print the log to the console output. In order to stop the process, press
C to stop it. Using the logcat command without any additional option will print the whole text available in the main logcat buffer, which probably is not so useful for your tests. You then may want to use some filters. We can filter the logs according to their priorities:
- V: Verbose (lowest priority)
- D: Debug
- I: Info
- W: Warning
- E: Error
- F: Fatal
- S: Silent (highest priority. Nothing is printed)
If we want only the messages with error priority or higher, for example, we just need to use the command:
$ adb logcat *:E
To filter by other log priorities, just change the end of the command with the respective letter. We can also filter the output by the tag used by the application logger 🔖 The command below prints to the output log messages with the tag MyTag and priority level Info or higher. The *:S at the end will exclude the log from other tags with any priority:
$ adb logcat MyTag:I *:S
Besides logs, there are several other important data, such as device build, current language, or Android version, that can be obtained by using ADB commands:
$ adb shell getprop [build.version.extensions.r]:  [cache_key.bluetooth.get_bond_state]:  [cache_key.bluetooth.get_profile_connection_state]:  # ...
The command above will output all the data that can be obtained using this command, but we can also pass the key displayed inside the brackets in order to get only a specific value. Some examples are displayed below:
# Get Android version $ adb shell getprop ro.build.version.release 11 # Get build fingerprint $ adb shell getprop ro.build.fingerprint google/sdk_gphone_x86_arm/generic_x86_arm:11/RSR1.201013.001/6903271:userdebug/dev-keys # Get current device language $ adb shell getprop persist.sys.locale en-US
Another interesting feature of ADB is the possibility to interact with the Android device by performing touches and swipes on the screen, entering text, and pressing buttons. To execute these interactions, we will use the input command followed by the name of the interactions to be performed and their arguments.
So to enter a string in a text field, use the command below (make sure the field has focus and remember to escape the whitespaces):
$ adb shell input text "this\ is\ some\ string"
The touches can be performed by coordinates. Just use the input tap command followed by the x and y points to be clicked:
$ adb shell input tap 500 400
Similarly, the swipe command can be executed by sending the coordinates, but we need to send two different points, the initial and the final ones. Optionally we can define the duration of the swipe movement in milliseconds:
# Perform a swipe gesture from the center to top $ adb shell input swipe 500 1000 500 100 # Perform the same gesture slowly. Takes 5 seconds $ adb shell input swipe 500 1000 500 100 5000
We can also use the input command to press device buttons, like home, back, menu, or even other less common ones like camera or headset buttons. This is possible because each of these buttons has a key code associated with them and the input command uses those codes to perform the actions.
You can find the list of all key codes in the official documentation 📃 See some examples below:
# Press Home button $ adb shell input keyevent KEYCODE_HOME # Press Camera button $ adb shell input keyevent KEYCODE_CAMERA # Press Back button $ adb shell input keyevent KEYCODE_BACK # Press Headset button $ adb shell input keyevent KEYCODE_HEADSETHOOK
Another scenario where ADB is really useful is when the testing applications are launching activities directly, which can be done by using the Activity Manager (am). Besides launching the main activity of an app you can also lunch other ones, reducing the steps required to reach a screen 💪
Let’s start using the Activity Manager to launch an application by its package name. We’ll use the Settings app as an example. Its package name is com.android.settings:
$ adb shell am start com.android.settings
After running this command the Settings application will be launched on the Android device. This command will just launch the application’s main activity. If we want to launch another one, we just need to inform the activity name with the flag -n. The command below launches the Wifi Settings screen directly:
$ adb shell am start -n com.android.settings/.Settings$WifiSettings2Activity
But how can we discover the activity name that we want to launch? Fortunately, there is also an ADB command to do that. We just need to use the dumpsys to extract the information about the activity that is being displayed on the screen.
Once the command will output a lot of data that is not relevant for us, let’s filter the output with the grep and cut shell commands in order to print just the activity name:
$ adb shell "dumpsys activity activities | grep mResumedActivity | cut -d ' ' -f 8" com.android.settings/.Settings$WifiSettings2Activity
After launching the application and performing your validations, surely you will want to close the app. To do that is just as simple as launching it, just use the force-stop command with the package name:
$ adb shell am force-stop com.android.settings
The last kind of command presented in this article will be the one that uses the Packager Manager (pm). Using the Package Manager it is clear application data, grant and revoke permissions and also list all the installed applications.
As mentioned at the beginning of this article, despite the fact that cleaning the application data is a quick task, it can consume a lot of time from the tester if it needs to be repeated before each test. To solve that we can run a pm command to clear the application data by using ADB.
To test that, try launching the Clock application and making some changes like creating an alarm ⏰ After that, run the command below and verify that all changes have been reset:
$ adb shell pm clear com.google.android.deskclock
After clearing the application data, you may want to grant the application permissions. This can be done manually when the app asks for them, but you could also enable them beforehand by using the pm command. The command below will grant the permission android.permission.READ_EXTERNAL_STORAGE to the Clock application:
$ adb shell pm grant com.google.android.deskclock android.permission.READ_EXTERNAL_STORAGE
If you want to revoke this permission, use the following command:
$ adb shell pm revoke com.google.android.deskclock android.permission.READ_EXTERNAL_STORAGE
In order to discover what is the name of the permissions to be used, you can use the pm command to list all known permissions:
$ adb shell pm list permissions All Permissions: permission:com.google.android.gms.auth.api.phone.permission.SEND permission:android.permission.REAL_GET_TASKS permission:android.permission.ACCESS_CACHE_FILESYSTEM permission:android.permission.REMOTE_AUDIO_PLAYBACK #...
We can also use the pm command to see if an application is installed. We just need to run the pm command to list all installed applications and then check if some package name is included in the output.
Alternatively, we can add a substring of the package name to the end of the command, then only the package names that match this substring will be printed at the command output. See the examples below:
# List all installed applications $ adb shell pm list packages package:com.google.android.networkstack.tethering package:com.android.cts.priv.ctsshim package:com.google.android.youtube #... # List only the package names that contains "android.settings" $ adb shell pm list packages android.settings package:com.android.settings.intelligence package:com.android.settings package:com.android.settings.auto_generated_rro_product__
I hope the commands presented in this article have been helpful to you and saved some effort when running your tests. It is also nice to point out that the ADB shell commands can be executed from UI Automator scripts, so they can also be useful for your automation scripts. You can also use TestProject’s ADB Wrapper Community Addon to execute any ADB shell command.
Please have in mind that those are just some of several available commands. There are a lot of possibilities that can help you and your team when working with Android devices. You can learn more by running the
adb help command 👩💻
The ADB tool is a must for anyone working with Android devices, whether it’s a developer or a tester. Hope you enjoyed my tutorial 😊