Skip to content

opencode + SwiftUI

In-app feedback for SwiftUI, fixed by opencode

You are building a SwiftUI app with opencode. opencode is an open-source terminal agent with its own interface. It defines MCP servers in opencode.json, and its permission block decides which tools may run without asking.

1. Paste one prompt into opencode

Run opencode in your project folder, connect a model provider with /connect if you have not yet, and paste the prompt in the terminal interface.

Add Nitpick feedback to this app. Fetch https://nitpickhq.com/install.md and follow every step.

opencode follows install.md. nitpick login opens your browser, where you create an account and start the subscription, and opencode waits for that before it adds the component.

By default all tools are enabled and run without asking. A permission block in opencode.json can set bash to ask, allow or deny, so set it to ask if you want to approve each shell command.

2. What lands in your SwiftUI code

Roughly this. opencode writes it, you review it.

  1. Add the Swift package in Xcode with File > Add Package Dependencies, and put the Nitpick product in your app target.
  2. Check that the deployment target is iOS 17.0 or newer.
  3. Call Nitpick.configure once at launch, then name screens and elements.
App.swift
import SwiftUI
import Nitpick

@main
struct MyApp: App {
    init() { Nitpick.configure(appKey: "npk_YOUR_PUBLIC_KEY") }

    var body: some Scene {
        WindowGroup { RootView().nitpick() }
    }
}

// Name what users may point at
Button("Start", action: start)
    .nitpickElement("Home/StartButton")

Needs iOS 17 or newer. The Swift package ships its own privacy manifest. Details in Install for SwiftUI.

3. Give opencode the MCP server

opencode lists MCP servers under the mcp key in opencode.json. A local server is a type, a command as one array, and an enabled flag.

opencode.json
{
  "$schema": "https://opencode.ai/config.json",
  "mcp": {
    "nitpick": {
      "type": "local",
      "command": ["npx", "-y", "@nitpickhq/cli", "mcp"],
      "enabled": true
    }
  }
}

Note the difference from the other agents: the command and its arguments are one array, not two fields.

Run opencode mcp list to see whether the server is configured, then ask it to list your apps with the nitpick tools. The model can only call them if the server started.

4. Build and run in the simulator with opencode

xcodebuild -list shows the schemes and builds one for a simulator, and xcrun simctl boots, installs and launches the app. Your scheme, simulator and bundle identifier will differ.

terminal
xcodebuild -list
xcodebuild -scheme MyApp -destination 'platform=iOS Simulator,name=iPhone 16' -derivedDataPath build build
xcrun simctl boot "iPhone 16"
xcrun simctl install booted build/Build/Products/Debug-iphonesimulator/MyApp.app
xcrun simctl launch booted com.example.myapp

With the default permissions it runs xcodebuild and xcrun simctl straight away. If you set bash to ask, you approve every build and simulator step like in the other agents.

5. Let opencode fix the reports

In opencode, ask it to check Nitpick for open feedback, fix what it can and resolve the reports. It calls list_feedback, reads each report with its screenshot through get_feedback, and finds the code. An element name such as checkout.pay_button leads straight to the line that says .nitpickElement("checkout.pay_button"), and a screen name leads to the matching .nitpickScreen call. When the fix is done it calls resolve_feedback.

Working with opencode

Good to know for SwiftUI

$9 a month per account. Unlimited apps.

Get started

Related

Sources