diff --git a/README.md b/README.md index 62e6e76..c9309db 100644 --- a/README.md +++ b/README.md @@ -18,6 +18,8 @@ * [Serial and Concurrent Tasks](#serial-and-concurrent-tasks) * [GCD Queue Control](#gcd-queue-control) * [Extensive Example](#extensive-example) +* [Callbacks](#callbacks) +* [Callbacks Example](#callbacks-example) * [Credit](#credit) * [License](#license) @@ -293,6 +295,48 @@ queue.run { result in Run the included demo app to see some of these examples above in action. +## Callbacks + +You can register closures to receive status updates on the queue after each task executes. + +```swift +typealias ClosureWithTaskQueueStatus = (TaskQueueStatus) -> Void +``` + +They will receive a status object: + +```swift +struct TaskQueueStatus { + var activeTaskCount: Int + var maximumActiveTaskCount: Int + var queuedTaskCount: Int + var running: Bool +} +``` + +## Callbacks example + +```swift +let queue = TaskQueue() + +// +// Simple sync task, just prints to console +// +queue.tasks += { + print("====== tasks ======") + print("task #1: run") +} + +// +// Simple callback, just prints to console +// +queue.callbacks.append({ (status) in + print("task queue status", status) +}) + + +queue.run() +``` ## Credit diff --git a/Sources/TaskQueue.swift b/Sources/TaskQueue.swift index 93d969c..f90bdcc 100644 --- a/Sources/TaskQueue.swift +++ b/Sources/TaskQueue.swift @@ -14,6 +14,13 @@ import Foundation +public struct TaskQueueStatus { + public var activeTaskCount: Int + public var maximumActiveTaskCount: Int + public var queuedTaskCount: Int + public var running: Bool +} + // MARK: TaskQueue class open class TaskQueue: CustomStringConvertible { @@ -23,12 +30,14 @@ open class TaskQueue: CustomStringConvertible { // public typealias ClosureNoResultNext = () -> Void public typealias ClosureWithResultNext = (Any? , @escaping (Any?) -> Void) -> Void + public typealias ClosureWithTaskQueueStatus = (TaskQueueStatus) -> Void // // tasks and completions storage // open var tasks = [ClosureWithResultNext]() open lazy var completions = [ClosureNoResultNext]() + open var callbacks = [ClosureWithTaskQueueStatus]() // // concurrency @@ -125,6 +134,13 @@ open class TaskQueue: CustomStringConvertible { task!(self.maximumNumberOfActiveTasks > 1 ? nil : result) { nextResult in self.numberOfActiveTasks -= 1 self._runNextTask(nextResult) + self.callbacks.forEach({ (callback) in + callback(TaskQueueStatus(activeTaskCount: self.numberOfActiveTasks, + maximumActiveTaskCount: self.maximumNumberOfActiveTasks, + queuedTaskCount: self.tasks.count, + running: self.running) + ) + }) } }