# iOS Sample: OctetV1Toy

Minimal demo of the OctetSDK public API: **one button, one verdict**. Use it to confirm your environment is set up correctly and to play with the predicate API without the noise of a full app.

The sample lives under [`octet-sdk-ios/sample/`](https://github.com/octetproof/octet-sdk-ios/tree/main/sample). The same instructions below also live in [`sample/README.md`](https://github.com/octetproof/octet-sdk-ios/blob/main/sample/README.md) in that repository. Handy if you're working offline.

## What it does

- Requests `NSLocationWhenInUseUsageDescription` on launch.
- Calls `try await Octet.start(config: OctetConfig(licenseKey: ...))`. The SDK verifies your license, activates against `api.octetproof.com/v1/activate` on first run, caches the token in Keychain, and brings up the proof pipeline.
- On button tap, runs `await sdk.loc.isWithin(region: .country(isoCode: "US"), atTime: Date())` and renders the verdict (result / reason / message / whether a proof attached).

## Build and run

### 1. Get a license key

Free key from [sdk.octetproof.com/signup](https://sdk.octetproof.com/signup).

### 2. Configure your local copy

```bash
cd octet-sdk-ios/sample
cp LocalConfig.swift.example LocalConfig.swift
```

Open `LocalConfig.swift` and paste your key:

```swift
enum LocalConfig {
    static let licenseKey = "octet_live_v4.public...."
}
```

`LocalConfig.swift` is gitignored. Your key stays local. If you skip this step, the build fails with `cannot find 'LocalConfig' in scope`.

### 3. Generate the Xcode project

The repo ships an [XcodeGen](https://github.com/yonaskolb/XcodeGen) spec rather than a committed `.xcodeproj`. Install once:

```bash
brew install xcodegen
```

Then generate:

```bash
xcodegen generate
```

### 4. Build and run

Pick whichever path fits your workflow.

#### Using Xcode (recommended)

```bash
open OctetV1Toy.xcodeproj
```

In Xcode:

1. Select the **OctetV1Toy** target -> **Signing & Capabilities** -> tick *Automatically manage signing* and pick your team.
2. Plug in your iOS device. The simulator cannot produce proofs (see below).
3. Cmd+R to build and run.

The free Apple Developer tier works. Apps installed via free provisioning expire after 7 days. A paid Apple Developer Program account removes the expiry.

#### From the command line

To compile-check without installing on a device:

```bash
xcodebuild \
  -project OctetV1Toy.xcodeproj \
  -scheme OctetV1Toy \
  -destination 'generic/platform=iOS' \
  -configuration Debug \
  build
```

Running on a connected device from CLI requires either [`ios-deploy`](https://github.com/ios-control/ios-deploy) (`brew install ios-deploy`) or `xcrun devicectl device install`, plus a valid signing setup. For day-to-day work the Xcode path is much easier. The command-line path is mainly for CI / build verification.

### 5. First-launch permissions

Two prompts:

- **Location When In Use**. Grant it. The SDK refuses to start without location auth.
- **Motion & Fitness**. Grant it. The SDK touches `CMMotionActivityManager` at init and Apple requires the usage description even for read-only access.

Then tap the button to fire a verdict.

## Annotated source

The whole sample is ~80 lines of SwiftUI. The interesting bits:

```swift
// Bring up the SDK once permission is granted.
let config = OctetConfig(licenseKey: LocalConfig.licenseKey)
let sdk = try await Octet.start(config: config)
```

```swift
// Fire a verdict on button tap.
let verdict = await sdk.loc.isWithin(
    region: .country(isoCode: "US"),
    atTime: Date()
)
```

```swift
// Render it.
"""
result:  \(verdict.result)
reason:  \(verdict.reason)
message: \(verdict.message)
proof:   \(verdict.proof != nil ? "set" : "nil")
"""
```

## Why simulator runs always return `INDETERMINATE`

`isWithin(.country(...))` from the iOS Simulator returns:

```
result:  INDETERMINATE
reason:  NO_FIX
message: running on simulator -- location proofs are unavailable in this environment
```

This is by design. The iOS Simulator has no real GNSS or motion stack, and the SDK's spoof-detection pipeline blocks proof generation. **Run on a real device** to see the full flow.

## Requirements

- iOS 16.0+ on the device
- Xcode 15+
- A valid OctetSDK license key

## See also

- [iOS Quick Start](/docs/getting-started/ios-quickstart/). Integrating the SDK into your own app from scratch.
- [Troubleshooting FAQ](/docs/troubleshooting/faq/). What to do when verdicts don't look right.
