diff --git a/bitchat/Services/BLEService.swift b/bitchat/Services/BLEService.swift index 4d5702af..0585167a 100644 --- a/bitchat/Services/BLEService.swift +++ b/bitchat/Services/BLEService.swift @@ -1921,10 +1921,10 @@ final class BLEService: NSObject { } lastIsolatedAt = nil // Base threshold when connected - var threshold = -90 + var threshold = TransportConfig.bleDynamicRSSIThresholdDefault // If we're at budget or queue is large, prefer closer peers let linkCount = peripherals.values.filter { $0.isConnected || $0.isConnecting }.count - if linkCount >= maxCentralLinks || connectionCandidates.count > 20 { + if linkCount >= maxCentralLinks || connectionCandidates.count > TransportConfig.bleConnectionCandidatesMax { threshold = -85 } // If we have many recent timeouts, raise further @@ -2666,7 +2666,7 @@ extension BLEService: CBPeripheralManagerDelegate { } } else { // If buffer grows suspiciously large, reset to avoid memory leak - if combined.count > 1_000_000 { // 1MB cap for safety + if combined.count > TransportConfig.blePendingWriteBufferCapBytes { // cap for safety pendingWriteBuffers.removeValue(forKey: centralUUID) SecureLogger.log("⚠️ Dropping oversized pending write buffer (\(combined.count) bytes) for central \(centralUUID)", category: SecureLogger.session, level: .warning) } diff --git a/bitchat/Services/NostrTransport.swift b/bitchat/Services/NostrTransport.swift index c2df2978..225b3ae0 100644 --- a/bitchat/Services/NostrTransport.swift +++ b/bitchat/Services/NostrTransport.swift @@ -20,7 +20,7 @@ final class NostrTransport: Transport { } private var readQueue: [QueuedRead] = [] private var isSendingReadAcks = false - private let readAckInterval: TimeInterval = 0.35 // ~3 per second + private let readAckInterval: TimeInterval = TransportConfig.nostrReadAckInterval var myPeerID: String { senderPeerID } var myNickname: String { "" } diff --git a/bitchat/Services/TransportConfig.swift b/bitchat/Services/TransportConfig.swift index 730afc6d..b471057b 100644 --- a/bitchat/Services/TransportConfig.swift +++ b/bitchat/Services/TransportConfig.swift @@ -25,4 +25,16 @@ enum TransportConfig { static let bleDutyOnDuration: TimeInterval = 5.0 static let bleDutyOffDuration: TimeInterval = 10.0 static let bleAnnounceMinInterval: TimeInterval = 1.0 + + // BLE discovery/quality thresholds + static let bleDynamicRSSIThresholdDefault: Int = -90 + static let bleConnectionCandidatesMax: Int = 20 + static let blePendingWriteBufferCapBytes: Int = 1_000_000 + + // Nostr + static let nostrReadAckInterval: TimeInterval = 0.35 // ~3 per second + + // UI thresholds + static let uiLateInsertThreshold: TimeInterval = 15.0 + static let uiProcessedNostrEventsCap: Int = 2000 } diff --git a/bitchat/ViewModels/ChatViewModel.swift b/bitchat/ViewModels/ChatViewModel.swift index 8b9378b0..06431d31 100644 --- a/bitchat/ViewModels/ChatViewModel.swift +++ b/bitchat/ViewModels/ChatViewModel.swift @@ -349,7 +349,7 @@ class ChatViewModel: ObservableObject, BitchatDelegate { // PeerManager replaced by UnifiedPeerService private var processedNostrEvents = Set() // Simple deduplication private var processedNostrEventOrder: [String] = [] - private let maxProcessedNostrEvents = 2000 + private let maxProcessedNostrEvents = TransportConfig.uiProcessedNostrEventsCap private let userDefaults = UserDefaults.standard private let nicknameKey = "bitchat.nickname" // Location channel state (macOS supports manual geohash selection) @@ -432,7 +432,7 @@ class ChatViewModel: ObservableObject, BitchatDelegate { private var dynamicPublicFlushInterval: TimeInterval = TransportConfig.basePublicFlushInterval private var recentBatchSizes: [Int] = [] @Published private(set) var isBatchingPublic: Bool = false - private let lateInsertThreshold: TimeInterval = 15.0 + private let lateInsertThreshold: TimeInterval = TransportConfig.uiLateInsertThreshold // Track sent read receipts to avoid duplicates (persisted across launches) // Note: Persistence happens automatically in didSet, no lifecycle observers needed