Вжух, и кольцо платит: как работает бесконтактная оплата умным кольцом Сбер


Салют, Хабр!
Когда мы разработали умное кольцо Сбер и рассказали о нём на Хабре (и не только), комментаторы регулярно спрашивали:
— А платить им можно? Почему нет?!
Докладываем: уже можно — теперь это первое в России умное кольцо, которое отслеживает показатели организма и при этом обладает функцией бесконтактной оплаты по bluetooth. Меня зовут Сергей, я главный инженер по разработке; расскажу, как реализовали проект.
Как работает оплата кольцом
Умное кольцо Сбер позволяет владельцу следить за показателями своего здоровья, вовремя замечать проблемы, избавляться от плохих привычек и приобретать хорошие — например, ложиться спать в одно и то же время. Предложение предупредит, если показатели регулярно отклоняются от нормальных, и поможет быстро записаться к врачу через сервис СберЗдоровье. ИИ-консультант ГигаЧат объяснит суть метрик и даст персонализированный совет. Словом, это устройство-помощник для хорошего самочувствия.
При этом для продукта под брендом Сбера логичная функция — это возможность оплачивать им покупки. Кольцо всё время на пальце, а значит, его не нужно «брать с собой», как кошелёк или смартфон. В устройстве есть Bluetooth; в нашем распоряжении есть технология «Вжух», она же бесконтактная технология оплаты по Bluetooth; всё сложилось.
Чтобы подключить оплату, пользователь привязывает к своему устройству счёт Сбера в приложении умного кольца через вызов банковского приложения по API. Затем проходит обучение жесту оплаты: необходимо поднять руку, на которой вы носите кольцо, меткой вверх, быстро и сильно тапнуть по нему дважды, затем в течение 10 секунд поднести руку с устройством к терминалу и подержать там 2-3 секунды — до появления анимации успешной оплаты. Это время нужно для передачи токена на терминал.
Видео с жестом оплаты
Когда функция оплаты подключена, а счёт привязан к кольцу, на устройство загружаются десять токенов с конкретным временем жизни — неделю. После десяти оплат (или через неделю) нужно получить новые токены, для этого синхронизировать кольцо с мобильным приложением.
Списания с кольца отображаются в банковском приложении так же, как если бы владелец кольца платил обычной картой. Мы установили лимит в 30 000 рублей на одну оплату кольцом; при желании пользователь может дополнительно снизить его в приложении.

Самой простой частью реализации оказалась сама процедура обмена данными между кольцом и терминалом. Она устроена как же, как одноимённая оплата смартфоном, а это досконально расписанный процесс. Повозиться пришлось с совершенно другими вещами.
Терминал + кольцо
В обмене данными по Bluetooth всегда есть Central-устройство, которое инициирует соединение, и Peripheral, принимающий запрос. Платёжный терминал выступает в роли Peripheral, то есть принимает входящие попытки установить с ним соединение. Но в том же режиме работает и умное кольцо Сбер; когда владелец устройства запускает на смартфоне приложение, именно апп инициирует контакт.
Просто назначить кольцо Central-устройством мы не могли: постоянно сканируя эфир в поиске приёмника (Peripheral), оно тратило бы много энергии. А кольцо должно как можно дольше сохранять заряд батареи, иначе его будет неудобно использовать 24/7.
В итоге мы переконфигурировали отвечающие за bluetooth модули ОС кольца так, чтобы оно выполняло обе роли. Большую часть времени оно остаётся Peripheral-устройством и ждёт соединения. Как только пользователь выполнил жест оплаты, переходит в режим сканирования эфира и начинает искать по bluetooth ближайший терминал. Фильтр RSSI с опорой на пограничное значение RSSI advertise-пакетов устройства отсекает все терминалы с уровнем сигнала ниже заданного.
Работа кольца в роли Periferal в процессе оплаты уже повлияла на энергопотребление, а дополнительно пришлось:
перевести с частоты 25 Гц на частоту 100 Гц акселерометр в кольце, который позволяет детектировать процесс оплаты;
ввести дополнительные вычисления для детектирования того же жеста — архитектура распознавания жестов устроена так, что алгоритмы активизируются раз в секунду.
Чтобы проверить, насколько каждый из этих факторов увеличил энергопотребление, мы провели ряд экспериментов с отладочной полоской и Power Profiler Kit. Оказалось, даже если совершать оплаты каждый час в течении суток, устройство требует максимум на 10% больше энергии. То есть без оплат кольцом оно будет держать заряд до 7 дней, а с ними — до 6,5 дней. Это по-прежнему хороший показатель.
Движение навстречу оплате
Для оплаты кольцом требовалось ввести некое специальное действие пользователя, которое будет давать устройству сигнал: «Я возле терминала и хочу заплатить за покупку». Иначе бы оно всё время находилось в режиме сканирования эфира и тратило энергию (плюс, конечно, процесс в таком режиме был бы менее защищённым). Нужен был жест, который:
владелец кольца не воспроизводит в обычной жизни;
не помешает устройству выполнять его непосредственные функции — измерять показатели;
достаточно органичен для любой руки, то есть не что-то в духе «прижмите большой палец к запястью той же руки».
Для детекции жеста оплаты используется акселерометр в умном кольце — тот же, что измеряет физическую активность пользователя. Поиск начался с самого простого жеста — короткого прикосновения к кольцу. Немедленно выяснилось, что в среднем человек случайно тапает по украшению на пальце сотни раз в день. Двойные тапы случаются реже, но всё равно исчисляются десятками. Ни то, ни другое не подходит.
По схожим причинам отпала идея предложить пользователям самим придумать жест оплаты и «записать» его в приложении. Слишком велик риск, что они выберут движение, которое регулярно и неосознанно повторяют в обычной жизни.
Сначала мы протестировали плавный поворот ладони из положения вверх в положение вниз. Для него с опорой на данные с акселерометра разработали алгоритм определения поворота на базе метода октетов: восьмых частей в плоскости трёх осей. Но оказалось, что подобный поворот ладони редко происходит случайно... потому что его и специально-то сделать сложно. Участники альфа-теста, несмотря на обучающее видео в приложении и тренировки, воспроизводили жест из положения «полуповёрнутой ладони» или просто слишком быстро. В итоге оплата не срабатывала, а пользователи громко критиковали функцию.
После альфа-тестирований мы нашли финальный жест: двойной тап по кольцу из положения «ладонь вверх». Он отвечает всем требованиям — не мешает кольцу работать, не требует от владельца сверхчеловеческих усилий и почти не нужен в обычной жизни (мы нашли только одно исключение — родители маленьких детей, которым надо натягивать штаны).
Человек прямоходящий
Чтобы быстро оценивать, насколько перспективны варианты движения для оплаты, мы разработали собственные механизмы для проверки жестов. Для начала собрали максимально разнообразный датасет жестов от самых разных людей. Оказалось, механика тапа взрослого мужчины очень сильно отличается от тапа девушки с длинными ногтями, а одна девушка с длинными ногтями — от другой: одна будет касаться кольца ногтем, другая — подушечкой пальца, а встроенный акселерометр оценит это как разные тапы.
Сбор данных акселерометра и оптического датчика уже работал в кольце (это частный случай сбора данных для алгоритмов метрик здоровья). Оставалось визуализировать полученные данные плюс определить фильтры искомых движений, чтобы отличать случайный жест от преднамеренного.
Мы собираем с частотой 100 Гц данные с акселерометра кольца об ускорении по трём осям: x, y, z. Гипотеза гласит, что человек с высокой вероятностью находится на Земле, а значит, модуль его ускорения в большинстве случаев составляет 1g. Нам известно расположение осей акселерометра относительно кольца, а оси Z — относительно пальца, так оно носится в определённом положении (метка внутри расположена со внутренней стороны ладони, чтобы оптические датчики работали корректно). Две другие оси могут инвертироваться; это зависит от того, как надето кольцо. Двойной тап — это по сути два сильных ускорения, которые придаются кольцу за короткий промежуток времени. По нашим наблюдениям тап — это то, что больше 0,4g.

По значениям координат x, y, z вектора ускорения мы дополнительно определяем положение руки и, значит, кольца в пространстве, чтобы минимизировать количество ложных двойных тапов. Жест засчитывается, только если во время него рука была в целевом положении: параллельно поверхности земли, ладонью вверх.
Отдельную сложность представлял большой палец: в силу его анатомических особенностей значения координат целевого положения будут отличаться от обычных. В приложение мы добавили вопрос к пользователю, на каком пальце тот носит кольцо, а в программное обеспечение — соответствующие характеристики: большой палец или нет? Правая или левая рука? Дело в том, что для левого и правого больших пальцев нужны разные координатные допущения (попробуйте поднять правую руку ладонью вверх горизонтально полу так, чтобы большой палец смотрел вправо, а потом сделать так же, но для левой руки).
На тысячах наборов данных мы выработали граничные правила, по которым жест вычисляется жест оплаты: положение в пространстве «ладонь вверх» и два коротких сильных ускорения. Если событие произошло, начинаем искать терминал. Находим? Ну это точно оплата. Вжух!
Впихнуть невпихуемое
В предыдущей статье о кольце мы рассказывали, что при разработке софта регулярно упирались в ограничение объёма памяти. С тех пор ничего не изменилось. Мы продолжаем жить в парадигме, где на кольце нет свободного места, но каждый раз его приходится находить. Напомним, что память устройства — 1 Мб flash и 256 Кб оперативной памяти процессора (RAM), плюс дополнительная флэшка на 4 Мб для хранения метрик как владельца, так и самого кольца.
Для реализации бесконтактной оплаты по bluetooth пришлось сильно перераспределить память между приложениями, которые живут в кольце. Это позволило выиграть почти 100 Кб под новый режим работы Bluetooth, который даёт кольцу возможность превращаться в Central-устройство.
Одновременно команда оптимизировала код, чтобы сократить нужный для него объём памяти. К примеру, добившись эффективности алгоритма акселерометра, который обсуждался выше, мы начали снижать количество вычислений:
отказались от самых энергоёмких математических операций — квадратных корней и деления;
перешли на 32-разрядные целочисленные типы данных;
применили метод скользящего среднего. Он, к примеру, позволил исключить реакцию на мелкие изменения в движении.
В некоторых местах пришлось пожертвовать понятностью и прозрачностью алгоритма, чтобы сократить количество вычислений и объём необходимой памяти. В итоге сложность алгоритма составляет О(n) по времени и O(1) по памяти.
Из минусов — для получения обновления прошивки потребуется более нестандартное обновление кольца. Напомним, кольцо обновляется по Bluetooth, когда пользователь запускает апп. Обновление для пользователя, когда на кольцо «заезжает» оплата, будет длиться немного дольше.
(Изначально мы заложились на расширение функционала «обновлятора» через флэшку, чтобы они происходили, когда кольцо заряжается. Но переконфигурация BLE-стека под работу в обоих режимах, Peripheral и Central, потребовала много памяти для стандартного кода Zephir OS).
В кольце есть цепочка приложений: стартер-загрузчик, затем небольшое приложение для обновления по BLE и основное приложение кольца. Чтобы на кольцо заехала оплата, нам нужно обновить не только основное приложение, но и наш «обновлятор» — одно из них обрезается, другое перемещается. Так и высвобождаются пресловутые 100 Кб под бесконтактную оплату.
«Вжух» — не первое и не последнее обновление умного кольца Сбер. Мы продолжаем добавлять в устройство новые функции, связанные со здоровьем (в сентябрьском релизе появился шеринг данных с близкими, ещё несколько обновлений будут до конца года). Но бесконтактная оплата выделяется среди новых опций: она использует сам форм-фактор кольца, то есть тот факт, что оно всё время на пальце, чтобы сделать жизнь пользователя проще и комфортнее.
KioskNews shows a cleaned-up reading view extracted from the publisher’s page — the original always lives on their site, not ours.