Agent skill

Swift iOS

by ericrisco in ericrisco/rsc-harness

A skill your agent uses when building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models, Swift 6 strict data-race diagnostics…

MITAuto-check passedMobile

Install Swift iOS

skills CLI
$ npx skills add ericrisco/rsc-harness --skill swift-ios -a claude-code

Project install by default; add -g for ~/.claude/skills/.

GitHub CLI
$ gh skill install ericrisco/rsc-harness swift-ios --agent claude-code

Project scope by default; add --scope user for a personal install. Needs GitHub CLI 2.90.0 or later (public preview).

Manual copy
$ git clone --depth 1 https://github.com/ericrisco/rsc-harness.git skills-src && mkdir -p .claude/skills && cp -r skills-src/skills/swift-ios .claude/skills/swift-ios && rm -rf skills-src

Use ~/.claude/skills/ instead of .claude/skills for a personal install. The folder must contain SKILL.md.

Claude Code skills documentation · loads skills from .claude/skills/

Facts

Skill name
swift-ios
GitHub stars
167
Token cost
~3k tokens
SKILL.md length
935 words
Files
6 (incl. scripts, references)
Skills in repo
227
Repo updated
First seen
Licence
MIT

At a glance

A skill your agent uses when building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models, Swift 6 strict data-race diagnostics…

  • Building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models
  • SKILL.md covers First move: match the project…, State & view architecture, Concurrency correctness (the… and Persistence, plus 6 more sections
  • Runs Shell scripts from its folder; calls swift, xcodebuild and xcrun
  • Swift 6 strict data-race diagnostics

What it does

Swift iOS is an agent skill from ericrisco/rsc-harness. Use when building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models, Swift 6 strict data-race diagnostics, async/await and actors, SwiftData persistence, NavigationStack, and Swift Testing. NOT cross-platform Dart (that is flutter), NOT React Native (that is react-native), NOT native Kotlin for Android (that is kotlin-android), NOT shared KMP code across both OSes (that is compose-multiplatform).

Its SKILL.md is about 3k tokens, which your agent loads only when the skill is triggered. The skill folder holds 8 other files, including scripts and reference files (for example `evals/README.md`, `evals/cases.yaml` and `references/concurrency.md`).

It sits in Mobile, covering iOS development and Cross-platform mobile apps. It works with iOS, Swift, SwiftUI and React Native. The repository describes itself as: Your agent invents things because it has no memory, and can't touch your database because it has no arms. rsc is the meta-harness that gives it both, plus the trade to know the… The licence is MIT.

When your agent uses it

  • Building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models
  • Swift 6 strict data-race diagnostics
  • Async/await and actors
  • SwiftData persistence

Example prompts

  • “/swift-ios”

Requirements

  • A Bash shell

What it can do on your machine

Read from SKILL.md and the folder at commit e3d5b33. It shows what the files ask for, not the result of running them.

  • Tool permissions

    Pre-approves nothing: there is no allowed-tools line, so your agent's usual permission prompts apply.

    From allowed-tools in the SKILL.md frontmatter.

  • Runs code

    Ships 1 file in scripts/ (Shell), which the agent can run.

    Shell commands in SKILL.md call:

    • swift
    • xcodebuild
    • xcrun

    From the folder's file list and the shell code blocks in SKILL.md.

  • Network

    No URLs in SKILL.md.

    From URLs in SKILL.md, links to its own repository left out.

  • Credentials

    Names no API keys, tokens, secrets or passwords.

    From names ending in _API_KEY, _TOKEN, _SECRET, _KEY or _PASSWORD in SKILL.md.

Context cost

Swift iOS loads about 3k tokens when it runs, and up to ~5.3k if it reads all its reference files. Until then it costs about 120 tokens; SKILL.md has 935 words of instructions outside code blocks.

Always · name and description, kept in context so the agent knows when to use it
~120
When it runs · the whole SKILL.md, loaded when a task matches
~3k
With references · SKILL.md plus every file in references/, read only if the agent opens them
~5.3k

Estimates: characters ÷ 4, the usual rule of thumb; real counts depend on the model's tokenizer. Scripts and assets cost tokens only if the agent reads them.

Safety

Auto-check passed

The automated check found no risky patterns in SKILL.md.

Automated static check — not a guarantee. Review scripts before installing. It scans the text of SKILL.md for risky patterns (piping downloads into a shell, reading credential files, hidden Unicode, destructive commands); the scripts in this folder are not scanned.

SKILL.md

The full file from ericrisco/rsc-harness at commit e3d5b33, republished under its MIT licence (© ericrisco). 935 words, ~2,957 tokens.

Download SKILL.mdSave it as .claude/skills/swift-ios/SKILL.md (or your agent's skills folder). This skill also uses 5 other files; get the full folder from GitHub.
name
swift-ios
description
Use when building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models, Swift 6 strict data-race diagnostics, async/await and actors, SwiftData persistence, NavigationStack, and Swift Testing. NOT cross-platform Dart (that is `flutter`), NOT React Native (that is `react-native`), NOT native Kotlin for Android (that is `kotlin-android`), NOT shared KMP code across both OSes (that is `compose-multiplatform`).
tags
swift, swiftui, ios, swift-concurrency, swiftdata, swift-testing, apple
recommends
kotlin-android, compose-multiplatform, flutter, react-native, expo, testing-web, github-actions, ship
origin
risco

swift-ios

Hand-off — the language vs the platform. This skill owns the platform: SwiftUI/UIKit views, app lifecycle, Xcode, iOS APIs, App Store shipping. Language-level Swift — Swift 6 data-race safety and approachable concurrency, actors and task groups, some vs any, ARC and performance, Swift Testing, macros — is this skill's own ground. A concurrency error, a hang, a data race or a retain cycle belongs here. Interface feel, springs and materials: ../motion-craft/SKILL.md.

Native Apple-platform apps: the code is .swift, the UI is SwiftUI, and the compiler enforces actor isolation. If the answer is a @MainActor, @Observable, async let, #expect, NavigationStack, or @Model, you are in the right place.

First move: match the project before you write a line

Mismatched language modes produce diagnostics you cannot reproduce and "fixes" that break the user's build. Pin the ground truth first.

bash
swift --version                               # exact toolchain
xcodebuild -version                           # Xcode version
# In the .xcodeproj / Package.swift, read two settings per target:
#   SWIFT_VERSION (Swift Language Version: 5 or 6)
#   SWIFT_DEFAULT_ACTOR_ISOLATION (Default Actor Isolation: nonisolated or MainActor)

Assumed baseline: Xcode 26 / Swift 6.2 / iOS 26 SDK (current stable seen is Xcode 26.2 / Swift 6.2.3). Do not quote a version you have not confirmed in the user's project. Rule: write for the target's actual language mode. Swift 5-mode code dropped into a Swift 6 target (or vice-versa) is the most common source of "it compiles on my machine" failures.

State & view architecture

For new code use @Observable (the Observation framework), never ObservableObject / @Published. Why: Observation tracks per-property — a view re-renders only when a property it actually reads changes, not on every object mutation.

Property wrapperUse it whenOne-line why
@StateThe view owns a value or an @Observable instanceLifecycle tied to the view; survives re-renders
@BindingA child needs write access to a parent's valuePasses a mutable reference down, no ownership
@BindableYou need two-way bindings into an @ObservableProduces $model.field for TextField etc.
@EnvironmentDependency injection of a shared @ObservableOne source of truth, no prop-drilling

@Observable gives you zero thread safety. Mutating an observed property off the main actor races the UI. Annotate UI models @MainActor.

swift
// Bad — legacy pattern, whole-object invalidation, no isolation
final class CounterModel: ObservableObject {
    @Published var count = 0
}

// Good — per-property tracking, main-actor isolated
@MainActor @Observable
final class CounterModel {
    var count = 0
}

struct CounterView: View {
    @State private var model = CounterModel()      // view owns it
    var body: some View {
        Stepper("\(model.count)", value: $model.count)  // @State gives bindings to @Observable
    }
}

Concurrency correctness (the core)

The mental model: SwiftUI runs on the main actor. Anything that touches UI state is main-actor work. Background work hops off, then hops back to mutate.

  • @MainActor class for UI/view-model state — it is the UI thread.
  • actor for shared non-UI mutable state (a cache, a connection pool). Never model a SwiftUI view model as an actor — actors are reentrant and not main-bound, so your UI updates land off-main.
  • Task { } inherits the current actor + priority — use it to fire async work from a Button. Task.detached inherits nothing and is almost never what you want; reaching for it to silence a warning is a bug, not a fix.
  • async let / TaskGroup for structured parallelism (fan out, then await all).
  • Cancellation is mandatory: check Task.isCancelled or try Task.checkCancellation() in loops. SwiftUI's .task {} auto-cancels when the view disappears — prefer it over a bare Task {} for view-lifetime work.

The #1 footgun — mutating observed UI state off the main actor:

swift
// Bad — detached task mutates main-isolated state; intermittent glitches + Swift 6 data-race warning
@MainActor @Observable final class Feed {
    var items: [Item] = []
    func load() {
        Task.detached {
            let data = try? await API.fetch()
            self.items = data ?? []          // off-main mutation: WRONG
        }
    }
}

// Good — Task {} inherits the main actor; await off-main work, mutation lands on-main
@MainActor @Observable final class Feed {
    var items: [Item] = []
    func load() async {
        do {
            items = try await API.fetch()    // await suspends; assignment is back on main
        } catch is CancellationError {
            // view disappeared — nothing to do
        } catch {
            // surface error
        }
    }
}
// In the view: .task { await feed.load() }   // auto-cancels on disappear

Escape hatch for UI-centric apps: set Default Actor Isolation = MainActor (SE-0466) on the target — unannotated code becomes main-actor-isolated by default, killing false-positive data-race warnings; you opt out with nonisolated only where you genuinely need it. The full diagnostic catalog, Sendable rules, and the staged Swift 6 migration live in references/concurrency.md.

Persistence

ChoiceUse when
SwiftData (default)New SwiftUI apps; relational/object graph; light-to-moderate migration needs
Core DataAdvanced/custom migrations, mature NSPersistentCloudKit edge cases
Files (Codable → disk)Trivial, non-relational blobs only
swift
import SwiftData

@Model final class Workout {
    var name: String
    var minutes: Int
    init(name: String, minutes: Int) { self.name = name; self.minutes = minutes }
}

// App entry: attach the container once
WindowGroup { ContentView() }.modelContainer(for: Workout.self)

// In a view: query + mutate
struct ListView: View {
    @Query(sort: \Workout.name) private var workouts: [Workout]
    @Environment(\.modelContext) private var context
    var body: some View {
        List(workouts) { Text($0.name) }
            .toolbar { Button("Add") { context.insert(Workout(name: "Run", minutes: 30)) } }
    }
}

Bad: hand-rolling JSON-to-disk for relational data with cross-references. Good: model the relationship with @Model and let SwiftData own identity and autosave.

Show full SKILL.md (359 more words)Show less

Navigation

Use NavigationStack with a value-typed path + navigationDestination(for:) — type-safe, programmatic, and deep-linkable. NavigationView is deprecated.

swift
// Bad
NavigationView { List(items) { NavigationLink(item.name, destination: DetailView(item: item)) } }

// Good — push by value, deep-link by mutating the path
@State private var path: [Item] = []
NavigationStack(path: $path) {
    List(items) { item in NavigationLink(item.name, value: item) }
        .navigationDestination(for: Item.self) { DetailView(item: $0) }
}
// Deep link: path = [parent, child]

Use NavigationSplitView for iPad/Mac multi-column layouts.

Testing

Swift Testing is the default (Xcode 16+, matured through Xcode 26): @Test, #expect (soft — keeps running), #require (hard — throws/unwraps), @Test(arguments:) for parameterized cases, @Suite types, parallel + in-process by default.

swift
import Testing
@testable import MyApp

@Suite struct ScoreTests {
    @Test func startsAtZero() { #expect(Score().value == 0) }

    @Test(arguments: [1, 2, 3]) func adds(_ n: Int) {
        var s = Score(); s.add(n)
        #expect(s.value == n)
    }

    @Test func requiredUser() throws {
        let user = try #require(UserStore().current)   // hard stop if nil
        #expect(user.isActive)
    }
}

UI automation (XCUIApplication) and performance (XCTMetric) stay in XCTest — both frameworks coexist in one target. Run: xcodebuild test -scheme MyApp -destination 'platform=iOS Simulator,name=iPhone 17'. Depth (traits, confirmation for async events, in-memory ModelContainer for SwiftData, the XCTest migration table) in references/testing.md.

Build / run loop

bash
xcodebuild -scheme MyApp -destination 'platform=iOS Simulator,name=iPhone 17' build
xcodebuild -scheme MyApp -destination 'platform=iOS Simulator,name=iPhone 17' test
xcrun simctl list devices                 # manage simulators
swift build && swift test                 # SwiftPM packages (libraries / modular targets)

App = .xcodeproj/.xcworkspace built with xcodebuild. Library or shared module = Package.swift built with swift build; use SwiftPM to pin dependency versions.

iOS 26 adoption (brief)

New surface: Liquid Glass via .glassEffect() (no UIVisualEffectView), the @Animatable macro for custom animatable shapes, native SwiftUI WebView, Chart3D, richer TabView roles. Adopt them behind if #available(iOS 26, *); do not casually raise the whole deployment target — most apps still support N-1/N-2.

Anti-patterns

Anti-patternWhy it's wrongDo instead
actor for a SwiftUI view modelReentrant, not main-bound → UI mutates off-main@MainActor @Observable class
Task.detached to silence a warningDrops actor + priority inheritance; hides the real raceTask {} or .task {}
@nonisolated(unsafe) to quiet isolation errorsDisables the safety you turned on; the race remainsMake the type Sendable or keep it main-isolated
DispatchQueue.main.async inside an @Observable modelOld concurrency model fighting actorsAnnotate the model @MainActor
ObservableObject / @Published for new codeWhole-object invalidation, no isolation help@Observable
NavigationViewDeprecated, no type-safe pathNavigationStack + navigationDestination
Blocking the main actor with sync network/disk I/OFreezes the UIawait async work, hop back to main to mutate
@MainActor on pure compute / leaf utilitiesNeedless serialization onto the UI threadLeave it nonisolated
XCTAssert in a new Swift Testing fileMixing frameworks; loses #expect diagnostics#expect / #require
Force-unwrapping @Query / fetch resultsCrashes on empty storeHandle the empty case

Cross-references

© ericrisco, MIT. Rendered from Markdown: HTML in the file is shown as text, images as links, and headings moved down two levels. Raw file

Files

SKILL.md and 5 other files (scripts, references) in skills/swift-ios of ericrisco/rsc-harness.

  • SKILL.md
  • evals/README.md
  • evals/cases.yaml
  • references/concurrency.md
  • references/testing.md
  • scripts/verify.sh

Open the folder on GitHubat commit e3d5b33

Compare with similar skills

Swift iOS next to the 5 skills that share the most tags, products or categories with it. Stars are the repository's; “used in” counts other GitHub owners with a copy.

Swift iOS compared with similar skills
SkillStarsUsed inTokensAuto-checkLicenceRepo updated
Swift iOS this skillericrisco/rsc-harness167—~3kAutomated safety check: PassMIT
Expo Brownfieldexpo/skills2.7k—~1.4kAutomated safety check: PassMIT
Expo Brownfield Integrationmweinbach/agent-coworker1562 repos~900Automated safety check: NotesCustom licence
Simulator Audio E2Ehyochan/react-native-nitro-sound961—~1.1kAutomated safety check: PassMIT
Expo UIarcboxlabs/linkcode156—~1.2kAutomated safety check: PassMIT
SimdeckNativeScript/SimDeck152—~3.6kAutomated safety check: PassMIT

Similar skills

  • Expo Brownfield

    expo/skills

    Official

    Integrate Expo and React Native into an existing native iOS or Android app.

    2.7k GitHub stars~1.4k tokensUpdated yesterday
    MobileAuto-check passed
  • Expo Brownfield Integration

    mweinbach/agent-coworker

    Helps add Expo and React Native to an existing native iOS or Android app, and choose between a prebuilt AAR or XCFramework and a fully integrated build.

    156 GitHub starsUsed in 2 repos~900 tokens
    MobileAuto-check: notes
  • Simulator Audio E2E

    hyochan/react-native-nitro-sound

    Build and run repeatable react-native-nitro-sound recorder/player regression tests on an iOS Simulator or Android emulator, with explicit virtual-device selection, microphone permission, Maestro…

    961 GitHub stars~1.1k tokensUpdated 9 days ago
    MobileAuto-check passed
  • Expo UI

    arcboxlabs/linkcode

    Framework (OSS). An agent skill from arcboxlabs/linkcode.

    156 GitHub stars~1.2k tokensUpdated 10 days ago
    MobileAuto-check passed
  • Simdeck

    NativeScript/SimDeck

    A skill your agent uses for simulator lifecycle, app install/launch, live viewing, UI inspection, touch/keyboard automation, screenshots, recordings, logs, pasteboard, hardware controls, and…

    152 GitHub stars~3.6k tokensUpdated 27 days ago
    MobileAuto-check passed
  • Moq Kit

    software-mansion-labs/skills

    Software Mansion's moq-kit — native Swift (iOS) and Kotlin (Android) SDKs for Media over QUIC (moq-lite) live streaming: sub-second-latency playback, camera/microphone/screen publishing, and…

    291 GitHub stars~5k tokensUpdated 10 days ago
    MobileAuto-check passed

More from ericrisco/rsc-harness

All 227 skills in this repo
  • Ab Testing

    ericrisco/rsc-harness

    A skill your agent uses when designing or analyzing a controlled experiment — falsifiable hypothesis, sample size from an MDE, reading significance/CI/power, CUPED, or rescuing tests that won't go…

    167 GitHub stars~2.4k tokensUpdated today
    Auto-check passed
  • Accessibility

    ericrisco/rsc-harness

    A skill your agent uses when making a web UI conform to WCAG 2.2 Level AA — axe-core or Lighthouse a11y violations, keyboard operability, focus management, ARIA roles/names/live regions, contrast…

    167 GitHub stars~3.4k tokensUpdated today
    Auto-check passed
  • Ads

    ericrisco/rsc-harness

    A skill your agent uses when running or fixing paid acquisition on Google or Meta — campaign structure (Performance Max, Demand Gen, Search, Advantage+), platform-fit creative, budget/scaling rules…

    167 GitHub stars~2.2k tokensUpdated today
    Auto-check passed
  • Agent Eval

    ericrisco/rsc-harness

    A skill your agent uses when measuring whether an LLM or agent system actually got better and gating merges on it: golden sets, fixing an inflated LLM-as-judge, scoring RAG (faithfulness, contextual…

    167 GitHub stars~3.2k tokensUpdated today
    Auto-check passed
  • AI Media

    ericrisco/rsc-harness

    A skill your agent uses when a creative goal must become a finished media file: pick and order generative-media models per modality — AI voiceover, image-to-video clips, score — then glue them with…

    167 GitHub stars~3.3k tokensUpdated today
    Auto-check passed
  • Analytics

    ericrisco/rsc-harness

    A skill your agent uses when instrumenting product or web analytics — GA4/PostHog SDK wiring, event taxonomy, funnels, double-counted events, consent gating, PII scrubbing.

    167 GitHub stars~2.8k tokensUpdated today
    Auto-check passed

Categories

Questions about Swift iOS

What does Swift iOS do?

A skill your agent uses when building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models, Swift 6 strict data-race diagnostics…. Swift iOS is an agent skill from ericrisco/rsc-harness. Use when building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models, Swift 6 strict data-race diagnostics, async/await and actors, SwiftData persistence, NavigationStack, and Swift Testing.

When should I use Swift iOS?

Swift iOS fits situations like: building native iOS and Apple-platform apps in Swift with SwiftUI and modern Swift concurrency — observable view models; swift 6 strict data-race diagnostics; async/await and actors; swiftData persistence.

How do I install Swift iOS in Claude Code?

Run `npx skills add ericrisco/rsc-harness --skill swift-ios -a claude-code`. Or copy the skill folder (skills/swift-ios in ericrisco/rsc-harness) into .claude/skills/swift-ios in your project. Claude Code loads it when a task matches its description.

How do I install Swift iOS in Codex?

Run `npx skills add ericrisco/rsc-harness --skill swift-ios -a codex`. Or copy the skill folder (skills/swift-ios in ericrisco/rsc-harness) into .agents/skills/swift-ios in your project. Codex loads it when a task matches its description.

Can I use Swift iOS in Cursor, Gemini CLI or GitHub Copilot?

Cursor, Gemini CLI, GitHub Copilot and OpenCode also load SKILL.md folders. With the skills CLI, run `npx skills add ericrisco/rsc-harness --skill swift-ios -a cursor` (or -a gemini-cli, github-copilot or opencode for the others). To copy it by hand, put the folder in .cursor/skills/swift-ios, .gemini/skills/swift-ios, .github/skills/swift-ios and .opencode/skills/swift-ios in your project.

What does Swift iOS need to run?

Going by SKILL.md and its folder, Swift iOS needs a shell for the scripts in its folder and the command-line tools its instructions call (swift, xcodebuild and xcrun). Our summary lists: A Bash shell.

Does Swift iOS access the network?

SKILL.md contains no URLs. Any network use would come from the scripts or tools the agent runs. This is read from the text; nothing was executed.

Is Swift iOS safe to install?

Our automated static check of SKILL.md found no risky patterns, such as piping downloads into a shell, reading credential files or hidden Unicode. It is not a guarantee. The check reads SKILL.md only: the scripts in the folder are not scanned, so read them before running anything.

What licence does Swift iOS use?

Swift iOS is published under the MIT licence (the repository's licence). It allows redistribution, so the full SKILL.md is shown on this page.

How many tokens does Swift iOS use?

About 3k tokens (SKILL.md is roughly 12k characters). Agents keep only the skill's name and description in context until a task matches; then they load SKILL.md in full. Its references folder adds about 2.3k tokens, read only when the agent opens those files.

What are the alternatives to Swift iOS?

Skills that share tags, products or a category with Swift iOS: Expo Brownfield (expo/skills, 2.7k stars), Expo Brownfield Integration (mweinbach/agent-coworker, 156 stars), Simulator Audio E2E (hyochan/react-native-nitro-sound, 961 stars) and Expo UI (arcboxlabs/linkcode, 156 stars). The comparison table on this page puts their stars, adoption, token cost, safety result and licence side by side.

Who maintains Swift iOS?

ericrisco (a GitHub user) maintains it in ericrisco/rsc-harness, which has 167 GitHub stars. The repository holds 227 skills in this directory. The repository was last updated on October 7, 2026.

Source: ericrisco/rsc-harness on GitHub. Facts on this page come from the repository at the commit we read; the author's words are quoted as theirs.