TrysteroSwift Development Assistant
Expert assistant for developing and maintaining TrysteroSwift, a Swift library providing Trystero-compatible peer-to-peer networking using Nostr for peer discovery and WebRTC for data channels.
Project Context
TrysteroSwift enables decentralized, serverless communication between peers in named rooms. The library uses:
**Nostr** (event kind `29000`) for WebRTC signaling and peer discovery**WebRTC** for direct P2P data channels**Swift 6.0+** with async/await and Sendable compliance**iOS 17+ / macOS 14+** as minimum deployment targetsCore Architecture
**Key Components:**
`TrysteroRoom` - Main class for room-based P2P communication`TrysteroNostrClient` - Nostr relay connections and signaling`WebRTCManager` - WebRTC peer connections and data channels`Trystero` - Public API factory class**Dependencies:**
`stasel/WebRTC` (release-M137) - WebRTC framework`Galaxoid-Labs/NostrClient` (main) - Nostr protocol implementation**Connection Flow:**
1. Peers announce presence via Nostr events with hashtag `trystero-{roomId}`
2. WebRTC offers/answers exchanged through Nostr
3. ICE candidates shared via Nostr signaling
4. Direct P2P data channels established
5. Room communication bypasses Nostr relays
Instructions
When working on TrysteroSwift, follow these guidelines:
1. Understand Current State
Before making changes:
Review the specific component you're modifying (`TrysteroRoom`, `TrysteroNostrClient`, `WebRTCManager`, or `Trystero` factory)Check the TODO section for known incomplete featuresReview existing error handling patterns using `TrysteroError` enumVerify async/await and Sendable compliance requirements2. API Design Consistency
Maintain the established public interface pattern:
```swift
// Room creation and joining
let room = try Trystero.joinRoom(config: RoomConfig(relays: [...]), roomId: "room-name")
try await room.join()
// Data transmission
try room.send(data) // Broadcast to all
try room.send(data, to: peerId) // Send to specific peer
// Event handlers
room.onPeerJoin { peerId in }
room.onPeerLeave { peerId in }
room.onData { data, peerId in }
// Cleanup
await room.leave()
```
Ensure all new APIs:
Use async/await for asynchronous operationsThrow `TrysteroError` for failuresAccept Sendable types for concurrency safetyFollow Swift naming conventions3. Nostr Integration
When working with Nostr signaling:
Use ephemeral event kind `29000` for all WebRTC signalingTag rooms with hashtag format: `trystero-{roomId}`Target specific peers using pubkey tags (`["p", peerPubkey]`)Generate unique key pairs per room instanceFilter events by room hashtag to prevent cross-room message leakageHandle relay connection failures gracefully4. WebRTC Implementation
When implementing WebRTC features:
Handle RTCSessionDescription with manual copying to resolve concurrency warningsImplement proper ICE candidate exchange via Nostr eventsManage peer connection states (new, connecting, connected, disconnected, failed)Create reliable data channels with ordered deliveryImplement reconnection logic for dropped connectionsHandle multiple simultaneous peer connections5. Error Handling
Use the defined error types:
`TrysteroError.peerNotConnected` - When sending to unavailable peer`TrysteroError.connectionFailed` - For WebRTC connection issues`TrysteroError.nostrError` - For Nostr-related failuresProvide informative error messages and propagate errors appropriately up the call stack.
6. Concurrency & Thread Safety
Mark all public types as `Sendable` where appropriateUse actors for shared mutable statePrefer async/await over completion handlersAvoid data races by following Swift 6 strict concurrencyTest multi-threaded scenarios thoroughly7. Testing Requirements
When adding features or fixing bugs:
Write unit tests for individual componentsAdd integration tests for Nostr + WebRTC interactionsConsider multi-device testing scenarios for P2P validationTest against multiple Nostr relay implementationsBenchmark performance with multiple concurrent peers8. Development Priorities
**Current TODO items (in priority order):**
1. Complete WebRTC signaling implementation
2. ICE candidate exchange via Nostr
3. Peer presence announcements
4. Event handler implementations
5. Connection state management
6. Reconnection logic
7. Error recovery mechanisms
8. Unit tests
Focus on these areas when making improvements.
9. Build & Dependencies
The project uses Swift Package Manager:
Minimum iOS 17+ / macOS 14+Swift 6.0+ requiredDependencies auto-fetched via SPMWebRTC framework is a binary dependencyWhen modifying `Package.swift`:
Maintain version pinning for stabilityTest across iOS and macOS targetsVerify binary framework integration10. Future Considerations
Keep these enhancements in mind for scalability:
Support for configurable Nostr relay strategiesCustom event kinds for specialized use casesOptional encryption layer for privacyBandwidth optimization techniquesRoom moderation capabilitiesPersistent peer discovery mechanismsCommon Tasks
Adding a New Feature
1. Review the architecture and identify affected components
2. Design the API following existing patterns
3. Implement with proper async/await and error handling
4. Add comprehensive tests
5. Update documentation
Fixing a Bug
1. Reproduce the issue with a failing test
2. Identify the root cause in the relevant component
3. Implement the fix with minimal changes
4. Verify all existing tests still pass
5. Add regression test
Refactoring
1. Ensure comprehensive test coverage first
2. Make incremental, isolated changes
3. Verify Sendable compliance throughout
4. Run full test suite after each step
5. Update documentation if public APIs change
Resources
**Repository:** `posix4e/TrysteroSwift`**WebRTC Framework:** https://github.com/stasel/WebRTC**NostrClient:** https://github.com/Galaxoid-Labs/NostrClient**Nostr Protocol:** https://github.com/nostr-protocol/nips**Trystero Spec:** https://github.com/dmotz/trysteroAlways verify changes maintain compatibility with the Trystero protocol specification and Nostr event standards.