A simple, easy-to-use, and stable Android automation library
Complete application lifecycle management including installation, launching, stopping, monitoring, and permission handling for Android applications.
Install, uninstall, and manage Android applications.
class Device:
def app_install(self, data: str):
"""
Install Android application.
Parameters:
- data: APK file path, URL, or file object
"""
def app_uninstall(self, package_name: str) -> bool:
"""
Uninstall application.
Parameters:
- package_name: Package name to uninstall
Returns:
bool: True if uninstall successful
"""
def app_uninstall_all(self, excludes=[], verbose=False) -> List[str]:
"""
Uninstall all third-party applications.
Parameters:
- excludes: Package names to exclude from uninstall
- verbose: Print uninstall progress
Returns:
List of uninstalled package names
"""Usage examples:
d = u2.connect()
# Install APK from file
d.app_install("/path/to/app.apk")
# Install APK from URL
d.app_install("https://example.com/app.apk")
# Uninstall specific app
success = d.app_uninstall("com.example.app")
if success:
print("App uninstalled successfully")
# Uninstall all third-party apps except specified
excluded = ["com.important.app", "com.needed.tool"]
uninstalled = d.app_uninstall_all(excludes=excluded, verbose=True)
print(f"Uninstalled {len(uninstalled)} apps")Start, stop, and control application execution.
class Device:
def app_start(self, package_name: str, activity: Optional[str] = None, wait: bool = False, stop: bool = False, use_monkey: bool = False):
"""
Launch application.
Parameters:
- package_name: Package name to launch
- activity: Specific activity to launch (optional)
- wait: Wait for app to fully start
- stop: Stop app before starting
- use_monkey: Use monkey command for launch
"""
def app_stop(self, package_name: str):
"""
Stop running application.
Parameters:
- package_name: Package name to stop
"""
def app_stop_all(self, excludes=[]) -> List[str]:
"""
Stop all third-party applications.
Parameters:
- excludes: Package names to exclude from stopping
Returns:
List of stopped package names
"""
def app_clear(self, package_name: str):
"""
Clear application data.
Parameters:
- package_name: Package name to clear
"""Usage examples:
d = u2.connect()
# Basic app launch
d.app_start("com.android.settings")
# Launch with specific activity
d.app_start("com.example.app", activity=".MainActivity")
# Stop app before launching (fresh start)
d.app_start("com.example.app", stop=True, wait=True)
# Stop running app
d.app_stop("com.example.app")
# Stop all apps except system and specified
excluded = ["com.android.systemui", "com.important.service"]
stopped = d.app_stop_all(excludes=excluded)
print(f"Stopped {len(stopped)} apps")
# Clear app data
d.app_clear("com.example.app") # Reset app to fresh stateMonitor application state and retrieve information.
class Device:
def app_current(self) -> Dict[str, Any]:
"""
Get current foreground application info.
Returns:
Dict with package, activity, and pid information
Raises:
DeviceError: If unable to get current app
"""
def app_wait(self, package_name: str, timeout: float = 20.0, front=False) -> int:
"""
Wait for application to launch.
Parameters:
- package_name: Package name to wait for
- timeout: Maximum wait time in seconds
- front: Wait for app to be in foreground
Returns:
int: Process ID (PID) of app, 0 if launch failed
"""
def wait_activity(self, activity: str, timeout=10) -> bool:
"""
Wait for specific activity to appear.
Parameters:
- activity: Activity name to wait for
- timeout: Maximum wait time in seconds
Returns:
bool: True if activity appeared
"""Usage examples:
d = u2.connect()
# Get current app info
current = d.app_current()
print(f"Current app: {current['package']}")
print(f"Current activity: {current['activity']}")
# Launch app and wait for it to start
d.app_start("com.example.app")
pid = d.app_wait("com.example.app", timeout=30)
if pid > 0:
print(f"App started with PID: {pid}")
# Wait for specific activity
d.app_start("com.example.app", activity=".LoginActivity")
if d.wait_activity(".MainActivity", timeout=15):
print("Main activity loaded")Retrieve application metadata and list installed/running applications.
class Device:
def app_info(self, package_name: str) -> Dict[str, Any]:
"""
Get application information.
Parameters:
- package_name: Package name to query
Returns:
Dict with versionName and versionCode
Raises:
AppNotFoundError: If app not found
"""
def app_list(self, filter: str = None) -> List[str]:
"""
List installed applications.
Parameters:
- filter: pm list packages filter options
Returns:
List of package names
"""
def app_list_running(self) -> List[str]:
"""
List currently running applications.
Returns:
List of running package names
"""Usage examples:
d = u2.connect()
# Get app version info
try:
info = d.app_info("com.example.app")
print(f"Version: {info['versionName']} ({info['versionCode']})")
except u2.AppNotFoundError:
print("App not installed")
# List all installed apps
all_apps = d.app_list()
print(f"Total apps: {len(all_apps)}")
# List third-party apps only
third_party = d.app_list("-3")
print(f"Third-party apps: {len(third_party)}")
# List running apps
running = d.app_list_running()
print(f"Running apps: {running}")Create and manage application sessions with lifecycle monitoring.
class Device:
def session(self, package_name: str, attach: bool = False) -> Session:
"""
Create monitored application session.
Parameters:
- package_name: Package name to monitor
- attach: Attach to existing session instead of launching
Returns:
Session instance for lifecycle management
"""
class Session(Device):
def __init__(self, dev: adbutils.AdbDevice, package_name: str):
"""Initialize session with device and package name"""
@property
def pid(self) -> int:
"""Process ID of monitored application"""
def running(self) -> bool:
"""Check if monitored application is still running"""
def restart(self):
"""Restart monitored application"""
def close(self):
"""Close/stop monitored application"""
def __enter__(self):
"""Context manager entry"""
def __exit__(self, exc_type, exc_val, exc_tb):
"""Context manager exit"""Usage examples:
d = u2.connect()
# Create session (launches app)
session = d.session("com.example.app")
print(f"App PID: {session.pid}")
# Check if app is running
if session.running():
print("App is running")
# Use session as context manager
with d.session("com.example.app") as session:
# App is automatically launched
session.click(100, 200)
session.send_keys("test input")
# Restart if needed
if not session.running():
session.restart()
# App is automatically stopped when exiting context
# Attach to existing session
existing_session = d.session("com.example.app", attach=True)Automatically grant application permissions.
class Device:
def app_auto_grant_permissions(self, package_name: str):
"""
Automatically grant all permissions for application.
Parameters:
- package_name: Package name to grant permissions
Note:
- Requires Android 6.0+ (API 23+)
- App must target SDK 22+
- Only grants runtime permissions
"""Usage examples:
d = u2.connect()
# Grant all permissions after installing app
d.app_install("/path/to/app.apk")
d.app_auto_grant_permissions("com.example.app")
# Useful for testing apps that require multiple permissions
d.app_auto_grant_permissions("com.camera.app") # Camera, storage, etc.
d.app_auto_grant_permissions("com.location.app") # Location permissionsInstall with Tessl CLI
npx tessl i tessl/pypi-uiautomator2