# How to Install IPAs into the Virtual iPhone Using vphone-cli

> Install IPAs into your virtual iPhone using vphone-cli. This guide shows the self-contained IPA installation pipeline for extracting, re-signing, and deploying iOS apps quickly.

- Repository: [Lakr/vphone-cli](https://github.com/Lakr233/vphone-cli)
- Tags: how-to-guide
- Published: 2026-09-12

---

**vphone-cli provides a self-contained IPA installation pipeline that extracts, re-signs, and deploys iOS apps to the virtual machine via vsock port 1337 without requiring external utilities like ideviceinstaller.**

The Lakr233/vphone-cli repository ships a comprehensive command-line toolchain for managing virtual iPhone instances on macOS. Understanding how to install IPAs into the virtual iPhone using vphone-cli enables developers to sideload unsigned or custom applications into an isolated iOS VM, with the entire workflow executing across five distinct architectural layers.

## Architecture of the IPA Installation Pipeline

The installation system is organized into specialized modules that handle everything from argument parsing to kernel-level networking.

### Command Interface Layer

In [`sources/vphone-cli/VPhoneCLI.swift`](https://github.com/Lakr233/vphone-cli/blob/main/sources/vphone-cli/VPhoneCLI.swift), the top-level command-line interface parses the `install` sub-command and its `--ipa` option using **ArgumentParser**. This layer validates file paths and instantiates the installation orchestrator.

### Package Processing and Extraction

[`VPhoneInstallPackage.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneInstallPackage.swift) manages the heavy lifting of IPA preparation. It opens the ZIP archive, extracts `Payload/*.app` to a temporary directory, and recursively scans for every Mach-O binary—including executables, app extensions, and dynamic libraries—that requires re-signing.

### Dynamic Code Signing

[`VPhoneSigner.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneSigner.swift) implements the cryptographic layer. It generates a fresh entitlements plist matching the virtual device’s provisioning profile and invokes the private `SecCodeSigner` API (or a bundled `codesign` shim) to write new `CodeSignature` folders for each binary. The implementation also updates the app’s `Info.plist` with the new signing identity.

### Network Transport and Guest Communication

[`VPhoneIPAInstaller.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneIPAInstaller.swift) and [`VPhoneControl.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneControl.swift) handle the host-to-guest transmission. `VPhoneControl` establishes a persistent vsock connection to port 1337 and implements automatic reconnection logic if the daemon restarts. `VPhoneIPAInstaller` constructs a length-prefixed JSON payload containing the command, app path, and signature metadata, then transmits it over this socket.

### Guest-Side Daemon

Inside the VM, the `scripts/vphoned` daemon listens on vsock port 1337. It unmarshals incoming JSON requests and forwards them to `installd`, the native iOS installation service, completing the deployment cycle.

## Step-by-Step Installation Flow

The end-to-end process follows this strict sequence when you invoke the CLI:

1. **Command Invocation** – `vphone-cli install --ipa /path/to/App.ipa` triggers `ArgumentParser` in [`VPhoneCLI.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneCLI.swift) to create a `VPhoneInstallPackage` instance.
2. **Extraction** – The package handler opens the IPA as a ZIP archive, extracts the `.app` bundle, and identifies all Mach-O targets.
3. **Re-signing** – `VPhoneSigner` generates entitlements and applies new code signatures to every binary, ensuring the VM’s kernel will execute the code.
4. **Payload Construction** – The installer prepares a JSON message with `command: "install"` and the absolute path to the re-signed bundle.
5. **Transmission** – `VPhoneControl` opens the vsock connection and sends the JSON prefixed with a 4-byte length header.
6. **Guest Execution** – `vphoned` receives the request, calls `installd -install <appPath>` inside the iOS VM, and captures the return status.
7. **Feedback** – The CLI prints a success marker (`✅ Installed App`) or surfaces the daemon’s error message to the user.

## Practical CLI Usage Examples

### Basic Installation

Install a single IPA file by providing its absolute or relative path:

```bash
vphone-cli install --ipa ~/Downloads/ExampleApp.ipa

```

### Batch Installation

The CLI accepts multiple `--ipa` arguments and processes them sequentially in a single command:

```bash
vphone-cli install \
  --ipa ~/Downloads/AppA.ipa \
  --ipa ~/Downloads/AppB.ipa

```

### Debugging with Verbose Output

Add the `-v` or `--verbose` flag to inspect the internal state transitions, including extraction progress, signing operations, and network transmission status:

```bash
vphone-cli -v install --ipa MyApp.ipa

```

### Custom Code Signing Identity

For advanced scenarios requiring a specific provisioning profile, export the `VPHONE_SIGN_IDENTITY` environment variable before execution. [`VPhoneSigner.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneSigner.swift) checks for this variable when generating signatures:

```bash
export VPHONE_SIGN_IDENTITY="Apple Development: John Doe (ABCD1234)"
vphone-cli install --ipa MyApp.ipa

```

## Summary

- **Self-contained workflow**: The `vphone-cli` binary handles extraction, signing, and installation without relying on Xcode’s `ideviceinstaller` or similar external tools.
- **vsock networking**: All communication occurs over vsock port 1337 using a length-prefixed JSON protocol managed by [`VPhoneControl.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneControl.swift) and the `vphoned` guest daemon.
- **Mandatory re-signing**: Every Mach-O binary in the IPA must be re-signed with the VM’s identity via [`VPhoneSigner.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneSigner.swift) before `installd` will accept the package.
- **Platform restriction**: The toolchain requires macOS 15 or later, as implemented in the source code’s platform directives.

## Frequently Asked Questions

### Do I need external tools like ideviceinstaller to deploy IPAs?

No. The Lakr233/vphone-cli repository implements a fully self-contained installation pipeline. The CLI manages extraction, code signing, and network transmission directly to the virtual machine’s `installd` service, eliminating dependencies on external Apple utilities.

### Why does vphone-cli re-sign application binaries before installation?

The virtual iPhone VM uses a unique code-signing identity distinct from your host Mac. According to [`VPhoneSigner.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneSigner.swift), the tool strips existing signatures and applies fresh ones using `SecCodeSigner` (or a shim) with entitlements that match the VM’s kernel policy. Without this step, the iOS kernel would terminate the app immediately upon launch.

### Which network port does the guest daemon use to receive install commands?

The guest-side daemon `vphoned` listens on **vsock port 1337**. [`VPhoneControl.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneControl.swift) establishes the host-to-guest connection on this port and transmits length-prefixed JSON payloads containing the installation instructions.

### Can I use a custom provisioning profile or signing certificate?

Yes. Set the environment variable `VPHONE_SIGN_IDENTITY` to your desired identity string before running the install command. The signing logic in [`VPhoneSigner.swift`](https://github.com/Lakr233/vphone-cli/blob/main/VPhoneSigner.swift) reads this variable and passes it to the underlying `codesign` invocation or `SecCodeSigner` configuration, allowing you to sign apps with specific developer certificates.