import SwiftUI import Foundation let global_endpoint = Endpoint2() func timeString(from: TimeInterval) -> String { let minutes = Int(from) / 60 let seconds = Int(from) % 60 return String(format: "%04d:%02d", minutes, seconds) } struct ContentView: View { @State var timer: Timer? @State var elapsed: TimeInterval = 0 var body: some View { VStack { Image(systemName: "globe") .imageScale(.large) .foregroundStyle(.tint) Text("Hello, world!") Text(timeString(from: elapsed)) .font(.largeTitle) .padding() Button("Start Traffic") { TrafficController.shared.startEndpoint() timer = Timer.scheduledTimer(withTimeInterval: 0.01, repeats: true) { _ in elapsed += 0.01 } } } .padding() } } #Preview { ContentView() } class TrafficController: NSObject, URLSessionDataDelegate, URLSessionTaskDelegate { static let shared = TrafficController() static let ftp_url_string = "ftp://lanforge:lanforge@10.0.0.7/test-file10M.bin" private lazy var session: URLSession = { let configuration = URLSessionConfiguration.default return URLSession(configuration: configuration, delegate: self, delegateQueue: nil) }() override init() { print("DEBUG: Called init for L4Handler!") super.init() } deinit { print("DEBUG: L4Handler deinit called. Deallocating both URLSession and URLSessionDelegate!") } func urlSession(_ session: URLSession, task: URLSessionTask, didCompleteWithError error: Error?) { if let error = error { print("ERROR: got error in urlSession(didComplete): \(error)") } } func startEndpoint() { global_endpoint.session = session global_endpoint.startTest() } } class Endpoint2 { var session: URLSession! var worker: Task? init() {} // MARK -- Protocol API func startTest() { guard worker == nil else { return } worker = Task { while !Task.isCancelled { doTrafficRound() // hard code 2 URLs per second try await Task.sleep(nanoseconds: UInt64(0.2 * 1_000_000_000)) } } } func stopTest() { guard let workerTask = worker else { print("ERROR: Cannot stop worker is already NULL") return } workerTask.cancel() } func doTrafficRound() { print("DEBUG: doing traffic round") if let url_object = URL(string: TrafficController.ftp_url_string) { let newTask = self.session.dataTask(with: url_object) newTask.resume() } else { print("DEBUG: Could not form URL from string: \(TrafficController.ftp_url_string)") } } }