如何使用NSStream连接到主机名具有附加路径的wss套接字?

时间:2017-10-12 01:25:01

标签: ios sockets wss nsstream nsinputstream

我正在尝试连接到wss套接字,主机名如下所示:“myhostname.com/ws/v2”。 以下是我开始连接的方式:

let host = "myhostname.com/ws/v2"

CFStreamCreatePairWithSocketToHost(kCFAllocatorDefault, host as CFString, 443, &readStream, &writeStream)

inputStream = readStream!.takeRetainedValue()
outputStream = writeStream!.takeRetainedValue()

outputStream.setProperty(StreamSocketSecurityLevel.negotiatedSSL, forKey: Stream.PropertyKey.socketSecurityLevelKey)
inputStream.setProperty(StreamSocketSecurityLevel.negotiatedSSL, forKey: Stream.PropertyKey.socketSecurityLevelKey)

inputStream.schedule(in: .current, forMode: .commonModes)
outputStream.schedule(in: .current, forMode: .commonModes)

inputStream.delegate = self
outputStream.delegate = self

inputStream.open()
outputStream.open()

失败并出现错误: The operation couldn’t be completed. (kCFErrorDomainCFNetwork error 1.)

但是,如果我从主机名中删除路径,那么它看起来像这样:myhostname.com然后在我的委托中我得到一个事件openCompleted。但是,之后它没有响应我的消息,我认为这是因为我连接到错误的套接字,因为我删除了路径。

当主机名有附加路径时,连接套接字的正确方法是什么?

1 个答案:

答案 0 :(得分:1)

myhostname.com/ws/v2不是主机名。它是一个(不完整的)URL(完整的URL为wss://myhostname.com/ws/v2)。主机名仅为myhostname.com,该主机上的Websocket路径仅为/ws/v2

WebSockets握手使用HTTP / S,因此仅使用NSStream连接到主机是不够的。您必须将TCP套接字连接到host和端口,然后在使用WSS时协商SSL / TLS握手,然后使用HTTP请求path向WebSocket请求Upgrade,并且只有在返回成功的HTTP 101回复时才执行WebSocket握手。

手动做很多工作。您确实应该使用实际的WebSocket客户端库。有很多可用的。