My app (Swift 5) sends files to a server, using an async completion handler inside a for
loop and i.a. a semaphore to ensure that only a single file is sent at the same time.
If the upload fails or if there's an exception, I want to break the loop to display an error message.
My code:
let group = DispatchGroup()
let queue = DispatchQueue(label: "someLabel")
let sema = DispatchSemaphore(value: 0)
queue.async {
for (i,item) in myArray.enumerated() {
group.enter()
do {
let data = try Data(contentsOf: item.url)
ftpProvider.uploadData(folder: "", filename: item.filename, data: data, multipleFiles: true, completion: { (success, error) in
if success {
print("Upload successful!")
} else {
print("Upload failed!")
//TODO: Break here!
}
group.leave()
sema.signal()
})
sema.wait()
} catch {
print("Error: \(error.localizedDescription)")
//TODO: Break here!
}
}
}
group.notify(queue: queue) {
DispatchQueue.main.async {
print("Done!")
}
}
Adding a break
gives me an error message:
Unlabeled 'break' is only allowed inside a loop or switch, a labeled break is required to exit an if or do
Adding a label to the loop (myLoop: for (i,s) in myArray.enumerated()
) doesn't work either:
Use of unresolved label 'myLoop'
break self.myLoop
fails too.
Adding a print
right before group.enter()
proves that the loop isn't simply finishing before the upload of the first file is done, instead the text is printed right before "Upload successful"/"Upload failed" is (as it's supposed to). Because of this breaking should be possible:
How do I break the loop, so I can display an error dialog from within group.notify
?