diff --git a/record_adb.py b/record_adb.py index 0cb1600..4c1dd3f 100644 --- a/record_adb.py +++ b/record_adb.py @@ -6,23 +6,30 @@ import argparse import subprocess import time -import os -import signal -# This script records the phone either through intent or simulating user touch -# for the purpose of generating videos that are consistent. -# The consistency allows us to compare said video. +# This script records a video of the phone screen and triggers app activity in one of three ways: +# - mode == "touch": Simulates user touch at the specified coordinates +# - mode == "launch": Launches an app with the .MainActivity +# - mode == "applink": Launches an app with the VIEW intent and a URL +# We can then compare the recorded videos across browsers. def main(args): - method = args.input + mode = args.mode device_path = './sdcard/output.mp4' - if method in 'touch' and (args.coordinate_x is None or args.coordinate_y is None): - print('--touch requires --coordinate-x --coordinate-y to use the touch input') + if mode == 'touch' and (args.coordinate_x is None or args.coordinate_y is None): + print('--mode touch requires --coordinate-x --coordinate-y ' + 'to use the touch input. Enable the touch coordinate overlay in the Android debug ' + 'settings to find the right coordinates.') + sys.exit() + + if mode == 'launch' and (args.package is None): + print('--mode launch requires --package argument') + sys.exit() + + if mode == 'applink' and (args.url is None or args.package is None): + print('--mode applink requires --url and --package arguments') sys.exit() - # if method in 'intent' and args.package is None: - # print('--intent requires --package ') - # sys.exit() kill_existing_processes("org.mozilla") kill_existing_processes("com.android.chrome") @@ -34,27 +41,57 @@ def main(args): record_process = subprocess.Popen(['adb', 'shell', 'screenrecord', '--bugreport'] + [device_path]) time.sleep(3) - # TODO allow intent trigger - # if method in 'intent': - # record_with_intent(args.package) - # else: - simulate_input(args.coordinate_x, args.coordinate_y) + if mode == "touch": + simulate_input(args.coordinate_x, args.coordinate_y) + elif mode == "launch": + # The launch activity name depends on the app. + # To find the right activity name, run `adb shell pm dump ` and look for an + # activity with `Action: "android.intent.action.MAIN"` and + # `Category: "android.intent.category.LAUNCHER"`. + if args.package.startswith("org.mozilla"): + activity = args.package + "/.App" + else: + # Assume Chrome + activity = args.package + "/com.google.android.apps.chrome.Main" + record_with_activity(activity) + else: + # The app link activity name depends on the app. + # To find the right activity name, run `adb shell pm dump ` and look for an + # activity with `Action: "android.intent.action.VIEW"` and `Category: "android.intent.category.BROWSABLE"`. + if args.package.startswith("org.mozilla"): + activity = args.package + "/org.mozilla.fenix.IntentReceiverActivity" + else: + # Assume Chrome + activity = args.package + "/com.google.android.apps.chrome.IntentDispatcher" + record_with_view_intent(activity, args.url) + time.sleep(5) record_process.kill() time.sleep(5) pull_recording(device_path, args.output) -# def record_with_intent(package): -# activity_start = subprocess.Popen(['adb', 'shell', 'am', 'start-activity', package +'/.App', -# '--ez finishonboarding true']) -# activity_start.wait() - def simulate_input(x, y): tap_event = subprocess.Popen(['adb', 'shell', 'input', 'tap'] + [str(x), str(y)]) tap_event.wait() +def record_with_activity(activity): + activity_start = subprocess.Popen( + ['adb', 'shell', 'am', 'start-activity', + '-a', 'android.intent.action.VIEW', activity] + ) + activity_start.wait() + + +def record_with_view_intent(activity, url): + activity_start = subprocess.Popen( + ['adb', 'shell', 'am', 'start-activity', '-d', url, + '-a', 'android.intent.action.VIEW', activity] + ) + activity_start.wait() + + def pull_recording(device_path, output): proc = subprocess.Popen(['adb', 'pull', device_path, output]) proc.wait() @@ -79,13 +116,14 @@ def kill_existing_processes(package_substr): if __name__ == "__main__": parser = argparse.ArgumentParser(description='record video through adb', - usage=('record_adb.py --input --coordinate-x and --cordinate-y ' + usage=('record_adb.py --mode touch -cx 660 -cy 2222 ' '--output ')) - # add intent later - parser.add_argument('-i', '--input', required=True, choices=("touch")) + + parser.add_argument('-m', '--mode', required=True, choices=("touch", "launch", "applink")) parser.add_argument('-cx', '--coordinate-x', type=int, help="X position of touch event") parser.add_argument('-cy', '--coordinate-y', type=int, help="Y position of touch event") - # parser.add_argument('-p','--package', type=str, help='package name to record if intent is used') - parser.add_argument('-o', '--output', type=str, help="output name of file") + parser.add_argument('-p', '--package', type=str, help="App package for launch / applink") + parser.add_argument('-u', '--url', type=str, help="applink URL") + parser.add_argument('-o', '--output', required=True, type=str, help="output file path") args = parser.parse_args() main(args)