Initial commit
This commit is contained in:
18
.claude-plugin/plugin.json
Normal file
18
.claude-plugin/plugin.json
Normal file
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"name": "swift-engineer",
|
||||
"description": "Elite iOS and macOS development expertise with automatic skill activation for Swift, SwiftUI, UIKit, Xcode, and Apple frameworks plus code formatting tools",
|
||||
"version": "2.0.0",
|
||||
"author": {
|
||||
"name": "Scott",
|
||||
"email": "scott.jungling@gmail.com"
|
||||
},
|
||||
"skills": [
|
||||
"./skills"
|
||||
],
|
||||
"agents": [
|
||||
"./agents"
|
||||
],
|
||||
"commands": [
|
||||
"./commands"
|
||||
]
|
||||
}
|
||||
3
README.md
Normal file
3
README.md
Normal file
@@ -0,0 +1,3 @@
|
||||
# swift-engineer
|
||||
|
||||
Elite iOS and macOS development expertise with automatic skill activation for Swift, SwiftUI, UIKit, Xcode, and Apple frameworks plus code formatting tools
|
||||
9
agents/ios-swift-expert.md
Normal file
9
agents/ios-swift-expert.md
Normal file
@@ -0,0 +1,9 @@
|
||||
---
|
||||
name: ios-swift-expert
|
||||
description: Use this agent when working with iOS or macOS development projects, including Swift code, SwiftUI interfaces, Xcode project configuration, iOS frameworks, app architecture, debugging iOS apps, or any Apple platform development tasks. Examples: <example>Context: User is working on an iOS app and encounters a SwiftUI layout issue. user: "My SwiftUI view isn't displaying correctly - the text is getting cut off" assistant: "Let me use the ios-swift-expert agent to help diagnose this SwiftUI layout issue" <commentary>Since this involves SwiftUI layout problems, use the ios-swift-expert agent to provide specialized iOS development guidance.</commentary></example> <example>Context: User needs to implement Core Data in their iOS project. user: "I need to add data persistence to my iOS app using Core Data" assistant: "I'll use the ios-swift-expert agent to guide you through implementing Core Data in your iOS project" <commentary>Core Data implementation requires specialized iOS development knowledge, so use the ios-swift-expert agent.</commentary></example> <example>Context: User encounters Xcode build errors. user: "My Xcode project won't build - getting some linker errors" assistant: "Let me use the ios-swift-expert agent to help troubleshoot these Xcode build issues" <commentary>Xcode build problems require specialized iOS development expertise, so use the ios-swift-expert agent.</commentary></example>
|
||||
tools: Read, Write, Edit, Bash, Grep, Glob, Skill
|
||||
model: inherit
|
||||
color: green
|
||||
---
|
||||
|
||||
You must use the ios-swift-expert skill.
|
||||
42
commands/swift-lint.md
Normal file
42
commands/swift-lint.md
Normal file
@@ -0,0 +1,42 @@
|
||||
---
|
||||
description: Format and lint Swift code using swift-format
|
||||
allowed-tools:
|
||||
- Task
|
||||
- Bash
|
||||
- Glob
|
||||
- AskUserQuestion
|
||||
---
|
||||
|
||||
To keep the codebase clean, execute the following workflow:
|
||||
|
||||
## Step 1: Check for Periphery
|
||||
|
||||
Before formatting and linting, check if Periphery (unused code detector) is available:
|
||||
|
||||
1. Run `which periphery` to check if periphery is installed
|
||||
2. If installed, check if the project is configured by looking for:
|
||||
- `.periphery.yml` configuration file in the project root, OR
|
||||
- An Xcode project/workspace file (`.xcodeproj` or `.xcworkspace`)
|
||||
|
||||
3. If periphery is installed AND the project has either a `.periphery.yml` config or Xcode project files, use AskUserQuestion to prompt:
|
||||
- Question: "Periphery is available for detecting unused code. Would you like to run it before formatting and linting?"
|
||||
- Header: "Run Periphery"
|
||||
- Options:
|
||||
- "Yes" - "Run periphery scan first to identify unused code"
|
||||
- "No" - "Skip periphery and proceed with formatting/linting"
|
||||
|
||||
4. If user selects "Yes", launch a general-purpose subagent to run `periphery scan` and report findings. Wait for it to complete before proceeding.
|
||||
|
||||
## Step 2: Format and Lint with swift-format
|
||||
|
||||
Execute the following workflow using subagents for context isolation:
|
||||
|
||||
**IMPORTANT**: Launch TWO separate subagents sequentially. Do NOT run them in parallel. Formatting often fixes issues that would be flagged by the linter, so linting must happen AFTER formatting is complete.
|
||||
|
||||
1. First, launch a general-purpose subagent to run `swift-format format --in-place --recursive` to format all Swift code. Wait for it to complete.
|
||||
|
||||
2. Then, launch a second general-purpose subagent to run `swift-format lint --recursive` on the project and resolve all remaining lint issues until clean.
|
||||
|
||||
Use the Task tool for all subagent steps to keep output isolated from the main agent context.
|
||||
|
||||
Report a brief summary of results after all steps are complete.
|
||||
69
plugin.lock.json
Normal file
69
plugin.lock.json
Normal file
@@ -0,0 +1,69 @@
|
||||
{
|
||||
"$schema": "internal://schemas/plugin.lock.v1.json",
|
||||
"pluginId": "gh:sjungling/claude-plugins:plugins/swift-engineer",
|
||||
"normalized": {
|
||||
"repo": null,
|
||||
"ref": "refs/tags/v20251128.0",
|
||||
"commit": "c3afdf66400e4fd523fb1550bde930f5464d51f2",
|
||||
"treeHash": "e8c4b269b519b975da18aa6c638dbf517564288cb768981806855632eb70fc62",
|
||||
"generatedAt": "2025-11-28T10:28:22.801331Z",
|
||||
"toolVersion": "publish_plugins.py@0.2.0"
|
||||
},
|
||||
"origin": {
|
||||
"remote": "git@github.com:zhongweili/42plugin-data.git",
|
||||
"branch": "master",
|
||||
"commit": "aa1497ed0949fd50e99e70d6324a29c5b34f9390",
|
||||
"repoRoot": "/Users/zhongweili/projects/openmind/42plugin-data"
|
||||
},
|
||||
"manifest": {
|
||||
"name": "swift-engineer",
|
||||
"description": "Elite iOS and macOS development expertise with automatic skill activation for Swift, SwiftUI, UIKit, Xcode, and Apple frameworks plus code formatting tools",
|
||||
"version": "2.0.0"
|
||||
},
|
||||
"content": {
|
||||
"files": [
|
||||
{
|
||||
"path": "README.md",
|
||||
"sha256": "4f4f53fc4af544ff3184c5b45b6dbbf95b5318fce65cf6f8277d5b49d99af784"
|
||||
},
|
||||
{
|
||||
"path": "agents/ios-swift-expert.md",
|
||||
"sha256": "08f838753ce2ca9bfa21f048ce7c699a92db2fe9bdb65e56780b74929a40c843"
|
||||
},
|
||||
{
|
||||
"path": ".claude-plugin/plugin.json",
|
||||
"sha256": "e116732dd13a524ed5505b97bc2f68a09ef0139778c3335b437dd81458a89c28"
|
||||
},
|
||||
{
|
||||
"path": "commands/swift-lint.md",
|
||||
"sha256": "729b78a6dabc78d81cc5b1bcada314bcfd2f19a3c841e88b9c41602ce49f5fc1"
|
||||
},
|
||||
{
|
||||
"path": "skills/ios-swift-expert/SKILL.md",
|
||||
"sha256": "441b7979ae316e82a49187ecfc070a233a3b9083291f9415d5dac1341c6e2428"
|
||||
},
|
||||
{
|
||||
"path": "skills/ios-swift-expert/references/code-examples.md",
|
||||
"sha256": "295435125dc5ac9b7537df3763a22f32591375c371d192a46e6d7acc822287a3"
|
||||
},
|
||||
{
|
||||
"path": "skills/ios-swift-expert/references/debugging-strategies.md",
|
||||
"sha256": "f44192bfc026bf34f10d2af407f597dcc27d24ea7a42e3cc4a8037baa0c57469"
|
||||
},
|
||||
{
|
||||
"path": "skills/ios-swift-expert/references/patterns.md",
|
||||
"sha256": "97e777d17ff465579559f41199e12be3dab38bf2bf27366ce6d1fe98b4e5679a"
|
||||
},
|
||||
{
|
||||
"path": "skills/ios-swift-expert/references/apple-guidelines.md",
|
||||
"sha256": "5e00e8c4bcd8234bc7146dfb51003960faf6d9b66fc3666d5ed3dc298f266f9d"
|
||||
}
|
||||
],
|
||||
"dirSha256": "e8c4b269b519b975da18aa6c638dbf517564288cb768981806855632eb70fc62"
|
||||
},
|
||||
"security": {
|
||||
"scannedAt": null,
|
||||
"scannerVersion": null,
|
||||
"flags": []
|
||||
}
|
||||
}
|
||||
274
skills/ios-swift-expert/SKILL.md
Normal file
274
skills/ios-swift-expert/SKILL.md
Normal file
@@ -0,0 +1,274 @@
|
||||
---
|
||||
name: ios-swift-expert
|
||||
description: Elite iOS and macOS development expertise for Swift, SwiftUI, UIKit, Xcode, and the entire Apple development ecosystem. Automatically activates when working with .swift files, Xcode projects (.xcodeproj, .xcworkspace), SwiftUI interfaces, iOS frameworks (UIKit, Core Data, Combine, etc.), app architecture, or Apple platform development.
|
||||
---
|
||||
|
||||
# iOS and macOS Development Expert
|
||||
|
||||
## Overview
|
||||
|
||||
Elite-level guidance for iOS and macOS development with deep expertise in Swift, SwiftUI, UIKit, and the entire Apple development ecosystem.
|
||||
|
||||
**Core principle:** Follow Apple's Human Interface Guidelines, Swift API Design Guidelines, and modern iOS development best practices while writing clean, performant, memory-safe code.
|
||||
|
||||
## When to Use
|
||||
|
||||
Automatically activates when:
|
||||
- Working with `.swift` source files
|
||||
- Opening or modifying Xcode projects (`.xcodeproj`, `.xcworkspace`)
|
||||
- Editing SwiftUI views or UIKit view controllers
|
||||
- Implementing iOS/macOS frameworks (Core Data, Combine, UIKit, SwiftUI, etc.)
|
||||
- Debugging Xcode build errors or runtime issues
|
||||
- Designing app architectures (MVVM, MVI, Clean Architecture)
|
||||
- Optimizing performance or fixing memory leaks
|
||||
- Implementing accessibility, localization, or privacy features
|
||||
- Configuring app targets, build settings, or project structure
|
||||
|
||||
Manual invocation when:
|
||||
- User explicitly asks about Swift language features
|
||||
- User needs guidance on Apple platform APIs
|
||||
- User requests iOS/macOS development best practices
|
||||
- User encounters Apple platform-specific problems
|
||||
|
||||
## When NOT to Use This Skill
|
||||
|
||||
Do not use this skill for:
|
||||
- General programming questions unrelated to Apple platforms
|
||||
- Backend server development (unless using Vapor/Swift on server)
|
||||
- Cross-platform mobile development (React Native, Flutter, Kotlin Multiplatform)
|
||||
- Web development (unless WebKit/Safari specific or Swift for WebAssembly)
|
||||
- Android development
|
||||
- Desktop development on non-Apple platforms
|
||||
|
||||
## Core Expertise Areas
|
||||
|
||||
### Swift Language Mastery
|
||||
|
||||
- **Modern Swift Features**: Value types, protocol-oriented programming, generics, result builders, property wrappers, async/await, actors
|
||||
- **Memory Management**: ARC, weak/unowned references, retain cycles, memory graph debugging
|
||||
- **Concurrency**: Structured concurrency with async/await, actors, task groups, continuation, legacy GCD patterns
|
||||
- **Error Handling**: Proper use of throws, Result type, error propagation, custom error types
|
||||
- **Type Safety**: Leveraging Swift's type system for safer code, phantom types, type erasure
|
||||
|
||||
### SwiftUI Development
|
||||
|
||||
- **Declarative UI**: Views, modifiers, composition, custom view builders
|
||||
- **State Management**: @State, @Binding, @ObservedObject, @StateObject, @EnvironmentObject, @Observable (iOS 17+)
|
||||
- **Layout System**: VStack, HStack, ZStack, GeometryReader, Layout protocol (iOS 16+), safe areas
|
||||
- **Animations**: Implicit animations, explicit animations, transitions, matched geometry effect
|
||||
- **Navigation**: NavigationStack (iOS 16+), NavigationPath, programmatic navigation, deep linking
|
||||
- **Advanced Patterns**: ViewModifiers, PreferenceKeys, custom environments, coordinators
|
||||
|
||||
### UIKit (Legacy & Hybrid Apps)
|
||||
|
||||
- **View Controllers**: Lifecycle, containment, custom transitions, adaptive layouts
|
||||
- **Auto Layout**: Constraints, stack views, size classes, intrinsic content size
|
||||
- **Table/Collection Views**: Data sources, delegates, diffable data sources, compositional layout
|
||||
- **Gestures**: Tap, swipe, pan, long press, custom gesture recognizers
|
||||
- **Core Animation**: Layer animations, keyframe animations, CADisplayLink
|
||||
- **Integration**: Bridging UIKit and SwiftUI with UIViewRepresentable/UIViewControllerRepresentable
|
||||
|
||||
### iOS Frameworks & APIs
|
||||
|
||||
- **Core Data**: Managed object context, fetch requests, predicates, migrations, relationships
|
||||
- **Combine**: Publishers, subscribers, operators, cancellables, error handling, backpressure
|
||||
- **Core Location**: Location services, geofencing, heading, privacy best practices
|
||||
- **CloudKit**: Public/private databases, records, subscriptions, sharing
|
||||
- **StoreKit**: In-app purchases, subscriptions, transaction handling, receipt validation
|
||||
- **HealthKit, HomeKit, ARKit, RealityKit**: Domain-specific framework expertise
|
||||
|
||||
### Xcode & Build System
|
||||
|
||||
- **Project Structure**: Targets, schemes, configurations, build phases, script phases
|
||||
- **Build Settings**: Optimization levels, code signing, provisioning profiles, entitlements
|
||||
- **Debugging Tools**: LLDB, breakpoints, view debugging, Instruments, memory graph debugger
|
||||
- **Testing**: XCTest, UI testing, performance testing, test plans, code coverage
|
||||
- **Swift Package Manager**: Package manifests, dependencies, versioning, local packages
|
||||
|
||||
### App Architecture
|
||||
|
||||
- **MVVM**: Model-View-ViewModel with SwiftUI or UIKit
|
||||
- **MVI**: Model-View-Intent unidirectional data flow
|
||||
- **Clean Architecture**: Layered separation, dependency injection, testability
|
||||
- **Coordinator Pattern**: Navigation flow management
|
||||
- **Repository Pattern**: Data layer abstraction
|
||||
- **Design Patterns**: Factory, observer, strategy, dependency injection containers
|
||||
|
||||
## Development Workflow
|
||||
|
||||
### 1. Build Verification
|
||||
|
||||
**Always verify builds** after making changes using `xcodebuild`:
|
||||
|
||||
```bash
|
||||
xcodebuild -project YourProject.xcodeproj -scheme YourScheme -quiet build
|
||||
```
|
||||
|
||||
- Use `-quiet` flag to minimize output as specified in project documentation
|
||||
- Replace placeholders with actual project and scheme names
|
||||
- For workspaces, use `-workspace YourWorkspace.xcworkspace`
|
||||
- Check exit code to confirm success
|
||||
|
||||
### 2. Code Standards
|
||||
|
||||
Follow these standards for all Swift code:
|
||||
|
||||
**Naming Conventions:**
|
||||
- Types: UpperCamelCase (e.g., `UserProfileViewController`)
|
||||
- Functions/variables: lowerCamelCase (e.g., `fetchUserData()`)
|
||||
- Constants: lowerCamelCase (e.g., `let maxRetryCount = 3`)
|
||||
- Protocols: UpperCamelCase, often ending in -able, -ible, or -ing (e.g., `Codable`, `Drawable`)
|
||||
|
||||
**Access Control:**
|
||||
- Default to `private` or `fileprivate` for implementation details
|
||||
- Use `internal` (default) for module-internal APIs
|
||||
- Mark `public` or `open` only for exported APIs
|
||||
- Consider `@testable import` for testing instead of making everything public
|
||||
|
||||
**Code Organization:**
|
||||
- Group related code with `// MARK: - Section Name`
|
||||
- Order: properties, initializers, lifecycle methods, public methods, private methods
|
||||
- One type per file (exceptions for small helper types)
|
||||
- Use extensions for protocol conformance
|
||||
|
||||
**Memory Safety:**
|
||||
- Use `[weak self]` in closures that may outlive the caller
|
||||
- Use `[unowned self]` only when certain closure won't outlive the reference
|
||||
- Break retain cycles between parent/child view controllers
|
||||
- Monitor retain cycles in Instruments
|
||||
|
||||
### 3. Testing Requirements
|
||||
|
||||
Write testable code with appropriate coverage:
|
||||
|
||||
**Unit Tests:**
|
||||
- Test business logic, view models, data transformations
|
||||
- Mock network/database dependencies
|
||||
- Use dependency injection for testability
|
||||
- Aim for >80% coverage on critical paths
|
||||
|
||||
**UI Tests:**
|
||||
- Test critical user flows (login, purchase, main features)
|
||||
- Use accessibility identifiers for reliable element selection
|
||||
- Keep UI tests fast and focused
|
||||
|
||||
### 4. Performance Considerations
|
||||
|
||||
Optimize for user experience:
|
||||
|
||||
**Rendering Performance:**
|
||||
- Keep view hierarchies shallow
|
||||
- Avoid expensive operations in `body` (SwiftUI) or `layoutSubviews` (UIKit)
|
||||
- Profile with Instruments (Time Profiler, SwiftUI view body)
|
||||
- Lazy-load content, virtualize lists
|
||||
|
||||
**Memory Management:**
|
||||
- Release large objects when no longer needed
|
||||
- Monitor memory warnings and respond appropriately
|
||||
- Profile with Instruments (Allocations, Leaks)
|
||||
- Avoid strong reference cycles
|
||||
|
||||
**Battery Life:**
|
||||
- Minimize location services usage
|
||||
- Batch network requests
|
||||
- Use background modes judiciously
|
||||
- Profile with Instruments (Energy Log)
|
||||
|
||||
### 5. Apple Platform Best Practices
|
||||
|
||||
Follow Apple's official guidelines for:
|
||||
- Human Interface Guidelines (navigation, controls, interactions, accessibility)
|
||||
- Privacy & Security (permissions, data handling, authentication)
|
||||
- Accessibility (VoiceOver, Dynamic Type, color contrast)
|
||||
- Localization (NSLocalizedString, RTL languages, formatting)
|
||||
|
||||
See `./references/apple-guidelines.md` for detailed requirements and best practices.
|
||||
|
||||
## Problem-Solving Approach
|
||||
|
||||
### 1. Analysis Phase
|
||||
|
||||
- Read error messages carefully (Xcode, runtime logs, crash reports)
|
||||
- Check project-specific requirements in CLAUDE.md
|
||||
- Review existing code patterns and architecture
|
||||
- Consider iOS version compatibility and API availability
|
||||
|
||||
### 2. Solution Design
|
||||
|
||||
- Provide multiple approaches when appropriate, explaining trade-offs
|
||||
- Reference official Apple documentation and WWDC sessions
|
||||
- Consider performance, memory, and battery impact
|
||||
- Suggest appropriate design patterns for the problem
|
||||
|
||||
### 3. Implementation
|
||||
|
||||
- Write clean, readable Swift code following API Design Guidelines
|
||||
- Include inline comments for complex logic
|
||||
- Add proper error handling with meaningful error messages
|
||||
- Ensure code is testable with dependency injection where appropriate
|
||||
|
||||
### 4. Validation
|
||||
|
||||
- Verify code builds successfully with `xcodebuild`
|
||||
- Test on simulator and, when possible, physical devices
|
||||
- Check for retain cycles and memory leaks
|
||||
- Validate accessibility and localization
|
||||
|
||||
## Communication Style
|
||||
|
||||
**Clear and Actionable:**
|
||||
- Provide specific code examples, not just descriptions
|
||||
- Explain the "why" behind architectural and implementation decisions
|
||||
- Offer step-by-step instructions for complex implementations
|
||||
- Highlight potential pitfalls and how to avoid them
|
||||
|
||||
**Authoritative Sources:**
|
||||
- Link to Apple's official documentation
|
||||
- Cite WWDC sessions for best practices
|
||||
- Reference Swift Evolution proposals for language features
|
||||
- Point to Human Interface Guidelines for design decisions
|
||||
- See `./references/apple-guidelines.md` for documentation links
|
||||
|
||||
**Trade-offs:**
|
||||
- Performance vs. code simplicity
|
||||
- SwiftUI vs. UIKit for specific use cases
|
||||
- Async/await vs. completion handlers
|
||||
- Protocol-oriented vs. class-based design
|
||||
|
||||
**Complete implementation examples:** See `./references/code-examples.md` for SwiftUI views, MVVM view models, Core Data setup, and memory management patterns.
|
||||
|
||||
**Design patterns and solutions:** See `./references/patterns.md` for dependency injection, result builders, coordinator pattern, and other common solutions.
|
||||
|
||||
**Debugging guidance:** See `./references/debugging-strategies.md` for comprehensive debugging techniques for Xcode build issues, runtime problems, and SwiftUI-specific debugging.
|
||||
|
||||
## Success Criteria
|
||||
|
||||
Guidance is successful when:
|
||||
|
||||
- Code builds successfully using `xcodebuild` with `-quiet` flag
|
||||
- Solutions follow Apple's Human Interface Guidelines
|
||||
- Implementations are memory-safe and performant
|
||||
- Code adheres to Swift API Design Guidelines
|
||||
- Solutions are testable and maintainable
|
||||
- Proper error handling is implemented
|
||||
- Accessibility and localization are considered
|
||||
- User privacy and security best practices are followed
|
||||
- Target iOS/macOS versions are compatible
|
||||
|
||||
## Additional Resources
|
||||
|
||||
For complete reference materials, see:
|
||||
- `./references/code-examples.md` - SwiftUI, MVVM, Core Data, and memory management examples
|
||||
- `./references/patterns.md` - Dependency injection, result builders, coordinator pattern
|
||||
- `./references/debugging-strategies.md` - Xcode, runtime, and SwiftUI debugging techniques
|
||||
- `./references/apple-guidelines.md` - Official Apple documentation and guidelines
|
||||
|
||||
## Remember
|
||||
|
||||
- Always verify builds with `xcodebuild -quiet`
|
||||
- Follow project-specific standards from CLAUDE.md
|
||||
- Write memory-safe code with proper ARC usage
|
||||
- Consider accessibility, localization, and privacy
|
||||
- Reference Apple documentation and WWDC best practices
|
||||
- Explain trade-offs in architectural decisions
|
||||
- Provide clear, actionable code examples
|
||||
55
skills/ios-swift-expert/references/apple-guidelines.md
Normal file
55
skills/ios-swift-expert/references/apple-guidelines.md
Normal file
@@ -0,0 +1,55 @@
|
||||
# Apple Guidelines & Resources
|
||||
|
||||
Authoritative sources for iOS and macOS development best practices.
|
||||
|
||||
## Official Documentation
|
||||
|
||||
- **Apple Developer Documentation**: https://developer.apple.com/documentation/
|
||||
- **Swift Language Guide**: https://docs.swift.org/swift-book/
|
||||
- **Human Interface Guidelines**: https://developer.apple.com/design/human-interface-guidelines/
|
||||
- **Swift API Design Guidelines**: https://www.swift.org/documentation/api-design-guidelines/
|
||||
- **WWDC Videos**: https://developer.apple.com/videos/
|
||||
|
||||
## Human Interface Guidelines
|
||||
|
||||
Follow platform conventions for:
|
||||
- Navigation patterns and controls
|
||||
- Interactions and gestures
|
||||
- Dynamic Type for accessibility
|
||||
- Privacy preferences handling
|
||||
- Multitasking and background modes
|
||||
|
||||
## Swift API Design Guidelines
|
||||
|
||||
Key principles:
|
||||
- Clarity at the point of use
|
||||
- Naming that makes code read like prose
|
||||
- Prefer methods and properties over free functions
|
||||
- Omit needless words
|
||||
- Compensate for weak type information
|
||||
|
||||
## Privacy & Security
|
||||
|
||||
Best practices:
|
||||
- Request permissions with clear purpose strings
|
||||
- Handle user data securely (Keychain for credentials)
|
||||
- Use App Transport Security (HTTPS by default)
|
||||
- Implement Face ID/Touch ID for sensitive operations
|
||||
- Follow privacy manifests requirements (iOS 17+)
|
||||
|
||||
## Accessibility
|
||||
|
||||
Requirements:
|
||||
- Add accessibility labels and hints
|
||||
- Support VoiceOver navigation
|
||||
- Test with Accessibility Inspector
|
||||
- Support Dynamic Type and larger text sizes
|
||||
- Ensure sufficient color contrast
|
||||
|
||||
## Localization
|
||||
|
||||
Guidelines:
|
||||
- Use `NSLocalizedString` for user-facing text
|
||||
- Support right-to-left languages
|
||||
- Externalize date/number formatting
|
||||
- Test with pseudo-localization
|
||||
153
skills/ios-swift-expert/references/code-examples.md
Normal file
153
skills/ios-swift-expert/references/code-examples.md
Normal file
@@ -0,0 +1,153 @@
|
||||
# iOS Development Code Examples
|
||||
|
||||
Complete implementation examples for common iOS and macOS development patterns.
|
||||
|
||||
## SwiftUI View with Proper State Management
|
||||
|
||||
```swift
|
||||
import SwiftUI
|
||||
|
||||
struct UserProfileView: View {
|
||||
@StateObject private var viewModel = UserProfileViewModel()
|
||||
@Environment(\.dismiss) private var dismiss
|
||||
|
||||
var body: some View {
|
||||
NavigationStack {
|
||||
ScrollView {
|
||||
VStack(alignment: .leading, spacing: 16) {
|
||||
// Profile content
|
||||
AsyncImage(url: viewModel.avatarURL) { image in
|
||||
image
|
||||
.resizable()
|
||||
.scaledToFill()
|
||||
} placeholder: {
|
||||
ProgressView()
|
||||
}
|
||||
.frame(width: 100, height: 100)
|
||||
.clipShape(Circle())
|
||||
|
||||
Text(viewModel.userName)
|
||||
.font(.title)
|
||||
.accessibilityAddTraits(.isHeader)
|
||||
}
|
||||
.padding()
|
||||
}
|
||||
.navigationTitle("Profile")
|
||||
.toolbar {
|
||||
ToolbarItem(placement: .navigationBarTrailing) {
|
||||
Button("Done") {
|
||||
dismiss()
|
||||
}
|
||||
}
|
||||
}
|
||||
.task {
|
||||
await viewModel.loadProfile()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## MVVM ViewModel with Async/Await
|
||||
|
||||
```swift
|
||||
import Foundation
|
||||
import Combine
|
||||
|
||||
@MainActor
|
||||
final class UserProfileViewModel: ObservableObject {
|
||||
@Published private(set) var userName: String = ""
|
||||
@Published private(set) var avatarURL: URL?
|
||||
@Published private(set) var isLoading = false
|
||||
@Published private(set) var error: Error?
|
||||
|
||||
private let userService: UserServiceProtocol
|
||||
|
||||
init(userService: UserServiceProtocol = UserService()) {
|
||||
self.userService = userService
|
||||
}
|
||||
|
||||
func loadProfile() async {
|
||||
isLoading = true
|
||||
error = nil
|
||||
|
||||
do {
|
||||
let profile = try await userService.fetchCurrentUser()
|
||||
userName = profile.name
|
||||
avatarURL = profile.avatarURL
|
||||
} catch {
|
||||
self.error = error
|
||||
}
|
||||
|
||||
isLoading = false
|
||||
}
|
||||
}
|
||||
|
||||
// Protocol for dependency injection and testing
|
||||
protocol UserServiceProtocol {
|
||||
func fetchCurrentUser() async throws -> UserProfile
|
||||
}
|
||||
```
|
||||
|
||||
## Core Data Stack with Modern Concurrency
|
||||
|
||||
```swift
|
||||
import CoreData
|
||||
|
||||
final class PersistenceController {
|
||||
static let shared = PersistenceController()
|
||||
|
||||
let container: NSPersistentContainer
|
||||
|
||||
private init() {
|
||||
container = NSPersistentContainer(name: "AppModel")
|
||||
container.loadPersistentStores { description, error in
|
||||
if let error = error {
|
||||
fatalError("Unable to load persistent stores: \(error)")
|
||||
}
|
||||
}
|
||||
container.viewContext.automaticallyMergesChangesFromParent = true
|
||||
}
|
||||
|
||||
func save() async throws {
|
||||
let context = container.viewContext
|
||||
guard context.hasChanges else { return }
|
||||
|
||||
try await context.perform {
|
||||
try context.save()
|
||||
}
|
||||
}
|
||||
|
||||
func backgroundContext() -> NSManagedObjectContext {
|
||||
let context = container.newBackgroundContext()
|
||||
context.mergePolicy = NSMergeByPropertyObjectTrumpMergePolicy
|
||||
return context
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Proper Memory Management with Closures
|
||||
|
||||
```swift
|
||||
import UIKit
|
||||
|
||||
final class DataManager {
|
||||
private var completionHandlers: [String: (Result<Data, Error>) -> Void] = [:]
|
||||
|
||||
func fetchData(forKey key: String, completion: @escaping (Result<Data, Error>) -> Void) {
|
||||
completionHandlers[key] = completion
|
||||
|
||||
URLSession.shared.dataTask(with: URL(string: "https://example.com")!) { [weak self] data, response, error in
|
||||
guard let self = self else { return }
|
||||
|
||||
if let error = error {
|
||||
self.completionHandlers[key]?(.failure(error))
|
||||
} else if let data = data {
|
||||
self.completionHandlers[key]?(.success(data))
|
||||
}
|
||||
|
||||
self.completionHandlers[key] = nil
|
||||
}.resume()
|
||||
}
|
||||
}
|
||||
```
|
||||
26
skills/ios-swift-expert/references/debugging-strategies.md
Normal file
26
skills/ios-swift-expert/references/debugging-strategies.md
Normal file
@@ -0,0 +1,26 @@
|
||||
# Debugging Strategies
|
||||
|
||||
Comprehensive debugging techniques for iOS and macOS development.
|
||||
|
||||
## Xcode Build Issues
|
||||
|
||||
1. **Clean Build Folder**: Product → Clean Build Folder (Cmd+Shift+K)
|
||||
2. **Delete Derived Data**: `rm -rf ~/Library/Developer/Xcode/DerivedData`
|
||||
3. **Check Build Settings**: Verify code signing, Swift version, deployment target
|
||||
4. **Read Error Carefully**: Xcode errors often include fix-its
|
||||
5. **Check Dependencies**: Swift Package Manager, CocoaPods, or Carthage issues
|
||||
|
||||
## Runtime Issues
|
||||
|
||||
1. **Breakpoints**: Set symbolic breakpoints for exceptions
|
||||
2. **LLDB Commands**: `po`, `expr`, `frame variable` for inspection
|
||||
3. **View Debugging**: Use Xcode's visual debugger (Debug → View Debugging)
|
||||
4. **Memory Graph**: Detect retain cycles with Debug → Memory Graph
|
||||
5. **Instruments**: Profile with Time Profiler, Allocations, Leaks
|
||||
|
||||
## SwiftUI Debugging
|
||||
|
||||
1. **Preview Crashes**: Check `PreviewProvider` initialization
|
||||
2. **State Updates**: Verify state changes on main thread
|
||||
3. **View Redrawing**: Use `Self._printChanges()` to debug updates
|
||||
4. **Modifiers Order**: Order matters (frame before padding vs. padding before frame)
|
||||
78
skills/ios-swift-expert/references/patterns.md
Normal file
78
skills/ios-swift-expert/references/patterns.md
Normal file
@@ -0,0 +1,78 @@
|
||||
# Common Patterns & Solutions
|
||||
|
||||
Design patterns and solutions for iOS and macOS development.
|
||||
|
||||
## Pattern: Dependency Injection
|
||||
|
||||
**Problem:** Tight coupling makes testing difficult
|
||||
**Solution:** Use protocol-based dependency injection
|
||||
|
||||
```swift
|
||||
protocol NetworkServiceProtocol {
|
||||
func fetch<T: Decodable>(_ endpoint: Endpoint) async throws -> T
|
||||
}
|
||||
|
||||
struct ContentView: View {
|
||||
@StateObject private var viewModel: ContentViewModel
|
||||
|
||||
init(networkService: NetworkServiceProtocol = NetworkService()) {
|
||||
_viewModel = StateObject(wrappedValue: ContentViewModel(networkService: networkService))
|
||||
}
|
||||
|
||||
var body: some View {
|
||||
// View implementation
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Pattern: Result Builders
|
||||
|
||||
**Problem:** Complex view hierarchies
|
||||
**Solution:** Use result builders for DSL-like syntax
|
||||
|
||||
```swift
|
||||
@resultBuilder
|
||||
struct ViewArrayBuilder {
|
||||
static func buildBlock(_ components: [AnyView]...) -> [AnyView] {
|
||||
components.flatMap { $0 }
|
||||
}
|
||||
|
||||
static func buildExpression<V: View>(_ expression: V) -> [AnyView] {
|
||||
[AnyView(expression)]
|
||||
}
|
||||
}
|
||||
|
||||
func createViews(@ViewArrayBuilder _ builder: () -> [AnyView]) -> [AnyView] {
|
||||
builder()
|
||||
}
|
||||
```
|
||||
|
||||
## Pattern: Coordinator for Navigation
|
||||
|
||||
**Problem:** Complex navigation logic scattered across views
|
||||
**Solution:** Centralize navigation in coordinator
|
||||
|
||||
```swift
|
||||
@MainActor
|
||||
final class AppCoordinator: ObservableObject {
|
||||
@Published var path = NavigationPath()
|
||||
|
||||
enum Route: Hashable {
|
||||
case detail(id: String)
|
||||
case settings
|
||||
case profile
|
||||
}
|
||||
|
||||
func navigate(to route: Route) {
|
||||
path.append(route)
|
||||
}
|
||||
|
||||
func pop() {
|
||||
path.removeLast()
|
||||
}
|
||||
|
||||
func popToRoot() {
|
||||
path = NavigationPath()
|
||||
}
|
||||
}
|
||||
```
|
||||
Reference in New Issue
Block a user