热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

开发笔记:iOS上的WebSocket框架Starscream

篇首语:本文由编程笔记#小编为大家整理,主要介绍了iOS上的WebSocket框架Starscream相关的知识,希望对你有一定的参考价值。

篇首语:本文由编程笔记#小编为大家整理,主要介绍了iOS 上的 WebSocket 框架 Starscream相关的知识,希望对你有一定的参考价值。




原文:WebSockets on iOS with Starscream
作者:Aaron Douglas
译者:kmyhy


传统的网络技术 (也就是 Berkeley sockets) 被认为是可靠和稳定的。但是 Berkeley socket 在某些 web 技术,比如代理和防火墙下不太好使。WebSocket 出现于 2011 年,是一种在客户端和服务端之间建立双向通讯的新技术。WebSocket 比起多个 HTTP 请求来说更有效率并允许长连接。

ios 上使用 WebSocket 并不是那么容易。iOS 和 Mac 库 Starscream 的出现,极大地简化了 WebSocket 的创建和使用。



注:本文假设你熟悉 CocoaPods。如果你不熟悉,请参考我们的 CocoaPods 教程。


在本文中,你将在一个叫做 Emoji Commuicator 的 App 中完成网络编程部分。Emoji Communicator 允许你将当前心情用一个 emoji 字符发布给所有连接到该服务的人。

Emoji Communicator 原来的开发者原本打算用 HTTP 请求获取新消息,但这个功能使用 WebSocket 显然更合适。你将使用 Starscream 来连接后台的 Web 服务器。


开始

首先需要一个 Web 服务器。在本文中,你会在本机上启动一个 web 服务器。这个示例的 web 服务器运行在 Node.js 下,使用一小个 Javascript 文件来支持它。

当然,首先需要安装 Node.js。如果不确定是否已经安装,可以在终端窗口中输入命令:

node --version

如果报错,请按照下列步骤下载和安装 Node.js。否则,你会看到 Node.js 的版本号,你就可以跳过下一节 Node.js 的下载。


安装和下载 Node.js

在 https://nodejs.org/ 下载 Node.js 的最新安装包 (当前 2016.9.22 的最新版本是)。下载完安装包 (例如 node-v6.6.0.pkg),双击进行安装。参考提示进行,选择默认选项就行了。

安装完后,在终端中检查 Node.js 是否工作正常:

node --version

如果你没有看到 6.6.0 (或者你所安装的版本),或者报错,再次检查安装是否正确。


聊天服务器

你将用到一个聊天服务器。从这里下载示例 iOS app 和 Web 服务器代码。解压缩 zip 包到桌面或者某个文件夹。在终端中,切换到该目录,并进入 nodeapp 子目录。

这个程序需要一个第三方模块,需要用 Node.js 的包管理器 npm 来安装。在这个目录中,执行:

npm install websocket

输入下列命令启动聊天服务器:

node chat-server.js

你会看到类似如下输出:

Tue Sep 13 2016 18:54:44 GMT-0500 (CDT) Server is listening on port 1337

然后在浏览器 Safari 或 Chrome 中打开 frontend.html

输入一个昵称,发送一条测试消息。如果要在第二个客户端进行测试,重新打开一个浏览器或标签页,用同一个 Url。用另一个昵称登录,发送一条消息;你会看到消息立即出现在另一个浏览器里。

这充分说明了 WebSocket 的强大之处。每个浏览器都和 web 服务器有一个单独的长连接——没有刷新。当消息到达,服务器会自动向所有连接着的客户端进行广播。返回终端,你可以看到所有的聊天活动:

$ node chat-server.js
Tue Sep 13 2016 18:54:44 GMT-0500 (CDT) Server is listening on port 1337
Tue Sep 13 2016 18:55:19 GMT-0500 (CDT) Connection from origin null.
Tue Sep 13 2016 18:55:19 GMT-0500 (CDT) Connection accepted.
Tue Sep 13 2016 18:55:34 GMT-0500 (CDT) User is known as: Aaron with green color.
Tue Sep 13 2016 18:55:37 GMT-0500 (CDT) Received Message from Aaron: Hello
Tue Sep 13 2016 18:58:49 GMT-0500 (CDT) Connection from origin null.
Tue Sep 13 2016 18:58:49 GMT-0500 (CDT) Connection accepted.
Tue Sep 13 2016 18:58:51 GMT-0500 (CDT) User is known as: James with red color.
Tue Sep 13 2016 18:58:55 GMT-0500 (CDT) Received Message from James: This is pretty slick!
Tue Sep 13 2016 18:59:03 GMT-0500 (CDT) Received Message from James: :]
Tue Sep 13 2016 18:59:27 GMT-0500 (CDT) Peer undefined disconnected.

WebSockets

HTTP 第一次出现是 1991 年,它设计为一种请求/响应式的通讯机制。Web 浏览器用这种机制工作良好,用户请求 web 页,服务器返回内容。但某些时候,需要有新数据时不经过用户请求就通知用户——也就是,服务器推。

HTTP 协议无法很好地解决推模型。在 websocket 出现前,web 服务通过一系列浏览器刷新机制来实现推模型,但效率无法让人满意。

webSocket 实现了服务端推机制。新的 web 浏览器全都支持 WebSocket,这使得它的使用超级简单。通过 WebSocket 能够打开持久连接,大部分网络都能轻松处理 WebSocket 连接。

WebSocket 通常应用在某些数据经常性或频繁改变的场景。例如 Facebook 中的 web 通知、Slack 中的实时聊天、交易系统中的变化的股票价格。

在 iOS 中使用 WebSocket 比较麻烦,你必须进行大量的设置,而且内置的 API 根本帮不上忙。这时 Starscream 出现了——这个小巧、易于使用的库让你所有的烦恼不翼而飞。


Emoji Communicator

打开 EmojiTransmitter.xcodeproj。在模拟器中运行程序,程序很简单,它需要用户输入一个昵称,然后显示一个界面,让用户选择一个 emoji 发送,并显示任何接收到的 emoji。

这个 App 还没有完成网络部分。你将使用 Starscream 来执行所有的 WebSocket 网络请求。

有许多方法可以将 Starscream 集成到你的项目。CocoaPods 和 Carthage 是两种最常见的包管理器。你两种都可以用,但本文将使用 CocoaPods。

首先,关闭打开的项目。开启终端窗口,将目录切换至项目文件夹。在这个项目中已经有一个配置了 Starscream pod 的 Podfile 文件了。你可以直接安装 pod:

pod repo update; pod install

当 CocoaPods 结束安装,在 Xcode 8 中打开 EmojiTransmitter.xcworkspace 文件。运行程序,检查 App 是否能够运行。
打开 ViewController.swift,在 import UIKit 后加入:

import Starscream

然后,在 ViewController 类的 username 属性后增加一个属性:

var socket = WebSocket(url: URL(string: "ws://localhost:1337/")!, protocols: ["chat"])

这是创建 WebSocket 连接的核心。注意 URL 的歌声,协议是 ws 而不是 Http/https。protocols 参数指定为 chat,这取决于服务端的实现,这个协议可以被使用,也可能被忽略。在本 demo 中,忽略它即可。
接着在 viewDidLoad 方法后加入:

deinit {
socket.disconnect(forceTimeout: 0)
socket.delegate = nil
}

当 View Controller 被销毁时,强制关闭 WebSocket 连接。

在 Starscream 中所有的工作都放在 delegate 中进行。Starscream 也支持闭包,如果你不愿意使用委托的话。

在 ViewController.swift,在 fileprivate 扩展后增加一个扩展:

// MARK: - WebSocketDelegate
extension ViewController : WebSocketDelegate {
public func websocketDidConnect(_ socket: Starscream.WebSocket) {
}
public func websocketDidDisconnect(_ socket: Starscream.WebSocket, error: NSError?) {
}
public func websocketDidReceiveMessage(_ socket: Starscream.WebSocket, text: String) {
}
public func websocketDidReceiveData(_ socket: Starscream.WebSocket, data: Data) {
}
}

这 4 个委托方法必须实现,否则代码无法通过编译。

然后,在 viewDidLoad 方法的 super.viewDidLoad() 后面添加:

socket.delegate = self
socket.connect()

运行程序,输入昵称,点击 Next。返回 Node.js 控制台你将看到有一个连接通知。

现在,你已经能够连接到 Node.js App 了,接下来是发送消息到服务器。

首先,将 sendMessage(_:) 方法修改为:

func sendMessage(_ message: String) {
socket.write(string: message)
}

这会发送消息(本例中,就是 emoji)到 Node.js 服务器。

然后,在 websocketDidConnect(_:) 方法中加入:

socket.write(string: username)

这会在连接建立后发送你在第一个界面中输入的昵称。这个服务器会将第一个接收到的消息当做用户名称。
在 websocketDidDisconnect(_:error:) 中加入:

performSegue(withIdentifier: "websocketDisconnected", sender: self)

无论什么原因,只要 socket 被断开,这都会让用户返回到输入昵称界面。如果在你自己的 App 中,你应当在这里进行更健全的错误处理。

接着,在 websocketDidReceiveMessage(_:text:) 方法中:

// 1
guard let data = text.data(using: .utf16),
let jsonData = try? JSONSerialization.jsonObject(with: data),
let jsonDict = jsonData as? [String: Any],
let messageType = jsonDict["type"] as? String else {
return
}
// 2
if messageType == "message",
let messageData = jsonDict["data"] as? [String: Any],
let messageAuthor = messageData["author"] as? String,
let messageText = messageData["text"] as? String {
messageReceived(messageText, senderName: messageAuthor)
}

收到的文字消息是可读的字符串——如果是 JSON,尝试将其转为集合对象。代码解释如下:


  1. 首先将字符串转为 NSData,然后将 NSData 传给 JSONSerialization 对象以将其转为载体并返回一个有效的对象。最后还检查了几个重要的 key,并设置对应的值。如果对象无效,直接通过 guard 语句退出。
  2. 过滤消息的 messageType,然后将数据传递给 messageReceived(messageText:, senderName:) 方法。

下面是一个从 Node.js 收到的 JSON 格式的消息示例:

{
"type": "message",
"data": {
"time": 1472513071731,
"text": ":]",
"author": "iPhone Simulator",
"color": "orange"
}
}

运行 app,每当你发送一条消息,emoji 将会用你选择的 emoji 和昵称刷新。返回 web 控制台,你的 emoji 消息也会显示。

这就是 Starscream 的使用!


结束

在这里下载最终完成的项目。

Emoji Communicator 是一个使用 WebSocket 的最简单的例子。如果你想在已经存在的服务中使用 Starscream,你可以参考更多资料:


  • 参考 Starscream 在 GitHub 上的项目主页 。
  • 参考 Mozilla 开发者网络 上关于 WebSocket 的介绍和如何实现 WebSocket。
  • 如果你需要某些让人昏昏欲睡的东西,请阅读 RFC 6455 ,关于 WebSocket 协议规范。

如果你有任何问题或建议,请在下面留言。



推荐阅读
  • 本文介绍如何使用JavaScript中的for循环来创建一个九九乘法表,适合初学者学习循环结构的应用。 ... [详细]
  • JavaScript 实现图片文件转Base64编码的方法
    本文详细介绍了如何使用JavaScript将用户通过文件输入控件选择的图片文件转换为Base64编码字符串,适用于Web前端开发中图片上传前的预处理。 ... [详细]
  • 本文探讨了利用Java实现WebSocket实时消息推送技术的方法。与传统的轮询、长连接或短连接等方案相比,WebSocket提供了一种更为高效和低延迟的双向通信机制。通过建立持久连接,服务器能够主动向客户端推送数据,从而实现真正的实时消息传递。此外,本文还介绍了WebSocket在实际应用中的优势和应用场景,并提供了详细的实现步骤和技术细节。 ... [详细]
  • MongoDB高可用架构:深入解析Replica Set机制
    MongoDB的高可用架构主要依赖于其Replica Set机制。Replica Set通过多个mongod节点的协同工作,实现了数据的冗余存储和故障自动切换,确保了系统的高可用性和数据的一致性。本文将深入解析Replica Set的工作原理及其在实际应用中的配置和优化方法,帮助读者更好地理解和实施MongoDB的高可用架构。 ... [详细]
  • 基于Node.js的高性能实时消息推送系统通过集成Socket.IO和Express框架,实现了高效的高并发消息转发功能。该系统能够支持大量用户同时在线,并确保消息的实时性和可靠性,适用于需要即时通信的应用场景。 ... [详细]
  • 深入浅出解析HTTP协议的核心功能与应用
    前言——协议是指预先设定的通信规则,确保双方能够按照既定标准进行有效沟通,从而实现准确的信息交换。例如,驯兽师通过拍手使动物坐下,这实际上是一种预设的协议。本文将详细探讨HTTP协议的核心功能及其广泛应用,解析其在现代网络通信中的重要作用。 ... [详细]
  • OBS Studio自动化实践:利用脚本批量生成录制场景
    本文探讨了如何利用OBS Studio进行高效录屏,并通过脚本实现场景的自动生成。适合对自动化办公感兴趣的读者。 ... [详细]
  • Python 伦理黑客技术:深入探讨后门攻击(第三部分)
    在《Python 伦理黑客技术:深入探讨后门攻击(第三部分)》中,作者详细分析了后门攻击中的Socket问题。由于TCP协议基于流,难以确定消息批次的结束点,这给后门攻击的实现带来了挑战。为了解决这一问题,文章提出了一系列有效的技术方案,包括使用特定的分隔符和长度前缀,以确保数据包的准确传输和解析。这些方法不仅提高了攻击的隐蔽性和可靠性,还为安全研究人员提供了宝贵的参考。 ... [详细]
  • 在CentOS 7上部署WebRTC网关Janus
    在CentOS 7上部署WebRTC网关Janus ... [详细]
  • 深入探索Node.js新框架:Nest.js第六篇
    在本文中,我们将深入探讨Node.js的新框架Nest.js,并通过一个完整的示例来展示其强大功能。我们将使用多个装饰器创建一个基本控制器,该控制器提供了多种方法来访问和操作内部数据,涵盖了常见的CRUD操作。此外,我们还将详细介绍Nest.js的核心概念和最佳实践,帮助读者更好地理解和应用这一现代框架。 ... [详细]
  • 本文详细解析了JSONP(JSON with Padding)的跨域机制及其工作原理。JSONP是一种通过动态创建``标签来实现跨域请求的技术,其核心在于利用了浏览器对``标签的宽松同源策略。文章不仅介绍了JSONP的产生背景,还深入探讨了其具体实现过程,包括如何构造请求、服务器端如何响应以及客户端如何处理返回的数据。此外,还分析了JSONP的优势和局限性,帮助读者全面理解这一技术在现代Web开发中的应用。 ... [详细]
  • 针对HTTP协议在数据传输过程中的安全漏洞,HTTPS应运而生,通过加密传输通道来防止信息泄露和篡改。作为一种基于SSL/TLS协议的加密超文本传输协议,HTTPS不仅提升了数据的安全性,还广泛应用于各种敏感信息的传输场景,如网上银行、电子商务和在线支付等。 ... [详细]
  • PyQt5 QTextEdit:深入解析Python中多功能GUI库的应用与实现
    本文详细探讨了 PyQt5 中 QTextEdit 组件在 Python 多功能 GUI 库中的应用与实现。PyQt5 是 Qt 框架的 Python 绑定,提供了超过 620 个类和 6000 个函数及方法,广泛应用于跨平台应用程序开发。QTextEdit 作为其中的重要组件,支持丰富的文本编辑功能,如富文本格式、文本高亮和自定义样式等。PyQt5 的流行性不仅在于其强大的功能,还在于其易用性和灵活性,使其成为开发复杂用户界面的理想选择。 ... [详细]
  • 如何尽量处理TIMEWAIT过多?
    如何尽量处理TIMEWAIT过多?编辑内核文件etcsysctl.conf,加入以下内容:net.ipv4.tcp_syncookies1表示开启SYNCookies。当出现SYN ... [详细]
  • 开源项目_一个国外开源项目描述中有中文“谢谢”,到底发生了什么?
    篇首语:本文由编程笔记#小编为大家整理,主要介绍了一个国外开源项目描述中有中文“谢谢”,到底发生了什么?相关的知识,希望对你有一定的参考价值。 ... [详细]
author-avatar
心跳-很执着
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有