summaryrefslogtreecommitdiffstats
path: root/testing/web-platform/tests/tools/wpt/android.py
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-07 09:22:09 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-04-07 09:22:09 +0000
commit43a97878ce14b72f0981164f87f2e35e14151312 (patch)
tree620249daf56c0258faa40cbdcf9cfba06de2a846 /testing/web-platform/tests/tools/wpt/android.py
parentInitial commit. (diff)
downloadfirefox-43a97878ce14b72f0981164f87f2e35e14151312.tar.xz
firefox-43a97878ce14b72f0981164f87f2e35e14151312.zip
Adding upstream version 110.0.1.upstream/110.0.1upstream
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'testing/web-platform/tests/tools/wpt/android.py')
-rw-r--r--testing/web-platform/tests/tools/wpt/android.py181
1 files changed, 181 insertions, 0 deletions
diff --git a/testing/web-platform/tests/tools/wpt/android.py b/testing/web-platform/tests/tools/wpt/android.py
new file mode 100644
index 0000000000..366502cc6c
--- /dev/null
+++ b/testing/web-platform/tests/tools/wpt/android.py
@@ -0,0 +1,181 @@
+# mypy: allow-untyped-defs
+
+import argparse
+import os
+import platform
+import shutil
+import subprocess
+
+import requests
+from .wpt import venv_dir
+
+android_device = None
+
+here = os.path.abspath(os.path.dirname(__file__))
+wpt_root = os.path.abspath(os.path.join(here, os.pardir, os.pardir))
+
+
+def do_delayed_imports():
+ global android_device
+ from mozrunner.devices import android_device
+ android_device.TOOLTOOL_PATH = os.path.join(os.path.dirname(__file__),
+ os.pardir,
+ "third_party",
+ "tooltool",
+ "tooltool.py")
+
+
+def get_parser_install():
+ parser = argparse.ArgumentParser()
+ parser.add_argument("--reinstall", action="store_true", default=False,
+ help="Force reinstall even if the emulator already exists")
+ return parser
+
+
+def get_parser_start():
+ return get_parser_install()
+
+
+def get_sdk_path(dest):
+ if dest is None:
+ # os.getcwd() doesn't include the venv path
+ dest = os.path.join(wpt_root, venv_dir())
+ dest = os.path.join(dest, 'android-sdk')
+ return os.path.abspath(os.environ.get('ANDROID_SDK_PATH', dest))
+
+
+def uninstall_sdk(dest=None):
+ path = get_sdk_path(dest)
+ if os.path.exists(path) and os.path.isdir(path):
+ shutil.rmtree(path)
+
+
+def install_sdk(logger, dest=None):
+ sdk_path = get_sdk_path(dest)
+ if os.path.isdir(sdk_path):
+ logger.info("Using SDK installed at %s" % sdk_path)
+ return sdk_path, False
+
+ if not os.path.exists(sdk_path):
+ os.makedirs(sdk_path)
+
+ os_name = platform.system().lower()
+ if os_name not in ["darwin", "linux", "windows"]:
+ logger.critical("Unsupported platform %s" % os_name)
+ raise NotImplementedError
+
+ os_name = 'darwin' if os_name == 'macosx' else os_name
+ # TODO: either always use the latest version or have some way to
+ # configure a per-product version if there are strong requirements
+ # to use a specific version.
+ url = f'https://dl.google.com/android/repository/sdk-tools-{os_name}-4333796.zip'
+
+ logger.info("Getting SDK from %s" % url)
+ temp_path = os.path.join(sdk_path, url.rsplit("/", 1)[1])
+ try:
+ with open(temp_path, "wb") as f:
+ with requests.get(url, stream=True) as resp:
+ shutil.copyfileobj(resp.raw, f)
+
+ # Python's zipfile module doesn't seem to work here
+ subprocess.check_call(["unzip", temp_path], cwd=sdk_path)
+ finally:
+ os.unlink(temp_path)
+
+ return sdk_path, True
+
+
+def install_android_packages(logger, sdk_path, no_prompt=False):
+ sdk_manager_path = os.path.join(sdk_path, "tools", "bin", "sdkmanager")
+ if not os.path.exists(sdk_manager_path):
+ raise OSError("Can't find sdkmanager at %s" % sdk_manager_path)
+
+ packages = ["platform-tools",
+ "build-tools;33.0.1",
+ "platforms;android-33",
+ "emulator"]
+
+ # TODO: make this work non-internactively
+ logger.info("Installing SDK packages")
+ cmd = [sdk_manager_path] + packages
+
+ proc = subprocess.Popen(cmd, stdin=subprocess.PIPE)
+ if no_prompt:
+ data = "Y\n" * 100 if no_prompt else None
+ proc.communicate(data)
+ else:
+ proc.wait()
+ if proc.returncode != 0:
+ raise subprocess.CalledProcessError(proc.returncode, cmd)
+
+
+def get_emulator(sdk_path, device_serial=None):
+ if android_device is None:
+ do_delayed_imports()
+ if "ANDROID_SDK_ROOT" not in os.environ:
+ os.environ["ANDROID_SDK_ROOT"] = sdk_path
+ substs = {"top_srcdir": wpt_root, "TARGET_CPU": "x86"}
+ emulator = android_device.AndroidEmulator("*", substs=substs, device_serial=device_serial)
+ emulator.emulator_path = os.path.join(sdk_path, "emulator", "emulator")
+ return emulator
+
+
+def install(logger, reinstall=False, no_prompt=False, device_serial=None):
+ if reinstall:
+ uninstall_sdk()
+
+ dest, new_install = install_sdk(logger)
+ if new_install:
+ install_android_packages(logger, dest, no_prompt)
+
+ if "ANDROID_SDK_ROOT" not in os.environ:
+ os.environ["ANDROID_SDK_ROOT"] = dest
+
+ emulator = get_emulator(dest, device_serial=device_serial)
+ return emulator
+
+
+def start(logger, emulator=None, reinstall=False, device_serial=None):
+ if reinstall:
+ install(reinstall=True)
+
+ sdk_path = get_sdk_path(None)
+
+ if emulator is None:
+ emulator = get_emulator(sdk_path, device_serial=device_serial)
+
+ if not emulator.check_avd():
+ logger.critical("Android AVD not found, please run |mach bootstrap|")
+ raise NotImplementedError
+
+ emulator.start()
+ emulator.wait_for_start()
+ return emulator
+
+
+def run_install(venv, **kwargs):
+ try:
+ import logging
+ logging.basicConfig()
+ logger = logging.getLogger()
+
+ install(logger, **kwargs)
+ except Exception:
+ import traceback
+ traceback.print_exc()
+ import pdb
+ pdb.post_mortem()
+
+
+def run_start(venv, **kwargs):
+ try:
+ import logging
+ logging.basicConfig()
+ logger = logging.getLogger()
+
+ start(logger, **kwargs)
+ except Exception:
+ import traceback
+ traceback.print_exc()
+ import pdb
+ pdb.post_mortem()