Перейти к содержимому

Form notifications как работает

  • автор:

Шаблон Microsoft Power Automate

Отправка уведомления при получении ответов Microsoft Forms

By Сообщество Microsoft Power Automate

Отправка push-уведомления при каждом получении ответа в Microsoft Forms.

Работайте меньше, достигайте большего

Объедините свои любимые приложения, чтобы автоматизировать повторяющиеся задачи.

Узнайте, как это работает

Посмотрите короткое видео о Microsoft Power Automate.

Узнайте, как легко создавать потоки любой сложности.

Другие шаблоны

Microsoft Forms Microsoft Forms SharePoint

Запись ответов для формы в SharePoint

By Microsoft Power Automate Community

Microsoft Forms Microsoft Forms Office 365 Outlook

Send an email to responder when response submitted in Microsoft Forms

By Microsoft Flow Community

Microsoft Forms Microsoft Forms Mail SharePoint

Обработка формы с использованием электронной почты и SharePoint

Microsoft Forms Microsoft Forms Утверждения SharePoint Office 365 Users Office 365 Outlook

Отправка ответов формы на утверждение

By Microsoft Power Automate Community

Начало работы

Power Platform

Обзор

Загрузки

Обучение

  • Свяжитесь с нами
  • Торговые знаки
  • Конфиденциальность и файлы cookie
  • Управление файлами cookie
  • Условия использования
  • Условия
  • русский
    • العربية
    • български
    • català
    • čeština
    • dansk
    • Deutsch (Österreich)
    • Deutsch (Schweiz)
    • Deutsch (Deutschland)
    • Ελληνικά
    • English (Australia)
    • English (Canada)
    • English (Cyprus)
    • English (UK)
    • English (Ireland)
    • English (India)
    • English (Malaysia)
    • English (New Zealand)
    • English (Singapore)
    • English (US)
    • English (South Africa)
    • español (España)
    • español (México)
    • eesti (Eesti)
    • euskara (euskara)
    • suomi
    • français (Belgique)
    • français (Canada)
    • français (Suisse)
    • français (France)
    • galego
    • עברית
    • हिन्दी
    • hrvatski
    • magyar
    • Indonesia
    • italiano (Svizzera)
    • italiano (Italia)
    • 日本語
    • 한국어
    • қазақ тілі
    • lietuvių
    • latviešu
    • Melayu
    • norsk bokmål
    • Nederlands (België)
    • Nederlands (Nederland)
    • polski
    • português (Brasil)
    • português (Portugal)
    • română
    • русский
    • slovenčina
    • slovenščina
    • српски (Србија)
    • srpski (Srbija)
    • svenska
    • ไทย
    • Türkçe
    • українська
    • Tiếng Việt
    • 中文(简体)
    • 中文(繁體)

    Web PUSH Notifications быстро и просто

    Добрый день. В этой небольшой заметке я хочу рассказать как быстро и просто настроить push-уведомления на вашем сайте. Эта статья ни в коем случае не претендует на звание исчерпывающего руководства, но, я надеюсь, что она даст точку старта для дальнейшего изучения.

    Информации по этой теме в интернете полно, но она фрагментирована, разбросана по разным ресурсам и перемешена с уведомлениями для мобильных устройств с примерами на Java, C++ и Python. Нас же, как веб-разработчиков, интересует JavaScript. В этой статье я постараюсь саккумулировать всю необходимую и полезную информацию.

    Web PUSH Notifications

    Я думаю, вы уже знаете что такое push-уведомления, но я всё же напишу коротко о главном.

    Пользователь, заходя на сайт, вытягивает (pull) с него данные. Это удобно и безопасно, но с развитием интернет ресурсов, появилась необходимость оперативно доставлять информацию пользователям не дожидаясь пока те сами сделают запрос. Так и появилась технология принудительной доставки (push) данных с сервера клиенту.

    Push-уведомления работают только если у вас на сайте есть HTTPS.
    Без валидного SSL сертификата запустить не получится. Так что если у вас еще нет поддержки HTTPS, то пришло время её сделать. Рекомендую воспользоваться Let’s Encrypt.
    Для запуска на localhost нужно прибегать к хитростям. Я же тестировал скрипты на Github Pages.

    Оглавление

    • Хорошие уведомления
    • Теория
      • Что же происходит на стороне клиента?
      • Сложности на серверной стороне
      • Приступаем к написанию клиента
      • Отправка уведомлений с сервера
      • Проект на GitHub Pages

      Хорошие уведомления

      Сразу хочу оговориться, что push-уведомления не для рекламных рассылок. Отправлять нужно только то, что действительно нужно конкретному пользователю и на что он действительно должен оперативно отреагировать.

      • Отправка уведомления об изменении статуса обращения пользователя в службу техподдержки;
      • Отправка уведомления об изменении статуса заказа;
      • Появление на складе товара, который ждал пользователь;
      • Ответили на комментарий пользователя к статье;
      • Новая задача в багтрекере со статусом Bug или Critical.
      • Новые поступления на склад;
      • Скидки и акции на товары;
      • Новая статья на сайте;
      • Ответили на комментарий пользователя к статье, который он написал год назад.

      Плохие примеры тоже требуют уведомления, но на них не нужно реагировать оперативно. Эти уведомления можно отправить на почту. Вообще, все важные уведомления рекомендуется дублировать на почту, так-как push-уведомления могут не дойти до пользователя по разным, не зависящих от вас, причинам. Также важным фактором является актуальность события. Об этом я еще поговорю чуть позже. Рекомендую к прочтению:

      • Хорошие уведомления по мнению Google
      • Рекламная статья от PushAll

      Вернемся к нашим баранам. Так как же всё это работает? Для начала немного теории.

      Теория

      Среди непосвященных бытует мнение что push-уведомления это простая технология, не требующая для реализации особых ресурсов. В действительности же это целый пул технологий.

      Для начала небольшая схема того как все это работает (анимированная схема):

      Схема взаимодействия в PUSH Notifications

      1. Сервер отдает страницу пользователю;
      2. Клиент подключается к серверу сообщений, регистрируется и получает ID;
      3. Клиент отправляет полученный ID на сервер и сервер привязывает конкретного пользователя к конкретному устройству используя ID устройства;
      4. Сервер отправляет сообщение клиенту через сервер сообщений используя полученный ранее ID.

      К сожалению, мне не удалось выяснить кто и как создает ID устройства и как сервер сообщений привязывается к конкретному устройству. Я использовал сервер сообщений Firebase Cloud Messaging от Google и его библиотеку. К сожалению, я не смог выяснить можно ли его заменить на свой сервер и как это сделать.

      Изначально для отправки сообщений использовали:
      Cloud to Device Messaging

      Потом его заменили на:
      Google Cloud Messaging

      А потом еще раз поменяли на:
      Firebase Cloud Messaging

      Интересно, что дальше.

      Что же происходит на стороне клиента?

      • JavaScript запрашивает у пользователя разрешение на показ уведомлений;
      • Если пользователь одобрил, то подключаемся к серверу сообщений и получаем ID устройства;
      • Отправляем идентификатор на наш сервер, чтобы мы идентифицировали пользователя;
      • Инициализируем JavaScript воркер который будет работать в фоне, получать сообщения от сервера сообщений и показывать их пользователю;
      • Подключаемся к серверу сообщений и ждем новых поступлений.

      Запрос прав на показ уведомлений

      Google рекомендует использовать переключатель для подписки и отписки от уведомлений. Таким образом, инициация процедуры подписки на уведомления исходит от пользователя, а не от сайта.
      Принудительно подписывать на уведомления каждого приходящего пользователя, это плохая практика. Не делайте так.

      Это все выглядит очень сложно, но на сервере все не проще.

      Сложности на серверной стороне

      • Понятно, что идентификатор устройства, присылаемый пользователем, мы сохраняем в базу данных;
      • Идентификатор устройства хорошо бы привязывать к пользователю, чтобы отправлять персонализированные сообщения;
      • Стоит помнить, что пользователь у нас один, а устройств у него может быть несколько, также одним устройством могут пользоваться несколько пользователей;
      • Отправка уведомлений пользователям не самая дешевая операция и поэтому событие, инициирующее отправку уведомления, нужно ставить в очередь на отправку;
      • Только маленькие проекты с малым числом получателей могут позволить себе отправлять уведомления по событию, в течении того-же HTTP запроса;
      • Так у нас появляется система очередей на RabbitMQ, Redis и т.д.;
      • Появляются демоны/воркеры которые разбирают очередь и другие инструменты поддержки очередей;
      • Для увеличения скорости отправки можно распараллелить процесс и разнести его на несколько нод.

      Практика

      Наконец-то, мы перешли к самому главному. Как я уже говорил ранее, в качестве сервера сообщений мы будем использовать Firebase Cloud Messaging, поэтому мы начинаем с регистрации и создания проекта на Firebase.

      • Заходим на сайт;
      • Регистрируемся;
      • Жмём кнопку Create new project или Import Google project, если у вас уже есть проект;
      • При создании указываем название проекта и страну;
      • После создания проекта попадаем на его dashboard;
      • В меню наводим на колесико рядом с Overview и выбираем Project settings;
      • На открывшейся странице переходим во вкладку Cloud Messaging;
      • Нас интересует Server key, который будет использоваться для отправки сообщений с сервера и Sender ID который будет использоваться для получения сообщений на стороне клиента.

      Можно еще покопаться в настройках и поиграться с разделением прав доступа, но, в общем-то, работа с сайтом Firebase закончена.

      Приступаем к написанию клиента

      Начнем с того что создадим Service Worker для получения push-уведомлений.
      Создаем файл firebase-messaging-sw.js с следующим содержимым.

      // firebase-messaging-sw.js importScripts('https://www.gstatic.com/firebasejs/3.6.8/firebase-app.js'); importScripts('https://www.gstatic.com/firebasejs/3.6.8/firebase-messaging.js'); firebase.initializeApp(< messagingSenderId: '' >); const messaging = firebase.messaging();
      • — это Sender ID который мы получили после регистрации в Firebase.

      Файл Service Worker-а должен называться именно firebase-messaging-sw.js и обязательно должен находиться в корне проекта, то есть доступен по адресу https://example.com/firebase-messaging-sw.js. Путь к этому файлу жестко прописан в библиотеке Firebase.

      Написанного кода достаточно для того чтобы показывать уведомления. О дополнительных возможностях поговорим чуть позже. Теперь добавим библиотеку Firebase и скрипт подписки в наш шаблон страницы.

      Добавляем на страницу кнопку для подписки на уведомления

      Подписка на уведомления

      // firebase_subscribe.js firebase.initializeApp(< messagingSenderId: '' >); // браузер поддерживает уведомления // вообще, эту проверку должна делать библиотека Firebase, но она этого не делает if ('Notification' in window) < var messaging = firebase.messaging(); // пользователь уже разрешил получение уведомлений // подписываем на уведомления если ещё не подписали if (Notification.permission === 'granted') < subscribe(); >// по клику, запрашиваем у пользователя разрешение на уведомления // и подписываем его $('#subscribe').on('click', function () < subscribe(); >); > function subscribe() < // запрашиваем разрешение на получение уведомлений messaging.requestPermission() .then(function () < // получаем ID устройства messaging.getToken() .then(function (currentToken) < console.log(currentToken); if (currentToken) < sendTokenToServer(currentToken); >else < console.warn('Не удалось получить токен.'); setTokenSentToServer(false); >>) .catch(function (err) < console.warn('При получении токена произошла ошибка.', err); setTokenSentToServer(false); >); >) .catch(function (err) < console.warn('Не удалось получить разрешение на показ уведомлений.', err); >); > // отправка ID на сервер function sendTokenToServer(currentToken) < if (!isTokenSentToServer(currentToken)) < console.log('Отправка токена на сервер. '); var url = ''; // адрес скрипта на сервере который сохраняет ID устройства $.post(url, < token: currentToken >); setTokenSentToServer(currentToken); > else < console.log('Токен уже отправлен на сервер.'); >> // используем localStorage для отметки того, // что пользователь уже подписался на уведомления function isTokenSentToServer(currentToken) < return window.localStorage.getItem('sentFirebaseMessagingToken') == currentToken; >function setTokenSentToServer(currentToken)

      Вот и все. Это весь код который требуется для получения push-уведомлений.

      Отправка уведомлений с сервера

      В общем виде отправка уведомления выглядит так:

      POST /fcm/send HTTP/1.1 Host: fcm.googleapis.com Authorization: key=YOUR-SERVER-KEY Content-Type: application/json < "notification": < "title": "Ералаш", "body": "Начало в 21:00", "icon": "https://eralash.ru.rsz.io/sites/all/themes/eralash_v5/logo.png?width=40&height=40", "click_action": "http://eralash.ru/" >, "to": "YOUR-TOKEN-ID" >
      • YOUR-SERVER-KEY — это Server key который мы получили при регистрации в Firebase;
      • YOUR-TOKEN-ID — это ID устройства конкретного пользователя.

      Все поля по порядку:

      • notification — параметры уведомления;
      • title — заголовок уведомления. Лимит 30 символов;
      • body — текст уведомление. Лимит 120 символов;
      • icon — иконка уведомления. Есть некоторые стандарты размеров иконок, но я использую 192×192. Иконки меньшего размера плохо смотрятся на мобильных устройствах;
      • click_action — URL адрес страницы на которую перейдет пользователь кликнув по уведомлению;
      • to — ID устройства получателя уведомления;
      • Полный список параметров здесь.

      Уведомление

      Это пример отправки одного уведомления одному получателю. Можно отправить одно уведомление сразу нескольким получателям. Вплоть до 1000 получателей за раз.

      < "notification": < "title": "Ералаш", "body": "Начало в 21:00", "icon": "https://eralash.ru.rsz.io/sites/all/themes/eralash_v5/logo.png?width=192&height=192", "click_action": "http://eralash.ru/" >, "registration_ids": [ "YOUR-TOKEN-ID-1", "YOUR-TOKEN-ID-2" "YOUR-TOKEN-ID-3" ] >

      Пример ответов от сервера сообщений:

      Отправка уведомления в Chrome
      Отправка уведомления в FireFox
      Ошибка отправки уведомления

      Мы не привязаны к какому-то конкретному языку программирования и для простоты примера будем использовать PHP с расширением cURL. Скрипт отправки уведомления нужно запускать из консоли.

      #!/usr/bin/env php $YOUR_TOKEN_ID, 'notification' => [ 'title' => 'Ералаш', 'body' => sprintf('Начало в %s.', date('H:i')), 'icon' => 'https://eralash.ru.rsz.io/sites/all/themes/eralash_v5/logo.png?width=192&height=192', 'click_action' => 'http://eralash.ru/', ], ]; $fields = json_encode($request_body); $request_headers = [ 'Content-Type: application/json', 'Authorization: key=' . $YOUR_API_KEY, ]; $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $url); curl_setopt($ch, CURLOPT_CUSTOMREQUEST, 'POST'); curl_setopt($ch, CURLOPT_HTTPHEADER, $request_headers); curl_setopt($ch, CURLOPT_POSTFIELDS, $fields); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); $response = curl_exec($ch); curl_close($ch); echo $response;

      messaging.onMessage

      Обработчик messaging.onMessage стоит отдельного упоминания, так как он относится как раз к категории подводных камней. В примерах от Firebase я не видел примера использование этого обработчика. О нем мне рассказал FluorescentHallucinogen, за что ему отдельное спасибо, но он не упомянул о некоторых особенностях его использования.

      Что же это за обработчик и как он работает. Из документации мы знаем, что этот обработчик вызывается если мы получаем push-уведомление и находимся в этот момент на странице сайта с которого отправлено уведомление (желающие использовать нативное решение могут посмотреть пример реализации). Эта функциональность очень полезна тем, что мы можем отобразить уведомление на странице сделав красивую модалку или еще что-то. У меня такой необходимости нет, потому я просто отображу стандартное уведомление.

      if ('Notification' in window) < var messaging = firebase.messaging(); messaging.onMessage(function(payload) < console.log('Message received. ', payload); new Notification(payload.notification.title, payload.notification); >); // . > // . 

      Вроде все просто, но есть подводный камень. Дело все в том что на мобильных устройствах запрещено использовать конструктор Notification. И для решения этой проблемы нужно использовать ServiceWorkerRegistration.showNotification() и обработчик в этом случае будет иметь виде:

      // . messaging.onMessage(function(payload) < console.log('Message received. ', payload); // регистрируем пустой ServiceWorker каждый раз navigator.serviceWorker.register('messaging-sw.js'); // запрашиваем права на показ уведомлений если еще не получили их Notification.requestPermission(function(result) < if (result === 'granted') < navigator.serviceWorker.ready.then(function(registration) < // теперь мы можем показать уведомление return registration.showNotification(payload.notification.title, payload.notification); >).catch(function(error) < console.log('ServiceWorker registration failed', error); >); > >); >); // . 

      Теперь уведомления работают и на мобильных устройствах. Казалось бы уже все, но нет. Не смотря на заверения некоторых, ServiceWorker не должен быть пустым. Мы же хотим, что бы по клику пользователь переходил на нужную нам страницу. Для этого нам нужно добавить обработчик клика по уведомлению в ServiceWorker.

      Сохраняем параметры уведомления для доступа свойству click_action в ServiceWorker-е.

      // . navigator.serviceWorker.ready.then(function(registration) < payload.notification.data = payload.notification; // параметры уведомления registration.showNotification(payload.notification.title, payload.notification); >).catch(function(error) < console.log('ServiceWorker registration failed', error); >); // . 

      Обрабатываем клик по уведомлению в ServiceWorker-е.

      // messaging-sw.js self.addEventListener('notificationclick', function(event) < const target = event.notification.data.click_action || '/'; event.notification.close(); // этот код должен проверять список открытых вкладок и переключатся на открытую // вкладку с ссылкой если такая есть, иначе открывает новую вкладку event.waitUntil(clients.matchAll(< type: 'window', includeUncontrolled: true >).then(function(clientList) < // clientList почему-то всегда пуст!? for (var i = 0; i < clientList.length; i++) < var client = clientList[i]; if (client.url == target && 'focus' in client) < return client.focus(); >> // Открываем новое окно return clients.openWindow(target); >)); >);

      TTL и дополнительный контроль над уведомлением

      Важным свойством для уведомления может является время его актуальности. Это зависит от ваших бизнес процессов. По умолчанию время жизни уведомлений 4 недели. Это очень много для уведомлений такого характера. Например, уведомление «Ваша любимая передача начинается через 15 минут» актуально в течении 15 минут. После этого сообщение уже не актуально и показываться не должно. За контроль над временем жизни отвечает свойство time_to_live со значением от 0 до 2419200 секунд. Подробней читать в документации. Сообщение с указанным TTL будет иметь вид:

      < "notification": < "title": "Ералаш", "body": "Начало через 15 минут", "icon": "https://eralash.ru.rsz.io/sites/all/themes/eralash_v5/logo.png?width=192&height=192", "click_action": "http://eralash.ru/" >, "time_to_live": 900, "to": "YOUR-TOKEN-ID" >

      Сообщение вида «Ваша любимая передача начинается через 15 минут» актуально в течении 15 минут, но уже через минуту после отправки оно станет не корректным. Потому что передача начнется не через 15 минут, а уже через 14. Контролировать такие ситуации нужно на стороне клиента.

      Для этого мы поменяем отправляемое с сервера сообщение:

      < "data": < "title": "Ералаш", "time": 1489006800, "icon": "https://eralash.ru.rsz.io/sites/all/themes/eralash_v5/logo.png?width=192&height=192", "click_action": "http://eralash.ru/" >, "time_to_live": 900, "to": "YOUR-TOKEN-ID" >

      Обратите внимание что поле notification поменялось на data . Теперь не будет вызываться обработчик по умолчанию Firebase и нам нужно самостоятельно сделать это. Добавим в конце файла firebase-messaging-sw.js следующие строки:

      // регистрируем свой обработчик уведомлений messaging.setBackgroundMessageHandler(function(payload) < if (typeof payload.data.time != 'undefined') < var time = new Date(payload.data.time * 1000); var now = new Date(); if (time < now) < // истек срок годности уведомления return null; >var diff = Math.round((time.getTime() - now.getTime()) / 1000); // показываем реальное время в уведомлении // будет сгенерировано сообщение вида: "Начало через 14 минут, в 21:00" payload.data.body = 'Начало через ' + Math.round(diff / 60) + ' минут, в ' + time.getHours() + ':' + (time.getMinutes() > 9 ? time.getMinutes() : '0' + time.getMinutes()) ; > // Сохраяем data для получения пареметров в обработчике клика payload.data.data = payload.data; // Показываем уведомление return self.registration.showNotification(payload.data.title, payload.data); >); // свой обработчик клика по уведомлению self.addEventListener('notificationclick', function(event) < // извлекаем адрес перехода из параметров уведомления const target = event.notification.data.click_action || '/'; event.notification.close(); // этот код должен проверять список открытых вкладок и переключатся на открытую // вкладку с ссылкой если такая есть, иначе открывает новую вкладку event.waitUntil(clients.matchAll(< type: 'window', includeUncontrolled: true >).then(function(clientList) < // clientList почему-то всегда пуст!? for (var i = 0; i < clientList.length; i++) < var client = clientList[i]; if (client.url == target && 'focus' in client) < return client.focus(); >> // Открываем новое окно return clients.openWindow(target); >)); >);

      Вот таким незамысловатым образом мы получили полный контроль над уведомлением. Что самое интересное, пользователю мы показываем время уведомления в его часовом поясе. Это актуально для сервисов который работают по всему миру или регионах с широким разбросом часовых поясов как у матушки-России.

      Заключение

      А теперь поговорим о грустном. Не смотря на все прелести технологии, у неё есть ряд недостатков:

      1. Самая главная проблема это, как всегда, поддержка в браузерах. Полноценная поддержка есть в Chrome, Firefox и Opera последних версий. IE, Safari, Opera Mini, UC Browser, Dolphin и прочая братия остаются за бортом. Но зато работает в мобильных версиях браузеров Chrome, Firefox и Opera.
      2. Открытый сайт и работающий Service Worker не гарантируют доставку сообщения. Хотя уведомления могут дойти и при закрытом браузере.

      Библиотека Firebase скрывает в себе много тайн и её исследование могло бы дать ответы на некоторые вопросы, но это уже выходит за рамки этой статьи.

      Поиграться

      Проект на GitHub Pages

      Так как для запуска Service Worker-а нужен HTTPS, то самым простым решением было разместить проект на GitHub Pages, что я и сделал.

      Проект представляет из себя полноценное приложение для отправки и получения уведомлений. Для того что бы получить уведомление надо:

      • Зайти на страницу;
      • Нажать кнопку Register;
      • Браузер запросит разрешение на показ уведомлений;
      • Подтверждаем разрешение;
      • На странице и в консоли браузера будет напечатан ID вашего устройства;
      • Появится кнопка Delete Token для удаления существующего токена и повторной регистрации;
      • Появится форма с параметрами уведомления которое можно отправить нажав на кнопку Send;
      • Меняем параметры по усмотрению и получаем разные уведомления.

      Можно отправить уведомление через любой инструмент для отправки HTTP запросов. Можно использовать сURL, я предпочитаю приложение Postman для Chrome.

      Запрос такой же как и описанный ранее:

      POST /fcm/send HTTP/1.1 Host: fcm.googleapis.com Authorization: key=AAAAaGQ_q2M:APA91bGCEOduj8HM6gP24w2LEnesqM2zkL_qx2PJUSBjjeGSdJhCrDoJf_WbT7wpQZrynHlESAoZ1VHX9Nro6W_tqpJ3Aw-A292SVe_4Ho7tJQCQxSezDCoJsnqXjoaouMYIwr34vZTs Content-Type: application/json < "data": < "title": "Ералаш", "body": "Начало в 21:00", "icon": "https://eralash.ru.rsz.io/sites/all/themes/eralash_v5/logo.png?width=192&height=192", "click_action": "http://eralash.ru/" >, "to": "YOUR-TOKEN-ID" >
      • YOUR-TOKEN-ID — это ID устройства который вы получили на странице приложения.

      Вот и все. Получаем уведомление и радуемся жизни.

      Ссылки

      Спиок ссылок по теме

      • Про PUSH
        • Wikipedia о технологии PUSH
        • Хорошие уведомления по мнению Google
        • Рекламная статья от PushAll
        • Web Push Book
        • Web Push from ServiceWorker
        • Поддержка в браузерах
        • HTTPS на localhost
        • Тестирование SSL сертификата
        • Let’s Encrypt
        • Статья по настройке Let’s Encrypt
        • Подписка на уведомления
        • Стратегия определения состояния для фложка подписки
        • Видео-инструкция по настройке Firebase
        • Notification
        • ServiceWorker
        • Использование Service Worker
        • localStorage
        • Promise
        • Фокусирование на открытом окне по клику на уведомление
        • Руководство
        • Проект из документации
        • Параметры сообщения
        • Список кодов ошибок
        • TTL
        • Размер иконок
        • Приложение Postman для Chrome
        • Quickstart от Firebase
          • Оригинал
          • Мой форк
          • На GitHub Pages
          • Проект
          • Исходники
          • Проект
          • Исходники

          Updated at 2018-06-09

          Обнаружились некоторые «особенности» в работе уведомлений.

          Дубликаты уведомлений

          Ко мне несколько раз обращались с вопросом: «Как исправить дублирующиеся уведомления?»

          Проявляется эта проблема если открыть сайт отправляющий уведомления одновременно в нескольких вкладках. В этом случае Service Worker отправляет уведомление в обе вкладки и в обоих вкладках срабатывает метод messaging.onMessage. Наблюдать эту проблему можно на моем Demo проекте.

          Что бы решить эту проблему, нужно в методе messaging.onMessage знать, что уведомление уже показывалось в другой вкладке. В качестве единого хранилища можно использовать localStorage , а идентифицировать уведомления по хеш сумме уведомления или присваивать уникальный id. Только стоит помнить, что localStorage не резиновый и id уже показанных уведомлений нужно подчищать через некоторое время.

          Могу порекомендовать для этих целей библиотеку pamelafox/lscache.
          Если у вас есть другой метод решения проблемы, напишите в комментариях.

          Картинки в уведомлениях

          Сегодня ко мне обратился пользователь CTterorist, заметивший, что не отображаются картинки (image) в уведомлениях.

          Немножко потестировав, мне удалось разобраться. Не смотря на то, что поле image отправляется в Firebase, вместе с другими параметрами уведомления, но обратно от Firebase поле image не приходит. Решается проблема очень просто. Можно отправлять картунку в поле data , а в обработчике показа уведомления вытягивать картинку из data и вставлять ее на место в уведомление.

          То есть, если вы отправите сообщение в таком виде, то Firebase потеряет картинку.

          < "notification": < "title": "Bubble Nebula", "body": "It's found today at 21:00", "icon": "https://peter-gribanov.github.io/serviceworker/Bubble-Nebula.jpg", "image": "https://peter-gribanov.github.io/serviceworker/Bubble-Nebula_big.jpg", "click_action": "https://www.nasa.gov/feature/goddard/2016/hubble-sees-a-star-inflating-a-giant-bubble" >, "to": "YOUR-TOKEN-ID" >

          Но если передать картинку в data , то она дойдет.

          < "data": < "title": "Bubble Nebula", "body": "It's found today at 21:00", "icon": "https://peter-gribanov.github.io/serviceworker/Bubble-Nebula.jpg", "image": "https://peter-gribanov.github.io/serviceworker/Bubble-Nebula_big.jpg", "click_action": "https://www.nasa.gov/feature/goddard/2016/hubble-sees-a-star-inflating-a-giant-bubble" >, "to": "YOUR-TOKEN-ID" >

          Обработчики показа уведомления такие же как в примерах выше.

          messaging.onMessage(function(payload) < console.log('Message received. ', payload); // регистрируем пустой ServiceWorker каждый раз navigator.serviceWorker.register('firebase-messaging-sw.js'); // запрашиваем права на показ уведомлений если еще не получили их Notification.requestPermission(function(result) < if (result === 'granted') < navigator.serviceWorker.ready.then(function(registration) < // своя логика как в примере с TTL и т.д. // копируем объект data payload.data.data = JSON.parse(JSON.stringify(payload.data)); registration.showNotification(payload.data.title, payload.data); >).catch(function(error) < console.log('ServiceWorker registration failed', error); >); > >); >);

          Аналогично в Service Worker ( firebase-messaging-sw.js )

          messaging.setBackgroundMessageHandler(function(payload) < console.log('Handling background message', payload); // своя логика как в примере с TTL и т.д. // копируем объект data payload.data.data = JSON.parse(JSON.stringify(payload.data)); registration.showNotification(payload.data.title, payload.data); >);

          Saved searches

          Use saved searches to filter your results more quickly

          Cancel Create saved search

          You signed in with another tab or window. Reload to refresh your session. You signed out in another tab or window. Reload to refresh your session. You switched accounts on another tab or window. Reload to refresh your session.

          Ajax feedback form for Joomla! Works everywhere and suits to every Joomla! theme

          License

          Delo-Design/radicalform

          This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

          Switch branches/tags
          Branches Tags
          Could not load branches
          Nothing to show
          Could not load tags
          Nothing to show

          Name already in use

          A tag already exists with the provided branch name. Many Git commands accept both tag and branch names, so creating this branch may cause unexpected behavior. Are you sure you want to create this branch?

          Cancel Create

          • Local
          • Codespaces

          HTTPS GitHub CLI
          Use Git or checkout with SVN using the web URL.
          Work fast with our official CLI. Learn more about the CLI.

          Sign In Required

          Please sign in to use Codespaces.

          Launching GitHub Desktop

          If nothing happens, download GitHub Desktop and try again.

          Launching GitHub Desktop

          If nothing happens, download GitHub Desktop and try again.

          Launching Xcode

          If nothing happens, download Xcode and try again.

          Launching Visual Studio Code

          Your codespace will open once ready.

          There was a problem preparing your codespace, please try again.

          Latest commit

          Git stats

          Files

          Failed to load latest commit information.

          Latest commit message
          Commit time

          README.md

          RadicalForm

          Радикально новый подход к созданию форм обратной связи на основе чистого Javascript

          logoss

          Минимальная версия Joomla 3.7

          Минимальная версия php 5.6

          Поддерживаются браузеры: Internet Explorer 11 и все современные версии браузеров (включая Safari).

          1. Это бесплатный плагин, который таким и останется.
          2. Не требует для своей работы jQuery!
          3. Работает в любом месте сайта, нет никаких ограничений. (актуально для различных конструкторов сайтов, интернет магазинов и т.д.)
          4. Это аякс плагин.
          5. Прекрасно работает во всплывающих окнах. Есть возможность их закрывать после отправки формы.
          6. Можно удобно вставлять цели яндекс метрики в интерфейсе плагина.
          7. Количество форм обратной связи на странице не ограничено! (удобно для лендингов)
          8. Можно отправлять фото и другие файлы (контроль вложений есть).
          9. Полей для отправки вложений может быть несколько.
          10. Корректно работает с кешированием Joomla.
          11. Проверяется CSRF токен.
          12. Есть интеграция с мессенджером телеграм.
          13. Используется встроенная возможность джумлы делать многоязычные формы (для каждого языка свою)
          14. Есть функция логирования отправленных форм
          15. Есть функция выбора адресата для каждой формы
          16. Возможно использовать в качестве кнопки «Заказ в один клик» в интернет магазинах и других продающих страницах
          17. Есть возможность вставки в тему письма любого поля формы
          18. Предусмотрена валидация HTML5 полей формы
          19. Есть возможность изменения поля Reply To
          20. Есть возможность переопределения шаблона отправляемых писем
          21. Корректно работает с полями со множественными значениями (checkbox, select multiple)
          22. Есть интеграция с сервисом Jivosite
          23. Есть возможность расширения за счет своего кода
          24. Есть возможность экспортировать историю отправленных форм в CSV
          25. Есть возможность расширения с помощью плагинов Joomla
          26. Есть возможность загружать файлы на сервер и отправлять файлы в виде ссылок

          Подробнее можно прочитать здесь

          Если есть проблемы со скачиванием с github — резервная ссылка для скачивания:

          A radically new approach to creating feedback forms

          1. This is a free plug-in that will remain so.
          2. You don’t need jQuery for this plugin!
          3. Works anywhere on the site, there are no restrictions. (relevant for various page builder, online stores, etc.)
          4. This is ajax plugin.
          5. Works great in pop-up windows. It is possible to close them after submitting the form.
          6. You can conveniently insert the yandex metrics in the plugin interface.
          7. The number of feedback forms on the page is unlimited! (convenient for landings)
          8. You can send photos and other files (there is control of attachments).
          9. There are several fields for sending attachments.
          10. Correctly works with Joomla caching.
          11. The CSRF token is checked.
          12. There is an integration with the messenger messaging.
          13. Using the built-in ability of Joomla to make multilingual forms (for each language its own)
          14. There is a function of logging sent forms
          15. There is a function for selecting a destination for each form
          16. It is possible to use the «One-Click Order» button in online stores and other selling pages
          17. There is a possibility of inserting in the subject of a letter of any form field
          18. HTML5 validation of form fields is provided
          19. You can change the Reply To field.
          20. There is a possibility to redefine the template of sent messages
          21. Correctly works with fields with multiple values (checkbox, select multiple)
          22. Added integration with the Jivosite service.
          23. You can add your custom code
          24. Export to CSV file
          25. There is a possibility of expansion using Joomla plug-ins
          26. It is possible to upload files to the server and send files as links

          You can read more here

          If there are problems with downloading from github — a backup link for download:

          Вопросы с меткой [android-notification]

          Android Notification – сообщение, которое может быть выведено на экран за пределами обычного пользовательского интерфейса приложения. Используется для уведомления пользователя о разных событиях.

          121 вопрос
          Конкурсные
          Неотвеченные

          • Конкурсные 0
          • Неотвеченные
          • Цитируемые
          • Рейтинг
          • Неотвеченные (мои метки)

          10 показов

          Как сделать actionButton для уведомления которая будет удалять уведомления?

          Всем привет, я делаю приложение заметки, где по назначенному времени приходит уведомление,в уведомлении есть кнопка завершить которая должна закрывать уведомление, уведомления создаются в .

          • android
          • android-notification

          задан 14 окт в 22:17
          39 показов

          Не работает NotificationCompat.Builder

          if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) < NotificationChannel notificationChannel = NotificationManagerCompat.getNotificationChannel("MyID"); .

          задан 13 апр в 18:32
          127 показов

          Почему не работает notification в Android на Kotlin?

          Приложение запускается без ошибок, но при нажатии на кнопку — уведомление не появляется. В настройках телефона по умолчанию — показ уведомлений разрешен class MainActivity : AppCompatActivity() < .

          задан 2 янв в 20:08
          30 показов

          Не отображается Custom Notification

          Если нотификация показана единственной в списке, то пропадает ее вид. Но как только появляется еще одна — сразу отображается как нужно. Как исправить? А вот так отображается если уже есть какие-то .

          задан 13 дек 2022 в 15:21
          27 показов

          Выполнение фоновой задачи по нажатию на уведомление android

          Мне нужно, чтобы впн туннель выключался при нажатии на уведомление. Я нашел такой код, но не понимаю где писать код, выполняющий, собственно, действие. Если писать в notify_intent, он выполняется .

          задан 28 ноя 2022 в 9:14
          69 показов

          Не работают уведомления на Android 8 и выше

          Я пытаюсь вывести самое простое тестовое уведомление в своем андроид приложении, но сталкиваюсь с тем что уведомление просто не выводится. Вот текст метода: public void notification(View view) < .

          задан 9 авг 2022 в 13:54
          40 показов

          Не показывается уведомление на Xiaomi, хотя на avd все работает

          Я пытаюсь сделать плеер на андроид и работаю над уведомлением для него. На виртуальном pixel2 API30 уведомление отображается но на смартфоне xiaomi Redmi 9C c 10 андроидом уведомление не приходит. .

          задан 26 июн 2022 в 14:28

          Android: напоминание посетить приложение после длительного простоя [закрыт]

          Довольно часто во всяких обучающих или игровых приложениях наблюдаю напоминалку (нотификацию) с призывами возобновить пользование. Стало интересно как подобное можно реализовать без сервера к примеру .

          • android
          • android-notification

          задан 23 мая 2022 в 18:28

          Как решить проблему: Attempt to invoke virtual method on a null object reference

          Всем привет. Я тут решил в своё android-приложение календаря добавить уведомления (Notifications) по времени с помощью AlarmManager. Но у меня появилась проблема: при вызове функции notifyUser() по .

          • java
          • android
          • android-notification
          • android-alarm-manager

          задан 9 янв 2022 в 9:13
          153 показа

          Как реализовать уведомление в Android по времени?

          У меня есть приложение с заметками. Я добавил туда уведомления (которые появляются в строке состояния). Для теста я сделал так, чтобы при нажатии на кнопку «Green» приложение не только .

          задан 8 янв 2022 в 8:22
          298 показов

          Не появляется Notification в Android 11 (sdk 30)

          Notification работал отлично, появлялся (sdk 28, android 9). Решила попробовать на эмуляторе под 11 андроид, как следствие уведомления не появляются. private void createNotificationChannel()< .

          задан 5 ноя 2021 в 18:14

          Отправка уведомлений по дням недели

          Нужно, чтобы приложение отправляло уведомление, к примеру, только по понедельникам в определенное время. Для этого лучше использовать AlarmManager или Notification или Push-notification или есть более .

          • android
          • android-notification
          • android-alarm-manager

          задан 29 авг 2021 в 13:44
          76 показов

          Не могу понять, почему не отображаются уведомления моего приложения

          Не могу понять в чем проблема, делал уведомления по видео, у него все работает, у меня нет. Я пытался делать уведомления и по другим видосам, код примерно один и тот же, но уведомления все равно никак .

          задан 20 июл 2021 в 13:29
          59 показов

          Создается два экземпляра NotificationListenerService. Как их можно использовать в DependencyInjection?

          Есть приложение со встроенным сервисом прослушки уведомлений. Т.к я использую prism, мне необходимо регистрировать этот сервис, который наследуется от моего интерфейса INotificationListenerService. .

          задан 3 июн 2021 в 9:14

          Рамки вокруг кастомного уведомления и фоновое изображение

          В кастомном уведомлении отображаются рамки вокруг и если новое уведомление приходит, то мое уведомление по высоте сужается. Как можно исправить эти две ошибки? if (Build.VERSION.SDK_INT > Build.

          • android
          • android-notification

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *