       default:
         handlersToExecute = []
       }
-      
-      return (result, handlersToExecute)
-    }
-
-    internal func addHandler(_ handler: @escaping ResultHandler) -> (Result<Value, Error>, [ResultHandler])? {
+
+      return PromiseSourceAction(result: result, handlers: handlersToExecute)
+    }
+
+    internal func addHandler(_ handler: @escaping ResultHandler) -> PromiseSourceAction? {
       lock.lock(); defer { lock.unlock() }
 
       switch state {


      case .resolved(let value):
        // Value is already available, call handler immediately
        return (.value(value), [handler])

      case .rejected(let error):
        // Error is already available, call handler immediately
        return (.error(error), [handler])
      }
    }
  }

  typealias ResultHandler = (Result<Value, Error>) -> Void

  internal let dispatchKey: DispatchSpecificKey<Void>
  internal let dispatchMethod: DispatchMethod

  /// The current state of the PromiseSource
  private let internalState: PromiseSourceState
  public var state: State<Value, Error> {
    return internalState.state
  }

  /// Print a warning on deinit of an unresolved PromiseSource
  public var warnUnresolvedDeinit: Bool

  // MARK: Initializers & deinit

  internal convenience init(value: Value) {
    self.init(state: .resolved(value), dispatchKey: DispatchSpecificKey(), dispatchMethod: .unspecified, warnUnresolvedDeinit: false)
  }

  internal convenience init(error: Error) {
    self.init(state: .rejected(error), dispatchKey: DispatchSpecificKey(), dispatchMethod: .unspecified, warnUnresolvedDeinit: false)
  }

  /// Initialize a new Unresolved PromiseSource
  ///
  /// - parameter warnUnresolvedDeinit: Print a warning on deinit of an unresolved PromiseSource
  public convenience init(dispatch dispatchMethod: DispatchMethod = .unspecified, warnUnresolvedDeinit: Bool = true) {
    self.init(state: .unresolved, dispatchKey: DispatchSpecificKey(), dispatchMethod: dispatchMethod, warnUnresolvedDeinit: warnUnresolvedDeinit)
  }

  internal init(state: State<Value, Error>, dispatchKey: DispatchSpecificKey<Void>, dispatchMethod: DispatchMethod, warnUnresolvedDeinit: Bool) {
    self.internalState = PromiseSourceState(state: state)
    self.dispatchKey = dispatchKey
    self.dispatchMethod = dispatchMethod
    self.warnUnresolvedDeinit = warnUnresolvedDeinit

    if case .queue(let queue) = dispatchMethod {
      queue.setSpecific(key: dispatchKey, value: ())
    }
  }

  deinit {
    if warnUnresolvedDeinit {
      switch state {
      case .unresolved:
        print("PromiseSource.deinit: WARNING: Unresolved PromiseSource deallocated, maybe retain this object?")
      default:
        break
      }
    }
  }


  // MARK: Computed properties

  /// Promise related to this PromiseSource
  public var promise: Promise<Value, Error> {
    return Promise(source: self)
  }


  // MARK: Resolve / reject

  /// Resolve an Unresolved PromiseSource with supplied value.
  ///
  /// When called on a PromiseSource that is already Resolved or Rejected, the call is ignored.
  public func resolve(_ value: Value) {
    resolveResult(.value(value))
  }


  /// Reject an Unresolved PromiseSource with supplied error.
  ///
  /// When called on a PromiseSource that is already Resolved or Rejected, the call is ignored.
  public func reject(_ error: Error) {
    resolveResult(.error(error))
  }

  internal func resolveResult(_ result: Result<Value, Error>) {
    let (result, handlersToCall) = internalState.resolve(with: result)
    callHandlers(result, handlers: handlersToCall, dispatchKey: dispatchKey, dispatchMethod: dispatchMethod)
  }

  // MARK: Adding result handlers

  internal func addOrCallResultHandler(_ handler: @escaping (Result<Value, Error>) -> Void) {
    if let (result, handlersToCall) = internalState.addHandler(handler) {
      callHandlers(result, handlers: handlersToCall, dispatchKey: dispatchKey, dispatchMethod: dispatchMethod)
    }
  }
}

internal func callHandlers<T>(_ value: T, handlers: [(T) -> Void], dispatchKey: DispatchSpecificKey<Void>, dispatchMethod: DispatchMethod) {

  for handler in handlers {
    switch dispatchMethod {


*/
public class PromiseSource<Value, Error> {
  internal let dispatchKey: DispatchSpecificKey<Void>
  internal let dispatchMethod: DispatchMethod

  /// The current state of the PromiseSource
  private let internalState: PromiseSourceState
  public var state: State<Value, Error> {
    return internalState.state
  }

  /// Print a warning on deinit of an unresolved PromiseSource
  public var warnUnresolvedDeinit: Bool

  // MARK: Initializers & deinit

  internal convenience init(value: Value) {
    self.init(state: .resolved(value), dispatchKey: DispatchSpecificKey(), dispatchMethod: .unspecified, warnUnresolvedDeinit: false)
  }

  internal convenience init(error: Error) {
    self.init(state: .rejected(error), dispatchKey: DispatchSpecificKey(), dispatchMethod: .unspecified, warnUnresolvedDeinit: false)
  }

  /// Initialize a new Unresolved PromiseSource
  ///
  /// - parameter warnUnresolvedDeinit: Print a warning on deinit of an unresolved PromiseSource
  public convenience init(dispatch dispatchMethod: DispatchMethod = .unspecified, warnUnresolvedDeinit: Bool = true) {
    self.init(state: .unresolved, dispatchKey: DispatchSpecificKey(), dispatchMethod: dispatchMethod, warnUnresolvedDeinit: warnUnresolvedDeinit)
  }

  internal init(state: State<Value, Error>, dispatchKey: DispatchSpecificKey<Void>, dispatchMethod: DispatchMethod, warnUnresolvedDeinit: Bool) {
    self.internalState = PromiseSourceState(state: state)
    self.dispatchKey = dispatchKey
    self.dispatchMethod = dispatchMethod
    self.warnUnresolvedDeinit = warnUnresolvedDeinit

    if case .queue(let queue) = dispatchMethod {
      queue.setSpecific(key: dispatchKey, value: ())
    }
  }

  deinit {
    if warnUnresolvedDeinit {
      switch state {
      case .unresolved:
        print("PromiseSource.deinit: WARNING: Unresolved PromiseSource deallocated, maybe retain this object?")
      default:
        break
      }
    }
  }


  // MARK: Computed properties

  /// Promise related to this PromiseSource
  public var promise: Promise<Value, Error> {
    return Promise(source: self)
  }


  // MARK: Resolve / reject

  /// Resolve an Unresolved PromiseSource with supplied value.
  ///
  /// When called on a PromiseSource that is already Resolved or Rejected, the call is ignored.
  public func resolve(_ value: Value) {
    resolveResult(.value(value))
  }


  /// Reject an Unresolved PromiseSource with supplied error.
  ///
  /// When called on a PromiseSource that is already Resolved or Rejected, the call is ignored.
  public func reject(_ error: Error) {
    resolveResult(.error(error))
  }

  internal func resolveResult(_ result: Result<Value, Error>) {
    let action = internalState.resolve(with: result)
    callHandlers(action.handlers, with: action.result, dispatchKey: dispatchKey, dispatchMethod: dispatchMethod)
  }

  // MARK: Adding result handlers

  internal func addOrCallResultHandler(_ handler: @escaping (Result<Value, Error>) -> Void) {
    if let action = internalState.addHandler(handler) {
      callHandlers(action.handlers, with: action.result, dispatchKey: dispatchKey, dispatchMethod: dispatchMethod)
    }
  }
}

extension PromiseSource {
  typealias ResultHandler = (Result<Value, Error>) -> Void

  fileprivate struct PromiseSourceAction {
    let result: Result<Value, Error>
    let handlers: [ResultHandler]
  }

  fileprivate class PromiseSourceState {
    private let lock = NSLock()
    private(set) var state: State<Value, Error>
    private var handlers: [ResultHandler] = []
