Customizing Networking Backend

March 5, 2018 ยท View on GitHub

APIKit uses URLSession as networking backend by default. Since Session has abstraction layer of backend called SessionAdapter, you can change the backend of Session like below:

Demo implementation of Alamofire adapter is available here.

SessionAdapter

SessionAdapter provides an interface to get (Data?, URLResponse?, Error?) from URLRequest and returns SessionTask for cancellation.

public protocol SessionAdapter {
    func createTask(with URLRequest: URLRequest, handler: @escaping (Data?, URLResponse?, Error?) -> Void) -> SessionTask
    func getTasks(with handler: @escaping ([SessionTask]) -> Void)
}

public protocol SessionTask: class {
    func resume()
    func cancel()
}

How Session works with SessionAdapter

Session takes an instance of type that conforms SessionAdapter as a parameter of initializer.

open class Session {
    public let adapter: SessionAdapter
    public let callbackQueue: CallbackQueue

    public init(adapter: SessionAdapter, callbackQueue: CallbackQueue = .main) {
        self.adapter = adapter
        self.callbackQueue = callbackQueue
    }

    ...
}

Once it is initialized with a session adapter, it sends URLRequest and receives (Data?, URLResponse?, Error?) via the interfaces which are defined in SessionAdapter.

open func send<Request: APIKit.Request>(_ request: Request, callbackQueue: CallbackQueue? = nil, handler: @escaping (Result<Request.Response, SessionTaskError>) -> Void = { _ in }) -> SessionTask? {
    let urlRequest: URLRequest = ...
    let task = adapter.createTask(with: urlRequest) { data, urlResponse, error in
        ...
    }

    task.resume()

    return task
}