1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
|
---
title: Navigator.sendBeacon()
slug: Web/API/Navigator/sendBeacon
tags:
- API
- Beacon
- sendBeacon
- Маяк
- Производительность
- метод
- сеть
translation_of: Web/API/Navigator/sendBeacon
---
<div>{{APIRef("HTML DOM")}}</div>
<p>Метод <code><strong>navigator.sendBeacon()</strong></code> используется для асинхронной передачи небольшого количества информации поверх {{Glossary("HTTP")}} веб-серверу.</p>
<h2 id="Синтаксис">Синтаксис</h2>
<pre class="syntaxbox">navigator.sendBeacon(<em>url [</em>, <em>data]</em>);
</pre>
<h3 id="Параметры">Параметры</h3>
<dl>
<dt><code>url</code></dt>
<dd>Параметр <code>url</code> устанавливает адрес, на который будут переданы данные параметра <code>data</code>.</dd>
</dl>
<dl>
<dt><code>data</code> {{optional_inline}}</dt>
<dd>Параметр <code>data</code> может содержать объект типа {{domxref("ArrayBufferView")}}, {{domxref("Blob")}}, {{domxref("DOMString")}}, или {{domxref("FormData")}}, который будет передан.</dd>
</dl>
<div class="note">
<p>Использует метод POST при передаче данных</p>
</div>
<h3 id="Возвращаемые_значения">Возвращаемые значения</h3>
<p><code><strong>sendBeacon()</strong></code> возвращает <code>true</code>, если браузер успешно поставил данные <code>data</code> в очередь отправления, в ином случае <code>false</code>.</p>
<h2 id="Описание">Описание</h2>
<p>Метод предназначен, главным образом, для передачи данных аналитики и диагностики на сервер, перед тем как страница будет закрыта. Так как отправление данных до закрытия страницы может привести к не достаточно полному сбору информации. Стандартный асинхронный {{domxref("XMLHttpRequest")}} не подходит для этих целей, потому что большинство браузеров игнорируют его в событии {{event("unload")}}.</p>
<p>Для решения этой проблемы ранее использовали синхронный <code>XMLHttpRequest</code> вызванный в событии <code>unload</code> или {{event("beforeunload")}} с данными для передачи. Синхронный <code>XMLHttpRequest</code> блокирует процесс выгрузки документа и текущая страница закрывается не сразу. Ситуация усугубляется, если пользователь уходит с вашей страницы по ссылке или нажимает кнопку "назад". Новая страница не будет загружена в этой вкладке, пока не выгрузится старая. В глазах пользователя, новая страница выглядит заторможенной, хотя на самом деле, это связанно с текущей, выгружаемой, страницей.</p>
<p>Существуют и другие способы обойти эту проблему. Один из них - создание элемента {{HTMLElement("img")}} и установка атрибута <code>src</code> в событии выгрузки. Это может сработать, потому что большинство браузеров остановят основной процесс, а вместе с ним и выгрузку страницы, до загрузки изображения. Ещё один способ - создать пустой цикл на несколько секунд, таким образом придержав основной поток и дав асинхронному <code>XMLHttpRequest</code> выполниться.</p>
<p>Но, проблема в том, что все эти методы не надёжны и приводят к значительным задержкам отклика интерфейса браузера. Не говоря о том, что всё это - плохой стиль написания кода.</p>
<p>В примере ниже показан код отправления аналитики при помощи синхронного <code>XMLHttpRequest</code> в событии выгрузки страницы. Это решение приведёт к задержке отклика интерфейса браузера. Не используйте это.</p>
<pre class="brush: js">window.addEventListener("unload", logData, false);
function logData() {
var client = new XMLHttpRequest();
client.open("POST", "/log", false); // последний параметр устанавливает синхронный стиль
client.setRequestHeader("Content-Type", "text/plain;charset=UTF-8");
client.send(analyticsData);
}
</pre>
<p>Здесь-то и найдётся применение <code><strong>sendBeacon()</strong></code>. При использовании метода <code>sendBeacon()</code>, данные будут переданы на сервер асинхронно, как только браузер найдёт оптимальный момент для этого. Это не вызовет задержек выгрузки и не повлияет на время загрузки следующей страницы. Решает все проблемы при отправлении аналитики: данные надёжно доставляются, это происходит асинхронно, не влияет на время выгрузки и загрузки страниц. Кроме того, код выглядит проще, чем при использовании прочих ухищрений.</p>
<p>Следующий пример покажет, как сделать отправление аналитики красиво и просто с помощью <code>sendBeacon()</code>.</p>
<pre class="brush: js">window.addEventListener("unload", logData, false);
function logData() {
navigator.sendBeacon("/log", analyticsData);
}
</pre>
<h2 id="Спецификация">Спецификация</h2>
{{Specifications}}
<h2 id="Совместимость_с_браузерами">Совместимость с браузерами</h2>
<p>{{Compat("api.Navigator.sendBeacon")}}</p>
<h2 id="See_also">See also</h2>
<ul>
<li>{{domxref("navigator", "navigator")}}</li>
<li>{{domxref("WorkerNavigator.sendBeacon()")}} (Использование <code>sendBeacon()</code> в workers)</li>
</ul>
|