Skip to Content

iOS Agent

TL;DR

The CMDOP iOS agent turns your iPhone or iPad into a remote endpoint. Install the app from the App Store, grant permissions, then control files, photos, and device telemetry via CLI or Python SDK. Shell access is not available due to iOS restrictions. Use push wake to maintain background connectivity.

The CMDOP iOS app turns your iPhone or iPad into a remote-controllable endpoint.

What does the iOS agent do?

What capabilities does the iOS agent have?

FeatureAvailableNotes
File accessSandboxed to app documents
Photo accessWith permission
TelemetryBattery, storage, device info
Push wakeWake device for operations
ShelliOS doesn’t allow
BrowseriOS restrictions

How do I install the CMDOP iOS app?

  1. Download CMDOP from App Store
  2. Open app and sign in
  3. Grant permissions (files, photos, notifications)
  4. Device appears in your workspace

How do I connect to an iOS device from the CLI?

# List all registered devices in your CMDOP workspace cmdop machines # Output: # HOSTNAME TYPE STATUS # macbook-pro desktop connected # prod-server server connected # marks-iphone ios connected # Open a terminal session to the iPhone device cmdop terminal marks-iphone # Note: No shell, but file operations work

How do I connect to an iOS device from the SDK?

from cmdop import AsyncCMDOPClient # Initialize a remote client session with your API key async with AsyncCMDOPClient.remote(api_key="cmd_xxx") as client: # Switch the terminal context to the iPhone device await client.terminal.set_machine("marks-iphone") # List all files at the root of the iPhone sandbox files = await client.files.list("marks-iphone", "/") print(./files) # Retrieve device telemetry: battery level, free storage, etc. info = await client.system.info("marks-iphone") print(f"Battery: {info.battery_percent}%") print(f"Storage: {info.storage_free_gb} GB free")

How do I get device info from an iOS device?

from pydantic import BaseModel # Pydantic model describing the fields returned by system.info() class DeviceInfo(BaseModel): device_name: str model: str os_version: str battery_percent: int battery_charging: bool storage_total_gb: float storage_free_gb: float wifi_connected: bool cellular_connected: bool # Fetch real-time device info from the connected iPhone info = await client.system.info("marks-iphone") # DeviceInfo( # device_name="Mark's iPhone", # model="iPhone 15 Pro", # os_version="17.4", # battery_percent=78, # battery_charging=False, # storage_total_gb=256.0, # storage_free_gb=45.2, # ... # )

What does the iOS file system look like?

iOS apps have sandboxed file access:

marks-iphone:/ ├── Documents/ # App documents (read/write) ├── Library/ # App library (read/write) ├── tmp/ # Temporary files (read/write) └── Photos/ # Photo library (read only, with permission)

How do I access files on an iOS device?

# List all files in the Documents directory files = await client.files.list("marks-iphone", "/Documents") # Read the contents of a text file from the device content = await client.files.read("marks-iphone", "/Documents/notes.txt") # Write a JSON configuration file to the device await client.files.write( "marks-iphone", "/Documents/config.json", '{"setting": "value"}' ) # Download a database file from the device to the local machine await client.files.download( "marks-iphone", "/Documents/data.sqlite", "./data.sqlite" ) # Upload a local PDF to the device's Documents folder await client.files.upload( "./report.pdf", "marks-iphone", "/Documents/report.pdf" )

How do I access photos on an iOS device?

# List all photos in the photo library (requires user-granted permission) photos = await client.files.list("marks-iphone", "/Photos") # Download a specific photo by filename to the local machine await client.files.download( "marks-iphone", "/Photos/IMG_1234.jpg", "./photo.jpg" )

What are the iOS agent limitations?

Why is there no shell access on iOS?

iOS doesn’t allow shell execution:

# Attempting shell execution on iOS will raise an error output, code = await client.terminal.execute("ls -la") # Error: Shell not available on iOS devices

Why can I only access sandboxed storage?

Only access files within app sandbox:

# Accessing sandbox paths works normally files = await client.files.list("marks-iphone", "/Documents") # Accessing paths outside the sandbox is denied by iOS files = await client.files.list("marks-iphone", "/var/mobile") # Error: Access denied

What are the background execution limitations?

iOS suspends apps in background:

# Long operations may be interrupted when the app is suspended # Use push wake for reliability (see Push Wake guide)

What are some common iOS agent use cases?

How do I backup photos from my iPhone?

async def backup_photos(): # List every photo in the device's photo library photos = await client.files.list("marks-iphone", "/Photos") # Download each photo to a local backup directory for photo in photos: await client.files.download( "marks-iphone", photo.path, f"./backup/{photo.name}" ) print(f"Backed up: {photo.name}") await backup_photos()

How do I sync documents to my iPhone?

async def sync_documents(): # Get the list of local and remote document filenames local_docs = os.listdir("./docs") remote_docs = await client.files.list("marks-iphone", "/Documents") # Upload any local file that doesn't already exist on the device for doc in local_docs: if doc not in [r.name for r in remote_docs]: await client.files.upload( f"./docs/{doc}", "marks-iphone", f"/Documents/{doc}" ) print(f"Synced: {doc}") await sync_documents()

How do I monitor my iPhone battery remotely?

async def monitor_battery(): while True: # Poll device info to read current battery level info = await client.system.info("marks-iphone") # Alert when battery drops below 20% and is not charging if info.battery_percent < 20 and not info.battery_charging: send_notification("iPhone battery low!") await asyncio.sleep(300) # Check every 5 minutes

How do I take a remote screenshot of my iPhone?

# Request a screenshot (the CMDOP app must be in the foreground) screenshot = await client.system.screenshot("marks-iphone") # Save the screenshot bytes to a local PNG file with open("screenshot.png", "wb") as f: f.write(screenshot)

What are the iOS app connection states?

StateConnectionOperations
ForegroundActiveAll operations
BackgroundMaintained (briefly)Limited time
SuspendedNonePush wake needed
TerminatedNonePush wake needed

Next

Last updated on