The Foundation framework provides the Operation
type, which represents a high-level object that encapsulates a portion of work that may be executed on a queue. Not only does the queue coordinate the performance of those operations, but you can also establish dependencies between operations, create cancelable operations, constrain the degree of concurrency employed by the operation queue, etc.
Operation
s become ready to execute when all of its dependencies are finished executing. The isReady
property then changes to true
.
Create a simple non-concurrent Operation
subclass:
class MyOperation: Operation {
init(<parameters>) {
// Do any setup work here
}
override func main() {
// Perform the task
}
}
class MyOperation: NSOperation {
init(<parameters>) {
// Do any setup work here
}
override func main() {
// Perform the task
}
}
Add an operation to an OperationQueue
:
myQueue.addOperation(operation)
This will execute the operation concurrently on the queue.
Manage dependencies on an Operation
.
Dependencies define other Operation
s that must execute on a queue before that Operation
is considered ready to execute.
operation2.addDependency(operation1)
operation2.removeDependency(operation1)
Run an Operation
without a queue:
operation.start()
Dependencies will be ignored. If this is a concurrent operation, the task may still be executed concurrently if its start
method offloads work to background queues.
Concurrent Operations.
If the task that an Operation
is to perform is, itself, asynchronous, (e.g. a URLSession
data task), you should implement the Operation
as a concurrent operation. In this case, your isAsynchronous
implementation should return true
, you'd generally have start
method that performs some setup, then calls its main
method which actually executes the task.
When implementing an asynchronous Operation
begins you must implement isExecuting
, isFinished
methods and KVO. So, when execution starts, isExecuting
property changes to true
. When an Operation
finishes its task, isExecuting
is set to false
, and isFinished
is set to true
. If the operation it is cancelled both isCancelled
and isFinished
change to true
. All of these properties are key-value observable.
Cancel an Operation
.
Calling cancel
simply changes the isCancelled
property to true
. To respond to cancellation from within your own Operation
subclass, you should check the value of isCancelled
at least periodically within main
and respond appropriately.
operation.cancel()