agentsclimarketplace

Tca architect

Skill ninjaproger/skills/skills/tca-architect

AI agent skills

Install
npx -y skills add ninjaproger/skills --skill tca-architect

Assembled from the repository path, not quoted from the project. Check it against their README if it does not work.

2 things to look at

  • no licenseNo license file was found in the repository. Code published without one is not open source by default, so using it at work is a question for whoever answers licensing questions where you are.
  • 0 stars0 stars. Stars are a popularity signal and not a quality one, but at this level it is likely that nobody has read this closely except its author, and you would be relying on your own review.

What its author says it does

Copied from the file, not written here

Architect modular iOS apps using Swift Package Manager and The Composable Architecture (TCA). Use when designing or implementing a new iOS app (or feature module) that should be split into separate SPM packages, each owning a TCA feature reducer, view, and tests. Covers the full workflow: module decomposition, Package.swift dependency graph, reducer/view/navigation patterns, dependency injection via swift-dependencies, and the delegate action pattern for cross-module communication. Trigger when the user asks to: architect a TCA app, create a new SPM module/feature, set up a modular iOS project, add a feature to an existing TCA app, wire navigation between features, or design a dependency client.

SKILL.md

6.6 KB, ~1.4k tokens by cl100k_base, as published. Nobody here has run it

TCA + SPM Modular Architecture

Project Layout

MyApp/
├── MyApp/                      # Xcode app target — THIN HOST ONLY (~16 lines)
│   └── MyApp.swift             # @main — creates one Store, renders root view
└── MyAppKit/                   # Single SPM package containing ALL code
    ├── Package.swift
    ├── Sources/
    │   ├── AppCore/            # Root reducer + root view, composes all tab features
    │   ├── DesignSystem/       # Tokens, colors, fonts — no TCA dependency
    │   ├── Models/             # Pure Swift value types — no TCA, no UI
    │   ├── Services/           # Dependency clients + actors — no UI
    │   ├── <SharedComponent>/  # Reusable TCA reducer used by 2+ features (Quiz, ChapterStep…)
    │   └── <Feature>/          # One module per tab/top-level feature
    │       └── Resources/      # JSON, images owned by this module (.process("Resources"))
    └── Tests/
        └── <Feature>Tests/

Rules:

  • The Xcode target never contains business logic. All code lives in the SPM package.
  • No file header comments — files start directly with import statements.
  • Each module that owns static resources (Resources/) must expose a public <Module>Bundle.swift with public static let bundle = Bundle.module so sibling modules can access those resources without a circular dependency.

Workflow

  1. Decompose features → Read references/module-design.md
  2. Set up Package.swift → Read references/module-design.md (Package.swift section)
  3. Implement reducers/views/navigation → Read references/tca-patterns.md
  4. Define dependency clients → Read references/dependency-patterns.md
  5. Wire root AppCore → See App Entry Point below

App Entry Point

// MyApp/MyAppApp.swift
import ComposableArchitecture
import AppCore
import SwiftUI

@main
struct MyApp: App {
    let store = Store(initialState: AppCoreReducer.State()) {
        AppCoreReducer()
    }
    var body: some Scene {
        WindowGroup { AppCoreView(store: store) }
    }
}

AppCore (Root Reducer + TabView)

AppCore imports every tab feature and composes them with Scope. The Reduce block at the end handles cross-feature logic by intercepting child delegate actions.

// Sources/AppCore/AppCoreView.swift
@Reducer
public struct AppCoreReducer {
    public enum Tab: Hashable { case home, profile, settings }

    @ObservableState
    public struct State: Equatable {
        var selectedTab: Tab = .home
        var home    = HomeReducer.State()
        var profile = ProfileReducer.State()
        var settings = SettingsReducer.State()
        public init() {}
    }

    public enum Action {
        case selectedTabChanged(Tab)
        case home(HomeReducer.Action)
        case profile(ProfileReducer.Action)
        case settings(SettingsReducer.Action)
    }

    public var body: some ReducerOf<Self> {
        Scope(state: \.home,     action: \.home)     { HomeReducer()     }
        Scope(state: \.profile,  action: \.profile)  { ProfileReducer()  }
        Scope(state: \.settings, action: \.settings) { SettingsReducer() }

        Reduce { state, action in
            switch action {
            case .selectedTabChanged(let tab):
                state.selectedTab = tab; return .none
            case .settings(.delegate(.loggedOut)):
                state.selectedTab = .home; return .none
            case .home, .profile, .settings:
                return .none
            }
        }
    }
}

public struct AppCoreView: View {
    @Bindable var store: StoreOf<AppCoreReducer>
    public var body: some View {
        TabView(selection: $store.selectedTab.sending(\.selectedTabChanged)) {
            NavigationStack {
                HomeView(store: store.scope(state: \.home, action: \.home))
            }
            .tabItem { Label("Home", systemImage: "house") }
            .tag(AppCoreReducer.Tab.home)
            // … other tabs
        }
    }
}

Key Principles

  • @ObservableState on every State — enables direct store.property reads in SwiftUI
  • @Bindable var store in views — enables two-way $store.field bindings
  • Scope before Reduce — child reducers always run before parent logic
  • Delegate actions for child→parent communication — see references/tca-patterns.md
  • @Reducer enum Destination for push/sheet/alert navigation — see references/tca-patterns.md
  • Dual @Presents for overlay + navigation simultaneously — see references/tca-patterns.md
  • @DependencyClient or manual struct for services — see references/dependency-patterns.md
  • Shared Component modules for reusable TCA reducers (used by 2+ features) — see references/module-design.md
  • Bundle parameter when a child reducer loads resources from a parent module's Resources/ — see references/tca-patterns.md

Non-Negotiable Defaults

UI: Vanilla SwiftUI always. Use UIViewRepresentable only when SwiftUI has no equivalent (e.g. MKMapView, WKWebView, MTKView). Never wrap a UIKit component just for styling convenience.

Concurrency (in priority order):

  1. async/await + AsyncStream + Swift actors — always try this first
  2. Combine — only if the API you're wrapping only exposes a Publisher and no async equivalent exists
  3. GCD / NSLock / DispatchQueue — only as a last resort for legacy C/ObjC callback-only APIs

Reference Files

  • references/module-design.md — Module decomposition guide, Package.swift templates, dependency graph rules, shared bundle access pattern
  • references/tca-patterns.md — Full reducer pattern, navigation (Destination enum + @Presents), delegate actions, async effects, testing
  • references/dependency-patterns.md@DependencyClient macro pattern, manual struct pattern, actor-as-dependency, live/test/mock implementations

What ships with it: 3 files

37.5 KB alongside SKILL.md

Keep looking

Skills are one crate of 327,069. Ordering is by how many stacks a row turns up in, so the top of any crate is what has actually been picked rather than what has the most stars.