Для подключения по websocket мы будем использовать SocketIOClientSwift
Скачать можно тут.
Установка там тоже в принципе описывается, но для тех кто совсем в танке расскажу, что есть простой способ, просто добавьте файлы из папки source в свой проект.
В нашем примере мы будем получать тикеты из системы технической поддержки которая работает на node.js
Создаем массив наших тикетов (пока что пустой):
var arrayOfTickets:[String] = []
Можно сделать получение данных по кнопке или при загрузке, в нашем примере при загрузке.
override func viewDidLoad() {
super.viewDidLoad()
let hostUrl = NSURL(string:"http://IP_или_домен:ПОРТ")! //тут указываем адрес подключения
let tokenSDK = "ТОКЕН ЕСЛИ ЕСТЬ" //тут токен если есть
let socket = SocketIOClient(socketURL: hostUrl, options: ["log": false,
"reconnects": true,
"reconnectAttempts": 1,
"reconnectWait": 1,
"connectParams": ["token":tokenSDK]]) // тут задаем параметры передачи данных
socket.on("connect") {data,ack in
let hejka = [""] // тут параметр (если есть)
let paginav = [""] // тут параметр 2 (если есть)
socket.emitWithAck("ВАШЕ_СОБЫТИЕ", "", hejka, paginav)(timeoutAfter: 0) // указываем событие которое генерируем
{data in
let dataTickets = data[1]["result"] as! NSArray // парсим json который пришел
let howMuchTickets = dataTickets.valueForKey("name")
for (var i=0; i < howMuchTickets.count; i++){
let ticketName = dataTickets[i].valueForKey("name") as? String
self.arrayOfTickets.append(ticketName!) // заполняем массив тикетов
}
}
}
socket.connect()
Считаем сколько нам нужно сгенерировать ячеек в таблице:
override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return arrayOfTickets.count
}
Выводим данные (у нас в примере кастомные ячейки, как их сделать не суть моего поста, но если есть вопросы — пишите):
override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
// dequeue the cell from our storyboard
let cell = tableView.dequeueReusableCellWithIdentifier("cell", forIndexPath: indexPath) as! CustomTableViewCell
// if the cell has a text label, set it to the model that is corresponding to the row in array
cell.ticketName?.text = arrayOfTickets[indexPath.row]
// return cell so that Table View knows what to draw in each row
return cell
}
Теперь для самых внимательных, как мы знаем запрос идет асинхронный, и при выполнении это кода, у нас ничего не появится.
Для того чтобы появилось нам нужно вызвать функцию tableview, и сказать ей чтобы перезагрузила данные, то есть добавим одну строку.
override func viewDidLoad() {
super.viewDidLoad()
let hostUrl = NSURL(string:"http://IP_или_домен:ПОРТ")! //тут указываем адрес подключения
let tokenSDK = "ТОКЕН ЕСЛИ ЕСТЬ" //тут токен если есть
let socket = SocketIOClient(socketURL: hostUrl, options: ["log": false,
"reconnects": true,
"reconnectAttempts": 1,
"reconnectWait": 1,
"connectParams": ["token":tokenSDK]]) // тут задаем параметры передачи данных
socket.on("connect") {data,ack in
let hejka = [""] // тут параметр (если есть)
let paginav = [""] // тут параметр 2 (если есть)
socket.emitWithAck("ВАШЕ_СОБЫТИЕ", "", hejka, paginav)(timeoutAfter: 0) // указываем событие которое генерируем
{data in
let dataTickets = data[1]["result"] as! NSArray
let howMuchTickets = dataTickets.valueForKey("name")
for (var i=0; i < howMuchTickets.count; i++){
let ticketName = dataTickets[i].valueForKey("name") as? String
self.arrayOfTickets.append(ticketName!) // // заполняем массив тикетов
self.tableView.reloadData() // ВОТ ЭТА СТРОКА
}
}
}
socket.connect()
Надеюсь гайд будет полезен, если есть вопросы или вы знаете как сделать лучше/быстрее/красивее пишите.
Комментарии (26)
PapaBubaDiop
20.02.2016 23:48+2Зачем
self.tableView.reloadData()
внутри цикла?mlnewton
21.02.2016 00:12-1так работает… что плохого? как лучше было сделать?
PapaBubaDiop
21.02.2016 01:02+1За скобки вынести? Чтоб один раз отработало, а не 500. И можно с анимацией появления, красиво так, вжи-и-и-к.
landan
25.02.2016 19:34Зачем это на хабре? Во первых, на гитхабе того же Socket.IO-Client-Swift есть примеры, во вторых, вы подаете плохой пример для начинающих.
mlnewton
25.02.2016 20:21Не нашел ни одного гайда под swift для начинающих как я, чем плох пример?
landan
25.02.2016 20:58Пример использования socket.io-client https://github.com/socketio/socket.io-client-swift
Примеры с tableView на свифте гуглятся за 5 секунд.
Пример плох тем, что вы просто смешали все в кучу, сокеты, таблицы, парсинг json и тд, так не делается. Если детальнее, то начнем с того, что SocketIOClient имеет специальный enum для опций. Дальше насчет парсинга, напрямую с dictionary и json никто не работает, создайте модели и используйте десериализатор, если нет кастомных вложеных обьектов, то можете использовать стандартный, или что-то более удобнее типа Gloss или EVEReflector.
Ну и self.tableView.reloadData() в цикле — это что-то =)mlnewton
25.02.2016 21:01Вы молодец, что такой умный, но мне например не понятны примеры с гитхаба. И многим судя по вопросам в личке требуется помощь чтобы разобраться. Более того 70% того что Вы написали мне не понятно. Это статья для новичков таких же как я. Просто статья не для Вас, Вы более продвинутый.
landan
25.02.2016 21:08Да вы поймите, ничего личного, все новичками были, но просто статья как мне кажется не уровень хабра, ну гуглится все элемтарно же.
mlnewton
25.02.2016 21:11я не смог нагуглить, и те 5 человек что мне написали тоже, я рад что им помог и тем 52 людям которые добавили в избранное статью, если Вам легче нагуглить, это Ваш выбор.
farcaller
отличный рецепт получить креш, когда ваше
http://
соединение перехватит редиректор провайдера.mlnewton
не очень понял, как лучше делать?
farcaller
as!
обязан убить приложение при несоответствии типа. Тип надо проверять, впрочем как и наличие элемента 1 и словаря с ключем "result" внутри. Всегда проверяйте все что вы получаете из внешних источников.