Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Long polling#313

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to ourterms of service andprivacy statement. We’ll occasionally send you account related emails.

Already on GitHub?Sign in to your account

Merged
dolgachio merged 13 commits intojavascript-tutorial:masterfromjeneg:5-10
Feb 21, 2022
Merged
Show file tree
Hide file tree
Changes fromall commits
Commits
Show all changes
13 commits
Select commitHold shift + click to select a range
ef2d2f5
Long polling
jenegFeb 10, 2022
7493e0d
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
c19bd2e
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
b1fbbca
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
baca155
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
b8b4bcf
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
5af7500
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
4be5032
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
e27fdde
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
da20417
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
f16e06b
Update 5-network/10-long-polling/article.md
jenegFeb 21, 2022
8fad01a
Update 5-network/10-long-polling/longpoll.view/browser.js
jenegFeb 21, 2022
1b1169c
Update 5-network/10-long-polling/longpoll.view/server.js
jenegFeb 21, 2022
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
88 changes: 44 additions & 44 deletions5-network/10-long-polling/article.md
View file
Open in desktop
Original file line numberDiff line numberDiff line change
@@ -1,98 +1,98 @@
#Long polling
#Тривале опитування

Long polling is the simplest way of having persistent connection with server, that doesn't use any specific protocol likeWebSocketor Server Side Events.
Тривале опитування (Long polling) -- це найпростіший спосіб реалізувати постійне з’єднання із сервером, без використання спеціального протоколу, такого якWebSocketабо Server Side Events.

Being very easy to implement, it's also good enough in a lot of cases.
Будучи дуже простим у реалізації, він також достатньо хороший у багатьох випадках.

##Regular Polling
##Періодичне опитування

The simplest way to get new information from the server is periodic polling. That is, regular requests to the server: "Hello, I'm here, do you have any information for me?".For example, once every 10seconds.
Найпростіший спосіб отримати нову інформацію з сервера -- періодичне опитування. Тобто регулярні запити до сервера: "Привіт, я тут, у вас є якась інформація для мене?".Наприклад, раз на 10секунд.

In response, the server first takes a notice to itself that the client is online, and second - sends a packet of messages it got till that moment.
У відповідь сервер спочатку помічає собі, що клієнт онлайн, а по-друге -- надсилає пакет повідомлень, які він отримав до цього моменту.

That works, but there are downsides:
1.Messages are passed with a delay up to10seconds (between requests).
2.Even if there are no messages, the server is bombed with requests every10seconds, even if the user switched somewhere else or is asleep. That's quite a load to handle, speaking performance-wise.
Це працює, але є і мінуси:
1.Повідомлення передаються із затримкою до10секунд (між запитами).
2.Навіть якщо повідомлень немає, сервер отримує запити кожні10секунд, навіть якщо користувач перейшов кудись в інше місце або сайт не використовується. З точки зору продуктивності, це може створювати велике навантаження.

So, if we're talking about a very small service, the approach may be viable, but generally, it needs an improvement.
Отже, якщо ми говоримо про невеликий сервіс, підхід може бути життєздатним, але загалом він потребує вдосконалення.

##Long polling
##Тривале опитування

So-called "long polling" is a much better way to poll the server.
Так зване "тривале опитування" (Long polling) -- це набагато кращий спосіб опитування сервера.

It's also very easy to implement, and delivers messages without delays.
Також він дуже простий у реалізації та дозволяє отримувати повідомлення без затримок.

The flow:
Як це працює:

1.A request is sent to the server.
2.The server doesn't close the connection until it has a message to send.
3.When a message appears - the server responds to the request with it.
4.The browser makes a new request immediately.
1.На сервер надсилається запит.
2.Сервер не закриває з’єднання, поки не з’явиться повідомлення для відправки.
3.Коли з’являється повідомлення -- сервер відповідає ним на запит.
4.Браузер негайно робить новий запит.

The situation when the browser sent a request and has a pending connection with the server, is standard for this method. Only when a message is delivered, the connection is reestablished.
Ситуація, коли браузер відправив запит і має відкрите з’єднання з сервером, є стандартною для цього методу. Лише після доставки повідомлення з’єднання із сервером закривається та відкривається нове.

![](long-polling.svg)

If the connection is lost, because of, say, a network error, the browser immediately sends a new request.
Якщо з’єднання втрачено, скажімо, через помилку мережі, браузер негайно надсилає новий запит.

A sketch of client-side`subscribe`function that makes long requests:
Ось ескіз функції`subscribe`на стороні клієнта, яка виконує тривале опитування:

```js
async function subscribe() {
let response = await fetch("/subscribe");

if (response.status == 502) {
//Status 502is a connection timeout error,
//may happen when the connection was pending for too long,
//and the remote server or a proxy closed it
//let's reconnect
//Статус 502-- це помилка тайм-ауту підключення,
//вона може статися, коли з’єднання було відкрито занадто довго,
//і віддалений сервер або проксі-сервер закрили його.
//У цьому випадку повторюємо підключення
await subscribe();
} else if (response.status != 200) {
//An error - let's show it
//У разі помилки -- покажемо її
showMessage(response.statusText);
//Reconnect in one second
//Повторне підключення через одну секунду
await new Promise(resolve => setTimeout(resolve, 1000));
await subscribe();
} else {
//Get and show the message
//Отримуємо та показуємо повідомлення
let message = await response.text();
showMessage(message);
//Callsubscribe() again to get the next message
//Знову викликаємоsubscribe(), щоб отримати наступне повідомлення
await subscribe();
}
}

subscribe();
```

As you can see,`subscribe`function makes a fetch, then waits for the response, handles it and calls itself again.
Як бачите, функція`subscribe`виконує запит, потім чекає на відповідь, обробляє її та знову викликає сама себе.

```warn header="Server should be ok with many pending connections"
The server architecture must be able to work with many pending connections.
```warn header="Сервер має підтримувати багато відкритих з’єднань"
Архітектура сервера повинна вміти працювати з великою кількістю незавершених з’єднаннь.

Certain server architectures run one process per connection, resulting in there being as many processes as there are connections, while each process consumes quite a bit of memory. So, too many connections will just consume it all.
Деякі архітектури серверів запускають один процес на одне з’єднання, в результаті чого процесів стає стільки, скільки є з’єднань, при цьому кожен процес споживає досить багато пам’яті. Таким чином, занадто багато з’єднань просто використають усю память.

That's often the case for backends written in languages likePHPand Ruby.
Це досить часто трапляється з серверами, які використовують мовиPHPі Ruby.

Servers written usingNode.js usually don't have such problems.
Сервери, написані за допомогоюNode.js, зазвичай не мають таких проблем.

That said, it isn't a programming language issue. Most modern languages, including PHPand Ruby allow to implement a proper backend. Just please make sure that your server architecture works fine with many simultaneous connections.
Тим не менш, це не проблема мови програмування. Більшість сучасних мов, включаючи PHPі Ruby, дозволяють реалізувати належну роботу сервера. Просто переконайтеся, що архітектура вашого сервера добре працює з багатьма одночасними з’єднаннями.
```

##Demo: a chat
##Демо: чат

Here's a demo chat, you can also download it and run locally (if you're familiar with Node.jsand can install modules):
Ось демонстраційний чат, який ви також можете завантажити та запустити локально (якщо ви знайомі з Node.jsі вмієте встановлювати модулі):

[codetabs src="longpoll" height=500]

Browser code is in `browser.js`.
Браузерний код знаходиться в `browser.js`.

##Area of usage
##Область використання

Long polling works great in situations when messages are rare.
Тривале опитування чудово працює в ситуаціях, коли повідомлення надходять рідко.

If messages come very often, then the chart of requesting-receiving messages, painted above, becomes saw-like.
Якщо повідомлення надходять дуже часто, то діаграма запиту-отримання повідомлень, намальована вище, стає схожою на пилку.

Every message is a separate request, supplied with headers, authentication overhead, and so on.
Кожне повідомлення є окремим запитом із заголовками, накладними витратами на аутентифікацію тощо.

So, in this case, another method is preferred, such as[Websocket](info:websocket)or [Server Sent Events](info:server-sent-events).
У цьому випадку перевага віддається іншим методам, наприклад[Websocket](info:websocket)або [Server Sent Events](info:server-sent-events).
16 changes: 8 additions & 8 deletions5-network/10-long-polling/longpoll.view/browser.js
View file
Open in desktop
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
//Sending messages, a simplePOST
//Відправляємо повідомлення простимPOST-запитом
function PublishForm(form, url) {

function sendMessage(message) {
Expand All@@ -18,7 +18,7 @@ function PublishForm(form, url) {
};
}

//Receiving messages with long polling
//Отримуємо повідомлення за допомогою тривалого опитування
function SubscribePane(elem, url) {

function showMessage(message) {
Expand All@@ -31,18 +31,18 @@ function SubscribePane(elem, url) {
let response = await fetch(url);

if (response.status == 502) {
//Connection timeout
//happens when the connection was pending for too long
//let's reconnect
//Тайм-аут з’єднання
//відбувається, коли з’єднання було відкрито занадто довго,
//відновлюємо з’єднання
await subscribe();
} else if (response.status != 200) {
//Show Error
//Показуємо помилку
showMessage(response.statusText);
//Reconnect in one second
//Повторне підключення через одну секунду
await new Promise(resolve => setTimeout(resolve, 1000));
await subscribe();
} else {
//Got message
//Отримано повідомлення
let message = await response.text();
showMessage(message);
await subscribe();
Expand Down
6 changes: 3 additions & 3 deletions5-network/10-long-polling/longpoll.view/index.html
View file
Open in desktop
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,18 @@
<!DOCTYPE html>
<script src="browser.js"></script>

All visitors of this page will see messages of each other.
Усі відвідувачі цієї сторінки будуть бачити повідомлення один одного.

<form name="publish">
<input type="text" name="message" />
<input type="submit" value="Send" />
<input type="submit" value="Надіслати" />
</form>

<div id="subscribe">
</div>

<script>
new PublishForm(document.forms.publish, 'publish');
//random url parameter to avoid any caching issues
//випадковий параметр URL-адреси, щоб уникнути проблем із кешуванням
new SubscribePane(document.getElementById('subscribe'), 'subscribe?random=' + Math.random());
</script>
10 changes: 5 additions & 5 deletions5-network/10-long-polling/longpoll.view/server.js
View file
Open in desktop
Original file line numberDiff line numberDiff line change
Expand Up@@ -34,28 +34,28 @@ function publish(message) {
function accept(req, res) {
let urlParsed = url.parse(req.url, true);

//new client wants messages
//новий клієнт хоче отримати повідомлення
if (urlParsed.pathname == '/subscribe') {
onSubscribe(req, res);
return;
}

//sending a message
//надсилаємо повідомлення
if (urlParsed.pathname == '/publish' && req.method == 'POST') {
//accept POST
//приймаємо запит POST
req.setEncoding('utf8');
let message = '';
req.on('data', function(chunk) {
message += chunk;
}).on('end', function() {
publish(message); //publish it to everyone
publish(message); //надсилаємо його для всіх користувачів
res.end("ok");
});

return;
}

//the rest is static
//решта -- статичні файли
fileServer.serve(req, res);

}
Expand Down

[8]ページ先頭

©2009-2025 Movatter.jp