WebSockets на iOS - PullRequest
       6

WebSockets на iOS

18 голосов
/ 07 апреля 2011

Я читал, что WebSockets работает на iOS 4.2 и выше.И я могу убедиться, что действительно есть объект WebSocket.Но я не могу найти ни одного работающего примера WebSocket, который работает на телефоне.

Например, http://yaws.hyber.org/websockets_example.yaws приведет к сбою приложения Mobile Safari.У кого-нибудь успешно работали WebSockets на телефоне?

Ответы [ 6 ]

11 голосов
/ 07 апреля 2011

Возможно, я нашел решение. Mobile Safari падает только с веб-сокетами, если вы настроили прокси через Wi-Fi.

6 голосов
/ 02 мая 2012

Поддерживается, но имейте ввиду, что стандарт, который реализует браузер iOS Safari, это не RFC 6455, а HyBi-00 / Hixie-76.

Вы также можете проверить с помощью этого браузера: http://websocketstest.com/

Также проверьте этот великий пост, который имеет большую часть информации относительно версий: https://stackoverflow.com/a/2700609/1312722


OBS! , это старый ответ. Я проверил через веб-страницу, упомянутую в этом посте, в сочетании с browserstack.com:

  • iPhone4S
  • iPhone5
  • iPhone5S
  • iPhone6 ​​
  • iPhone6 ​​Plus
  • iPhone6S
  • iPhone6S Plus

Все с использованием RFC 6455

3 голосов
/ 04 июня 2012

У меня была похожая проблема, и я даже заглянул в этот пост, чтобы найти решение этой проблемы. Для меня это никак не связано с подключением к Wi-Fi. Кажется, это ошибка в реализации веб-сокетов в iOS (даже до текущей версии 5.1). Включив кучу отладок XCode, я обнаружил, что это как-то связано с управлением памятью, потому что я получал бы что-то вроде «сообщения, отправленного на освобожденный экземпляр». Скорее всего, был объект, который не имел правильного количества ссылок и был очищен слишком рано.

Этот блог содержит много полезной информации о симптомах проблемы и способах ее устранения, но не имеет обходного пути: http://dalelane.co.uk/blog/?p=1652

В конце концов, однако, я нашел этот обходной путь, и мое приложение теперь почти полностью перестало падать.

me = this // strange javascript convention
this.socket = new WebSocket(url);
// put onmessage function in setTimeout to get around ios websocket crash
this.socket.onmessage = function(evt) { setTimeout(function() {me.onMessageHandler(evt);}, 0); };
2 голосов
/ 31 января 2013

Я заставил их работать на Chrome и Safari, iPhone и iPad (и на других мобильных устройствах тоже, но, думаю, вы не против их). Вот код Javascript, который я использую:

<script language="javascript" type="text/javascript">

    var wsUri = document.URL.replace("http", "ws");
    var output;
    var websocket;


    function init()
    {
        output = document.getElementById("output");
        wsConnect();
    }

    function wsConnect()
    {
        console.log("Trying connection to " + wsUri);
        try
        {
            output = document.getElementById("output");
            websocket = new WebSocket(wsUri);
            websocket.onopen = function(evt)
            {
                    onOpen(evt)
            };
            websocket.onclose = function(evt)
            {
                    onClose(evt)
            };
            websocket.onmessage = function(evt)
            {
                    onMessage(evt)
            };
            websocket.onerror = function(evt)
            {
                    onError(evt)
            };
        }
        catch (e)
        {
            console.log("Exception " + e.toString());
        }
    }


    function onOpen(evt)
    {
        alert("Connected to " + wsUri);
    }

    function onClose(evt)
    {
        alert("Disconnected");
    }

    function onMessage(evt)
    {
        alert('Received message : ' + evt.data);
    }

    function onError(evt)
    {
        alert("Error : " + evt.toString());
    }

    function doSend(message)
    {
        websocket.send(message);
    }

    window.addEventListener("load", init, false);

Отправка данных с клиента на сервер осуществляется с помощью функции doSend (). Получение данных с сервера также работает, я тестировал их с пользовательского сервера C ++.

1 голос
/ 14 декабря 2016

Я отлаживал похожую проблему и обнаружил, что если вы использовали https для получения веб-страницы, iOS будет перехватывать, если вы используете передачу протокола "ws:" в WebSocket.Если вы используете "wss:", все будет работать и ловушек не будет.

1 голос
/ 10 мая 2016

Вот рабочий пример

Клиент веб-сокета

<!DOCTYPE html>
<meta charset="utf-8" />
<head>
<title>WebSocket Test</title>
<script language="javascript" type="text/javascript">

    var websocket;

function OpenWebSocket()
{

   try {
       websocket = new WebSocket(document.getElementById("wsURL").value);
       websocket.onopen = function(evt) { onOpen(evt) };
       websocket.onclose = function(evt) { onClose(evt) };
       websocket.onmessage = function(evt) { onMessage(evt) };
       websocket.onerror = function(evt) { onError(evt) };
   }
   catch(err) {
       writeToScreen(err.message);
   }
}

function CloseWebSocket()
{
     websocket.close();
}

function FindWebSocketStatus()
{
     try {
         if (websocket.readyState == 1){
          writeToScreen("Websocket connection is in open state")
         }
         else if (websocket.readyState == 0){
             writeToScreen("Websocket connection is in connecting state")
         }
         else{
          writeToScreen("Websocket connection is in close state")
         }
     }
     catch(err) {
         writeToScreen(err.message);
     }
}

function FindWebSocketBufferedAmount(){
    try {
            writeToScreen(websocket.bufferedAmount)
    }
    catch(err) {
        writeToScreen(err.message);
    }
}

function SendMessageThroughSocket(){
    doSend(document.getElementById("wsMessage").value);
}

function onOpen(evt)
{
    writeToScreen("Socket Connection Opened");
}

function onClose(evt)
{
    writeToScreen("Socket Connection Closed");
}

function onMessage(evt)
{
    writeToScreen('<span style="color: blue;">SERVER RESPONSE: ' + evt.data+'</span>');
}

function onError(evt)
{
    writeToScreen('<span style="color: red;">ERROR:</span> ' + evt.data);
}

function doSend(message)
{
    try{
    writeToScreen("CLIENT SENT: " + message);
    websocket.send(message);
    }
    catch(err) {
        writeToScreen(err.message);
    }
}

function writeToScreen(message)
{
    var output = document.getElementById("output");
    var pre = document.createElement("p");
    pre.style.wordWrap = "break-word";
    pre.innerHTML = message;
    output.appendChild(pre);
}
</script>
</title>
</head>
<body>
    <table>
        <tr>
            <td>
                WebSocket URL
            </td>
            <td>
                <input type="text" id="wsURL" value="ws://echo.websocket.org/"/>
            </td>
        </tr>
        <tr>
            <td>
                WebSocket Message
            </td>
            <td>
                <input type="text" id="wsMessage" value="Hi"/>
            </td>
        </tr>
        <tr>
            <td colspan="2" style="text-align:left;">
                <input type="button" value="Open Socket Connection" onclick="OpenWebSocket();"/>
            </td>
        </tr>
        <tr>
            <td colspan="2" style="text-align:left;">
                 <input type="button" value="Send Message" onclick="SendMessageThroughSocket();"/>
            </td>
        </tr>
        <tr>
          <td colspan="2" style="text-align:left;">
              <input type="button" value="Close Socket Connection" onclick="CloseWebSocket();"/>
          </td>
         </tr>
        <tr>
            <td colspan="2" style="text-align:left;">
                <input type="button" value="Find Socket Status" onclick="FindWebSocketStatus();"/>
            </td>
        </tr>
        <tr>
            <td colspan="2" style="text-align:left;">
                <input type="button" value="Find Socket Buffered Amount" onclick="FindWebSocketBufferedAmount();"/>
            </td>
        </tr>
    </table>

<div id="output"></div>
</body>
</html>

Сервер веб-сокетов

Создать собственный сервер сокетов также просто. Просто установите узел .js и socket.io , затем перейдите к установке веб-сокета через npm

#!/usr/bin/env node
var WebSocketServer = require('websocket').server;
var http = require('http');

var server = http.createServer(function(request, response) {
                               console.log((new Date()) + ' Received request for ' + request.url);
                               response.writeHead(404);
                               response.end();
                               });
server.listen(8888, function() {
              console.log((new Date()) + ' Server is listening on port 8888');
              });

wsServer = new WebSocketServer({
                               httpServer: server,
                               // You should not use autoAcceptConnections for production
                               // applications, as it defeats all standard cross-origin protection
                               // facilities built into the protocol and the browser.  You should
                               // *always* verify the connection's origin and decide whether or not
                               // to accept it.
                               autoAcceptConnections: false
                               });

function originIsAllowed(origin) {
    // put logic here to detect whether the specified origin is allowed.
    return true;
}

wsServer.on('request', function(request) {
            if (!originIsAllowed(request.origin)) {
            // Make sure we only accept requests from an allowed origin
            request.reject();
            console.log((new Date()) + ' Connection from origin ' + request.origin + ' rejected.');
            return;
            }

            var connection = request.accept();
            console.log((new Date()) + ' Connection accepted.');
            connection.on('message', function(message) {
                          if (message.type === 'utf8') {
                          console.log('Received Message: ' + message.utf8Data);
                          connection.sendUTF('Message received at server:'+message.utf8Data);
                          }
                          else if (message.type === 'binary') {
                          console.log('Received Binary Message of ' + message.binaryData.length + ' bytes');
                          connection.sendBytes(message.binaryData);
                          }
                          });
            connection.on('close', function(reasonCode, description) {
                          console.log((new Date()) + ' Peer ' + connection.remoteAddress + ' disconnected.');
                          });
            });

NodeJS folder in finder

сохраните вышеуказанный файл как .js и запустите его как узел filename.js из терминала или командной строки

NodeJS

Приведенный выше файл выглядит так, как будто мы сначала создали http-сервер с использованием узла, затем передаем созданный экземпляр http-сервера в Websocketserver, а затем в экземпляр Socket.iO

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...