--- title: Написание клиентских приложений с помощью вебсокетов slug: WebSockets/Writing_WebSocket_client_applications translation_of: Web/API/WebSockets_API/Writing_WebSocket_client_applications ---
{{ draft() }}
Вебсокеты - технология, которя позволяет открыть интерактивную сессию общения между браузером пользователя и сервером. Соединяясь через вебсокеты, веб-приложения могут осуществлять взаимодействие в реальном времени вместо того, чтобы делать запросы к клиенту о входящих/исходящих изменениях.
API вебсокетов доступно в Javascript коде, область видимости которого включает объект DOM {{ domxref("Window") }} или любой объект, реализующий {{ domxref("WorkerUtils") }}; это означает, что вы можете использовать Web Workers.
Чтобы общаться через протокол вебсокетов необходимо создать объект WebSocket
; при его создании автоматически происходит попытка открыть соединение с сервером.
Конструктор WebSocket принимает один обязательный и один необязательный параметр:
WebSocket WebSocket( in DOMString url, in optional DOMString protocols ); WebSocket WebSocket( in DOMString url, in optional DOMString[] protocols );
url
protocols
{{ optional_inline() }}В конструкторе могут возникать следующие исключения:
SECURITY_ERR
Если ошибка случается во время попытки подключения, то в объект WebSocket
сначала посылается простое событие с именем «error» (таким образом, задействуя обработчик onerror
), потом - событие CloseEvent
(таким образом, задействуя обработчик onclose
) чтобы обозначить причину закрытия соединения.
Однако, начиная с версии Firefox 11, типичным является получение в консоль от платформы Mozilla расширенного сообщения об обшибке и кода завершения, как то определено в RFC 6455, Section 7.4 посредством CloseEvent
.
Этот простой пример создает новый WebSocket, подключаемый к серверу ws://www.example.com/socketserver
. В данном примере в конструктор сокета в качестве дополнительного параметра передается пользовательский протокол "protocolOne", хотя эта часть может быть опущена.
var exampleSocket = new WebSocket("ws://www.example.com/socketserver", "protocolOne");
После выполнения функции, exampleSocket
.readyState
будет иметь значение CONNECTING
. readyState
изменится на OPEN
как только соединение станет готовым к передаче данных.
Если нужно открыть соединение, поддерживающее несколько протоколов, можно передать массив протоколов:
var exampleSocket = new WebSocket("ws://www.example.com/socketserver", ["protocolOne", "protocolTwo"]);
Когда соединение установлено (что соответствует, readyState
OPEN
), exampleSocket.protocol
сообщит, какой протокол выбрал сервер.
In the above examples ws
has replaced http
, similarly wss
replaces https
. Establishing a WebSocket relies on the HTTP Upgrade mechanism, so the request for the protocol upgrade is implicit when we address the HTTP server as ws://www.example.com
or wss://www.example.com
.
Однажды открыв соединение, вы можете передавать данные на сервер. Для осуществления этого, вызовите метод send()
объекта WebSocket
для каждого сообщение, которое желаете отправить:
exampleSocket.send("Here's some text that the server is urgently awaiting!");
Вы можете пересылать данные в виде строки, {{ domxref("Blob") }}, так и ArrayBuffer
.
As establishing a connection is asynchronous and prone to failure there is no guarantee that calling the send()
method immediately after creating a WebSocket object will be successful. We can at least be sure that attempting to send data only takes place once a connection is established by defining an onopen
handler to do the work:
exampleSocket.onopen = function (event) { exampleSocket.send("Here's some text that the server is urgently awaiting!"); };
One handy thing you can do is use JSON to send reasonably complex data to the server. For example, a chat program can interact with a server using a protocol implemented using packets of JSON-encapsulated data:
// Send text to all users through the server function sendText() { // Construct a msg object containing the data the server needs to process the message from the chat client. var msg = { type: "message", text: document.getElementById("text").value, id: clientID, date: Date.now() }; // Send the msg object as a JSON-formatted string. exampleSocket.send(JSON.stringify(msg)); // Blank the text input element, ready to receive the next line of text from the user. document.getElementById("text").value = ""; }
WebSockets is an event-driven API; when messages are received, a "message" event is delivered to the onmessage
function. To begin listening for incoming data, you can do something like this:
exampleSocket.onmessage = function (event) { console.log(event.data); }
Let's consider the chat client application first alluded to in {{ anch("Using JSON to transmit objects") }}. There are assorted types of data packets the client might receive, such as:
The code that interprets these incoming messages might look like this:
exampleSocket.onmessage = function(event) { var f = document.getElementById("chatbox").contentDocument; var text = ""; var msg = JSON.parse(event.data); var time = new Date(msg.date); var timeStr = time.toLocaleTimeString(); switch(msg.type) { case "id": clientID = msg.id; setUsername(); break; case "username": text = "<b>User <em>" + msg.name + "</em> signed in at " + timeStr + "</b><br>"; break; case "message": text = "(" + timeStr + ") <b>" + msg.name + "</b>: " + msg.text + "<br>"; break; case "rejectusername": text = "<b>Your username has been set to <em>" + msg.name + "</em> because the name you chose is in use.</b><br>" break; case "userlist": var ul = ""; for (i=0; i < msg.users.length; i++) { ul += msg.users[i] + "<br>"; } document.getElementById("userlistbox").innerHTML = ul; break; } if (text.length) { f.write(text); document.getElementById("chatbox").contentWindow.scrollByPages(1); } };
Here we use JSON.parse()
to convert the JSON object back into the original object, then examine and act upon its contents.
Text received over a WebSocket connection is in UTF-8 format.
Prior to Gecko 9.0 {{ geckoRelease("9.0") }}, certain non-characters in otherwise valid UTF-8 text would cause the connection to be terminated. Now Gecko permits these values.
When you've finished using the WebSocket connection, call the WebSocket method close()
:
exampleSocket.close();
It may be helpful to examine the socket's bufferedAmount
attribute before attempting to close the connection to determine if any data has yet to be transmitted on the network.
WebSockets should not be used in a mixed content environment; that is, you shouldn't open a non-secure WebSocket connection from a page loaded using HTTPS or vice-versa. In fact, some browsers explicitly forbid this, including Firefox 8 and later.
{{ languages ( {"zh-tw": "zh_tw/WebSockets/Writing_WebSocket_client_applications"} ) }}