Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save wongzigii/19240a0ac43a352c44b4f007b7c26dc4 to your computer and use it in GitHub Desktop.
Save wongzigii/19240a0ac43a352c44b4f007b7c26dc4 to your computer and use it in GitHub Desktop.

Revisions

  1. @Sorix Sorix revised this gist Jun 3, 2020. 1 changed file with 11 additions and 0 deletions.
    11 changes: 11 additions & 0 deletions AsynchronousOperation.swift
    Original file line number Diff line number Diff line change
    @@ -1,19 +1,24 @@
    // Created by Vasily Ulianov on 09.02.17, updated in 2019.
    // License: MIT

    import Foundation

    /// Subclass of `Operation` that adds support of asynchronous operations.
    /// 1. Call `super.main()` when override `main` method.
    /// 2. When operation is finished or cancelled set `state = .finished` or `finish()`
    open class AsynchronousOperation: Operation {
    public override var isAsynchronous: Bool {
    return true
    }

    public override var isExecuting: Bool {
    return state == .executing
    }

    public override var isFinished: Bool {
    return state == .finished
    }

    public override func start() {
    if self.isCancelled {
    state = .finished
    @@ -22,16 +27,19 @@ open class AsynchronousOperation: Operation {
    main()
    }
    }

    open override func main() {
    if self.isCancelled {
    state = .finished
    } else {
    state = .executing
    }
    }

    public func finish() {
    state = .finished
    }

    // MARK: - State management

    public enum State: String {
    @@ -40,6 +48,7 @@ open class AsynchronousOperation: Operation {
    case finished = "Finished"
    fileprivate var keyPath: String { return "is" + self.rawValue }
    }

    /// Thread-safe computed state value
    public var state: State {
    get {
    @@ -58,7 +67,9 @@ open class AsynchronousOperation: Operation {
    didChangeValue(forKey: oldValue.keyPath)
    }
    }

    private let stateQueue = DispatchQueue(label: "AsynchronousOperation State Queue", attributes: .concurrent)

    /// Non thread-safe state storage, use only with locks
    private var stateStore: State = .ready
    }
  2. @Sorix Sorix revised this gist Jun 3, 2020. 1 changed file with 1 addition and 15 deletions.
    16 changes: 1 addition & 15 deletions AsynchronousOperation.swift
    Original file line number Diff line number Diff line change
    @@ -1,24 +1,19 @@
    // Created by Vasily Ulianov on 09.02.17, updated in 2019.
    // License: MIT

    import Foundation

    /// Subclass of `Operation` that adds support of asynchronous operations.
    /// 1. Call `super.main()` when override `main` method.
    /// 2. When operation is finished or cancelled set `state = .finished` or `finish()`
    open class AsynchronousOperation: Operation {
    public override var isAsynchronous: Bool {
    return true
    }

    public override var isExecuting: Bool {
    return state == .executing
    }

    public override var isFinished: Bool {
    return state == .finished
    }

    public override func start() {
    if self.isCancelled {
    state = .finished
    @@ -27,19 +22,16 @@ open class AsynchronousOperation: Operation {
    main()
    }
    }

    open override func main() {
    if self.isCancelled {
    state = .finished
    } else {
    state = .executing
    }
    }

    public func finish() {
    state = .finished
    }

    // MARK: - State management

    public enum State: String {
    @@ -48,7 +40,6 @@ open class AsynchronousOperation: Operation {
    case finished = "Finished"
    fileprivate var keyPath: String { return "is" + self.rawValue }
    }

    /// Thread-safe computed state value
    public var state: State {
    get {
    @@ -58,21 +49,16 @@ open class AsynchronousOperation: Operation {
    }
    set {
    let oldValue = state

    willChangeValue(forKey: state.keyPath)
    willChangeValue(forKey: newValue.keyPath)

    stateQueue.sync(flags: .barrier) {
    stateStore = newValue
    }

    didChangeValue(forKey: state.keyPath)
    didChangeValue(forKey: oldValue.keyPath)
    }
    }

    private let stateQueue = DispatchQueue(label: "AsynchronousOperation State Queue", attributes: .concurrent)

    /// Non thread-safe state storage, use only with locks
    private var stateStore: State = .ready
    }
    }
  3. @Sorix Sorix revised this gist Nov 15, 2019. 1 changed file with 75 additions and 50 deletions.
    125 changes: 75 additions & 50 deletions AsynchronousOperation.swift
    Original file line number Diff line number Diff line change
    @@ -1,53 +1,78 @@
    //
    // AsynchronousOperation.swift
    //
    // Created by Vasily Ulianov on 09.02.17.
    // Copyright © 2017 Vasily Ulianov. All rights reserved.
    //
    // Created by Vasily Ulianov on 09.02.17, updated in 2019.
    // License: MIT

    import Foundation

    /// Subclass of `Operation` that add support of asynchronous operations.
    /// ## How to use:
    /// 1. Call `super.main()` when override `main` method, call `super.start()` when override `start` method.
    /// 2. When operation is finished or cancelled set `self.state = .finished`
    class AsynchronousOperation: Operation {
    override var isAsynchronous: Bool { return true }
    override var isExecuting: Bool { return state == .executing }
    override var isFinished: Bool { return state == .finished }

    var state = State.ready {
    willSet {
    willChangeValue(forKey: state.keyPath)
    willChangeValue(forKey: newValue.keyPath)
    }
    didSet {
    didChangeValue(forKey: state.keyPath)
    didChangeValue(forKey: oldValue.keyPath)
    }
    }

    enum State: String {
    case ready = "Ready"
    case executing = "Executing"
    case finished = "Finished"
    fileprivate var keyPath: String { return "is" + self.rawValue }
    }

    override func start() {
    if self.isCancelled {
    state = .finished
    } else {
    state = .ready
    main()
    }
    }

    override func main() {
    if self.isCancelled {
    state = .finished
    } else {
    state = .executing
    }
    }
    }
    /// Subclass of `Operation` that adds support of asynchronous operations.
    /// 1. Call `super.main()` when override `main` method.
    /// 2. When operation is finished or cancelled set `state = .finished` or `finish()`
    open class AsynchronousOperation: Operation {
    public override var isAsynchronous: Bool {
    return true
    }

    public override var isExecuting: Bool {
    return state == .executing
    }

    public override var isFinished: Bool {
    return state == .finished
    }

    public override func start() {
    if self.isCancelled {
    state = .finished
    } else {
    state = .ready
    main()
    }
    }

    open override func main() {
    if self.isCancelled {
    state = .finished
    } else {
    state = .executing
    }
    }

    public func finish() {
    state = .finished
    }

    // MARK: - State management

    public enum State: String {
    case ready = "Ready"
    case executing = "Executing"
    case finished = "Finished"
    fileprivate var keyPath: String { return "is" + self.rawValue }
    }

    /// Thread-safe computed state value
    public var state: State {
    get {
    stateQueue.sync {
    return stateStore
    }
    }
    set {
    let oldValue = state

    willChangeValue(forKey: state.keyPath)
    willChangeValue(forKey: newValue.keyPath)

    stateQueue.sync(flags: .barrier) {
    stateStore = newValue
    }

    didChangeValue(forKey: state.keyPath)
    didChangeValue(forKey: oldValue.keyPath)
    }
    }

    private let stateQueue = DispatchQueue(label: "AsynchronousOperation State Queue", attributes: .concurrent)

    /// Non thread-safe state storage, use only with locks
    private var stateStore: State = .ready
    }
  4. @Sorix Sorix revised this gist Mar 14, 2017. 1 changed file with 14 additions and 1 deletion.
    15 changes: 14 additions & 1 deletion AsynchronousOperation.swift
    Original file line number Diff line number Diff line change
    @@ -1,5 +1,16 @@
    //
    // AsynchronousOperation.swift
    //
    // Created by Vasily Ulianov on 09.02.17.
    // Copyright © 2017 Vasily Ulianov. All rights reserved.
    //

    import Foundation

    /// Subclass of `Operation` that add support of asynchronous operations.
    /// ## How to use:
    /// 1. Call `super.main()` when override `main` method, call `super.start()` when override `start` method.
    /// 2. When operation is finished or cancelled set `self.state = .finished`
    class AsynchronousOperation: Operation {
    override var isAsynchronous: Bool { return true }
    override var isExecuting: Bool { return state == .executing }
    @@ -17,7 +28,9 @@ class AsynchronousOperation: Operation {
    }

    enum State: String {
    case ready, executing, finished
    case ready = "Ready"
    case executing = "Executing"
    case finished = "Finished"
    fileprivate var keyPath: String { return "is" + self.rawValue }
    }

  5. @Sorix Sorix created this gist Feb 7, 2017.
    40 changes: 40 additions & 0 deletions AsynchronousOperation.swift
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,40 @@
    import Foundation

    class AsynchronousOperation: Operation {
    override var isAsynchronous: Bool { return true }
    override var isExecuting: Bool { return state == .executing }
    override var isFinished: Bool { return state == .finished }

    var state = State.ready {
    willSet {
    willChangeValue(forKey: state.keyPath)
    willChangeValue(forKey: newValue.keyPath)
    }
    didSet {
    didChangeValue(forKey: state.keyPath)
    didChangeValue(forKey: oldValue.keyPath)
    }
    }

    enum State: String {
    case ready, executing, finished
    fileprivate var keyPath: String { return "is" + self.rawValue }
    }

    override func start() {
    if self.isCancelled {
    state = .finished
    } else {
    state = .ready
    main()
    }
    }

    override func main() {
    if self.isCancelled {
    state = .finished
    } else {
    state = .executing
    }
    }
    }