Metadata-Version: 2.4
Name: simdrive
Version: 1.0.0b13
Summary: SimDrive — reproduce and validate iOS bugs in 60 seconds with Claude. MCP-native iOS automation; 36 vision-first tools.
Author-email: SyncTek LLC <info@synctek.io>
License-Expression: Elastic-2.0
Project-URL: Homepage, https://simdrive.dev
Project-URL: Documentation, https://simdrive.dev
Project-URL: Repository, https://github.com/SyncTek-LLC/simdrive
Project-URL: Source, https://github.com/SyncTek-LLC/simdrive
Project-URL: Issues, https://github.com/SyncTek-LLC/simdrive/issues
Project-URL: Logo, https://simdrive.dev/brand/og-image.png
Keywords: ios,simulator,mcp,claude,testing,qa,agent,anthropic,automation,xcuitest,appium-alternative,ai-testing,sampling,xcode
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Developers
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Operating System :: MacOS
Classifier: Topic :: Software Development :: Testing
Classifier: Topic :: Software Development :: Quality Assurance
Classifier: Topic :: Software Development :: Libraries :: Python Modules
Requires-Python: >=3.10
Description-Content-Type: text/markdown
License-File: LICENSE
License-File: NOTICE
Requires-Dist: Pillow>=10.0
Requires-Dist: boto3>=1.20
Requires-Dist: email-validator>=2.0
Requires-Dist: httpx<1.0
Requires-Dist: mcp>=1.0
Requires-Dist: prometheus-client>=0.19
Requires-Dist: pyobjc-framework-Quartz>=10.0
Requires-Dist: pyobjc-framework-Vision>=10.0
Requires-Dist: pydantic>=2.0
Requires-Dist: pynacl>=1.6.2
Requires-Dist: pyyaml>=6.0
Requires-Dist: requests>=2.28
Provides-Extra: ssim
Requires-Dist: scikit-image>=0.22; extra == "ssim"
Provides-Extra: claude
Requires-Dist: anthropic>=0.30; extra == "claude"
Provides-Extra: dev
Requires-Dist: anthropic>=0.30; extra == "dev"
Requires-Dist: fastapi>=0.115; extra == "dev"
Requires-Dist: hypothesis>=6; extra == "dev"
Requires-Dist: httpx>=0.24; extra == "dev"
Requires-Dist: moto[s3]>=5.0; extra == "dev"
Requires-Dist: mypy>=1.0; extra == "dev"
Requires-Dist: pytest>=7.0; extra == "dev"
Requires-Dist: pytest-asyncio>=0.23; extra == "dev"
Requires-Dist: pytest-benchmark>=4.0; extra == "dev"
Requires-Dist: pytest-cov>=4; extra == "dev"
Requires-Dist: ruff>=0.1.0; extra == "dev"
Requires-Dist: sqlalchemy>=2.0; extra == "dev"
Provides-Extra: cloud
Requires-Dist: boto3>=1.20; extra == "cloud"
Requires-Dist: fastapi>=0.100; extra == "cloud"
Requires-Dist: uvicorn>=0.20; extra == "cloud"
Requires-Dist: sqlalchemy>=2.0; extra == "cloud"
Requires-Dist: pynacl>=1.6.2; extra == "cloud"
Requires-Dist: email-validator>=2.0; extra == "cloud"
Dynamic: license-file

<!-- mcp-name: io.github.SyncTek-LLC/simdrive -->

<p align="center">
  <picture>
    <source media="(prefers-color-scheme: dark)" srcset="https://github.com/SyncTek-LLC/simdrive/raw/main/docs/brand/wordmark-dark.svg">
    <img alt="simdrive" src="https://github.com/SyncTek-LLC/simdrive/raw/main/docs/brand/wordmark.svg" width="320">
  </picture>
</p>

<p align="center"><strong>Reproduce and validate iOS bugs in 60 seconds with Claude.</strong></p>


SimDrive is the MCP-native iOS automation toolkit your AI agent already knows
how to drive. Hand it a Linear ticket, watch it walk the steps in the
simulator (or a paired real device), and get back a deterministic recording
that replays the same way every time.

## 60-second bug repro

```text
You (in Cursor / Claude Code):
  "Use simdrive to reproduce Linear ENG-1247 — sign-in fails on iPhone 17 /
   iOS 26.3 with test@example.com."

Claude:
  → session_start({device: "iPhone 17", os_version: "26.3", bundle_id: "com.acme.app"})
  → observe()                              # screenshot + annotated marks
  → tap({text: "Email"})
  → type_text({text: "test@example.com"})
  → tap({text: "Password"})
  → type_text({text: "pw123"})
  → tap({text: "Sign In"})
  → observe()                              # captures error toast
  → record_stop({name: "ENG-1247-repro"})  # YAML+PNG attached to PR
```

After you ship the fix, replay the same recording with the `replay` tool to
confirm it still fails (or now passes) before deploy.

## What you get

- **Bug reproduction + validation (hero)** — agent reads the ticket, drives
  the simulator, captures the failure, saves a deterministic recording.
- **Record → replay** — recordings are YAML + PNG bundles that re-run
  identically each time via the `replay` tool.
- **Autonomous test suites** — `run_journey` reads a YAML journey with goals
  and success criteria; SimDrive drives the agent loop and reports
  pass/fail with evidence.
- **Real iOS device support** — WebDriverAgent-backed; one-command
  `simdrive bootstrap-device <udid>` bring-up.
- **Visual regression detection** — SSIM-based pre/post comparison with
  configurable drift handling.
- **Performance baselines + regression comparison** — capture CPU / RSS /
  thread baselines and diff future runs.

## Install

```bash
pip install simdrive
```

No license or account required.

Requires: macOS, Xcode 15+, Python 3.10+.

## Wire SimDrive into your MCP client

Add to `.claude/mcp.json` (Claude Code), `claude_desktop_config.json` (Claude
Desktop), or your Cursor MCP config:

```json
{
  "mcpServers": {
    "simdrive": { "command": "simdrive" }
  }
}
```

Restart the client. Your agent now has 36 SimDrive tools available.

> **Note:** SimDrive is no longer offered as a commercial product. It remains
> available as a free, open MCP tool for internal/personal use — see
> `LICENSE`.

## Minimum-viable session

```python
session_start(bundle_id="com.example.app")
observe()                                  # see initial screen
tap(label="Sign In")                       # tap a labelled control
observe()                                  # verify state
record_stop(session_id="...", name="signin-smoke")   # save replay
session_end(session_id="...")              # clean up
```

## Tool surface (36 MCP tools)

| Group | Tools |
|-------|-------|
| Lifecycle (3) | `session_start`, `session_end`, `session_status` |
| Observe (1) | `observe` |
| Act (6) | `tap`, `swipe`, `type_text`, `press_key`, `clear_field`, `tap_and_wait_keyboard` |
| Record/Replay (5) | `record_start`, `record_stop`, `replay`, `list_replays`, `validate_replay` |
| Logs (1) | `logs` |
| Performance (4) | `perf`, `perf_baseline`, `perf_compare`, `memory` |
| Diagnostics (5) | `doctor`, `app_state`, `apps`, `crashes`, `list_devices` |
| Robustness (4) | `dismiss_first_launch_alerts`, `pre_grant_permissions`, `set_appearance`, `dismiss_sheet` |
| Recordings (2) | `lint_recordings`, `migrate_recording` |
| Journeys (1) | `load_journey` |
| Version (1) | `version` |
| Accessibility (3) | `perform_accessibility_action`, `get_announcements`, `set_text` |

Canonical machine-readable list: `simdrive/src/simdrive/server.py::_TOOLS`.

## Real-device support

Drive a paired iPhone or iPad in addition to the simulator:

```bash
export SIMDRIVE_ALLOW_PHYSICAL_DEVICE=1
simdrive bootstrap-device <device-udid>
```

```python
session_start(bundle_id="com.example.app", udid="<device-udid>", target="device")
```

WDA bootstrap on iOS 26.x has some rough edges; the simulator
(`target="simulator"`, default) is the fully supported path.

## Environment variables

| Variable | Effect |
| --- | --- |
| `SIMDRIVE_ALLOW_PHYSICAL_DEVICE=1` | Allow driving a paired physical iPhone/iPad (see above). |
| `SIMDRIVE_NO_AUTO_RESTART=1` | Suppress the version-drift auto-restart. When the running server is older than the wheel on disk (after `pip install -U simdrive`), simdrive normally re-execs itself to pick up the new code. **Set this for MCP-driver sessions** (Claude Code, etc.): an auto-restart re-execs the process and desyncs the MCP stdio transport, after which every tool call fails `MCP error -32602: Invalid request parameters` until you reconnect (`/mcp`). When simdrive detects it is serving as an MCP stdio server it now suppresses the auto-restart automatically and tells you to reconnect; this env var makes that the default everywhere (incl. embedded/CLI contexts). Truthy values: `1`, `true`, `yes`, `on`. |

## Known limitations

See `docs/LIMITATIONS.md` for: `type_text` first-character drop workaround,
SSIM-vs-structural-check semantics, SwiftUI half-sheet dismissal,
appearance-respring caveats, real-device input scope.

## Support

- **Docs:** <https://docs.simdrive.dev>
- **Bugs / feature requests:** [open an issue](https://github.com/SyncTek-LLC/simdrive/issues/new/choose)
- **Email (private support):** <support@simdrive.dev>
- **Security disclosures:** <security@simdrive.dev>

## License

Elastic License 2.0 — see `LICENSE`. Free for internal use; prohibits
offering SimDrive as a competing managed service.

Built by [SyncTek](https://synctek.io).
