Хабрахабр

Вариант работы с вебсокетами в iOS на языке Swift / Написал менеджер для работы с websocket

Всем привет.

4 года назад я уже разбирался с вебсокетами в iOS, тогда я решил задачу с помощью одной из библиотек cocoapods, статья есть на Хабре. А сегодня хочу продемонстрировать еще одно решение, нативное без cocoapods.

Я написал свой менеджер для работы с вебсокетами (Менеджер в данном случае синглтон класс который может быть вызван в любом месте приложения, так как это синглтон его экземпляр будет создан только один раз для всего приложения).

Воспользуюсь я для своих целей нативными средствами.

import Foundation class WSManager { public static let shared = WSManager() // создаем Синглтон private init(){} private var dataArray = [МОДЕЛЬ_МОИХ_ДАННЫХ]() let webSocketTask = URLSession(configuration: .default).webSocketTask(with: URL(string: "wss://ТУТ_ВАШ_АДРЕС"*)) //функция вызова подключения public func connectToWebSocket() { webSocketTask.resume() self.receiveData() { _ in } } //функция подписки на что либо public func subscribeBtcUsd() { let message = URLSessionWebSocketTask.Message.string("SUBSCRIBE: НА_ЧТО_ПОДПИСЫВАЕМСЯ") webSocketTask.send(message) { error in if let error = error { print("WebSocket couldn’t send message because: \(error)") } } } //функция отписки от чего либо public func unSubscribeBtcUsd() { let message = URLSessionWebSocketTask.Message.string("UNSUBSCRIBE: ОТ_ЧЕГО_ОТПИСЫВАЕМСЯ ") webSocketTask.send(message) { error in if let error = error { print("WebSocket couldn’t send message because: \(error)") } } } //функция получения данных, с эскейпингом чтобы получить данные наружу func receiveData(completion: @escaping ([МОДЕЛЬ_МОИХ_ДАННЫХ]?) -> Void) { webSocketTask.receive { result in switch result { case .failure(let error): print("Error in receiving message: \(error)") case .success(let message): switch message { case .string(let text): let data: Data? = text.data(using: .utf8) let srvData = try? CODABLE_МОДЕЛЬ_ТОГО_ЧТО_ДОЛЖНО_ПРИЙТИ.decode(from: data ?? Data()) for singleData in srvData ?? [] { self.dataArray.append(МОДЕЛЬ_МОИХ_ДАННЫХ(параметр1: singleData.parametr1, параметр2: singleData.parametr2, параметр3: singleData.parametr3)) } case .data(let data):// В вашем варианте данные могут приходить сразу сюда print("Received data: \(data)") @unknown default: debugPrint("Unknown message") } self.receiveData() {_ in } // рекурсия } } completion(self.dataArray) // отправляем в комплишн то что насобирали в нашу модель }}

Вот такой менеджер получился, пример вызова

import UIKit class MainViewController: UIViewController { private var dataArray = [МОДЕЛЬ_МОИХ_ДАННЫХ]() override func viewDidLoad() { super.viewDidLoad() WSManager.shared.connectToWebSocket() // подключаемся WSManager.shared.subscribeBtcUsd() //подписываемся на получение данных self.getData() //получаем данные } private func getData() { //получаем данные WSManager.shared.receiveData() { [weak self] (data) in guard let self = self else { return } guard let data = data else { return } self.dataArray = data // кладем данные в переменную и дальше можно делать с ними то что требуется } } }

*по поводу адреса
wss:// это аналог https://
ws:// это аналог http://

Вот такой вариант работы с вебсокетом получился, если есть вопросы, пожелания, поучения как сделать лучше, пишите, буду рад 🙂

Тестовый пример доступен у меня в гитхабе

Также я использую extension для Decodable который доступен тоже у меня в гитхабе
я про вот эту часть

let srvData = try? CODABLE_МОДЕЛЬ_ТОГО_ЧТО_ДОЛЖНО_ПРИЙТИ.decode(from: data ?? Data())
Теги
Показать больше

Похожие статьи

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *

Кнопка «Наверх»
Закрыть