Интеграция в мобильные приложения Android (v2)
Библиотека Webim Mobile SDK 2.0 предоставляет разработчикам мобильных приложений на платформе Google Android средства для встраивания в эти приложения чата между их пользователями и операторами компании-разработчика на основе технологий, применяющихся в сервисе Webim.
N.B.
Поддерживается с версии Android 4.+ (Android API 15+)
Внимание!
Данная версия SDK устарела. Техническая поддержка клиентов, использующих эту версию SDK, более не осуществляется!
Пример приложения: WebimClient
Нами предлагается пример приложения, написанный на Java с использованием библиотеки Webim Mobile SDK для Android. Это приложение позволяет открыть чат между пользователем телефона и оператором.
Тестовое приложение (код на GitHub)
Скачать тестовое приложение c Google Play
Адрес административного раздела — https://demo.webim.ru. Приложение работает под учётной записью demo
.
Инструкция по добавлению Webim Mobile SDK в проект Android
Чтобы подключить библиотеку Webim Mobile SDK в проект на платформе Google Android, выполните следующие шаги:
-
Подключите проект библиотеки в файле
build.gradle
в разделеdependencies
:2. Добавить необходимые для работы SDKcompile 'com.webim.sdk:webimclientsdkandroid:2.+'
permissions
:uses-permission android:name="android.permission.INTERNET" uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"
-
На экране чата внизу разместите надпись "Предоставлено: webim.ru", где webim.ru подчёркнуто и является кликабельной ссылкой на сайт Webim.
Пример подобного использования см. в тестовом приложении WebimClient.
Структура
Webim Mobile SDK предоставляют простой и удобный интерфейс для работы с сервисом Webim. Она осуществляется через класс WMSession
, который через механизм делегирования оповещает об изменении состояния чата. Для того чтобы начать работать с чатом, необходимо инициализировать объект WMSession
и выставить ему делегата. Делегат будет управлять отображаемыми видами и следить за изменением состояния сессии. Делегат должен следовать интерфейсу WMSessionDelegate
. Кроме выбора делегата необходимо определиться с размещением и учётной записью в сервисе Webim. Объект WMSession
работает только с одним выбранным размещением.
Конструкторы WMSession
выглядят следующим образом:
WMSession(Context context, String serverName, String location, WMSessionDelegate delegate);
WMSession(Context context, String serverName, String location, WMSessionDelegate delegate, WMVisitorExt visitorFields);
serverName
может быть задано в виде имени аккаунта или же полноценной ссылкой на сервер (demo
или https://demo.webim.ru
или кастомный домен https://test.mywebimserver.com
)
Расширенная версия конструктора принимает в себя объект WMVisitorExp
, который описывает характеристики текущего пользователя приложения.
Подробнее о идентификации посетителей можно прочитать по данной ссылке.
Начало работы
Для начала работы чата с сервером необходимо запустить сессию методом:
session.startSession(); *
WMSessionDelegate
вызовется метод, в котором будет содержаться объект, характеризующий сессию (sessionItem
):
void sessionDidReceiveFullUpdate(WMSession session);
При изменении состояния сессии на делегате WMSessionDelegate
вызовется метод
void sessionDidChangeSessionStatus(WMSession session);
enum WMSessionState{WMSessionStateUnknown,WMSessionStateIdle,WMSessionStateIdleAfterChat, WMSessionStateChat, WMSessionStateOfflineMessage; }
Для использования интересно только одно состояние сессии: WMSessionStateOfflineMessage
- выставление состояния сессии в этот флаг означает, что не осталось онлайн операторов и чат будет завершен.
Вызов чата
При первом запуске приложения чат скорее всего не будет инициализирован, то есть session.getChat() == null
или session.hasChat() == false
. В случае его появления (начала диалога со стороны оператора или посетителя) он автоматически добавится в объект сессии (или же удалится после закрытия пользователем и оператором). При повторной инициализации чат уже (ещё) может существовать, если это так, то необходимо отобразить этот чат. Он уже будет содержать сообщения. Объект чата имеет несколько состояний, которые важны для определения необходимости отображать этот чат пользователю.
enum WMChatState {
WMChatStateUnknown,
WMChatStateQueue,
WMChatStateChatting,
WMChatStateClosed,
WMChatStateClosedByVisitor,
WMChatStateClosedByOperator,
WMChatStateInvitation; }
Если чат существует и находится в одном из состояний WMChatStateInvitation
, WMChatStateQueue
, WMChatStateChatting
или WMChatStateClosedByOperator
, то его необходимо отобразить пользователю.
Если на делегате вызывается один из методов об изменении чата, то при изменении состояния на любое другое - чат должен закрыться. Обращения к такому чату (посылка сообщений, закрытие) будут возвращать ошибку.
Перед началом чата необходимо убедиться в наличии операторов онлайн. Это можно узнать, вызвав метод WMSessionOnlineStatus session.getOnlineStatus()
.
enum WMSessionOnlineStatus {
WMSessionOnlineStatusUnknown("unknown"),
WMSessionOnlineStatusOnline("online"),
WMSessionOnlineStatusBusyOnline("busy_online"),
WMSessionOnlineStatusOffline("offline"),
WMSessionOnlineStatusBusyOffline("busy_offline"); }
Если чат не существует, то его можно инициировать методом сессии:
session.startChat();
Если вызов этого метода будет удачным, то на делегате вызовется метод:
void sessionDidStartChat(WMSession session, WMChat chat);
или
sessionDidChangeChatStatus(WMSession session)
Использование чата
Для закрытия чата вызывается метод:
session.closeChat();
Инициированный чат содержит в себе массив сообщений, принадлежащих этому чату. Каждое из сообщений имеет тип, описанный в классе WMMessage
.
Для отправки сообщения от пользователя необходимо вызвать метод у сессии:
public String sendMessage(String message, final OnMessageSendListener listener)
где message
- переменная типа String
с сообщением.
OnMessageSendListener
вызывается сразу после ответа сервера и содержит два метода обратного вызова (callback):
-
оnSuccess(String clientSideId)
— означает успешную отправку -
onFailure(String clientSideId, WMSessionError error)
— сигнализирующий об ошибке во время отправки сообщения.
Также можно отправить в чат файл, вызвав метод:
public String sendFile(InputStream fileData, String name, String mimeType, final OnFileUploadListener listener)
OnFileUploadListener
вызывается сразу после ответа сервера и содержит два метода обратного вызова (callback):
-
оnSuccess(String clientSideId)
— означает успешную отправку -
onFailure(String clientSideId, WMSessionError error)
— сигнализирующий об ошибке во время отправки сообщения.
Опционально оба метода принимают и возвращают clientSideId
по которому можно отслеживать статус доставки сообщения.
Реакцией на успешную доставку сообщения, так же как и на появления системного или операторского сообщения будет вызов на делегате метода:
void sessionDidReceiveMessage(WMSession session, WMMessage message);
Для сообщений типа WMMessageKindFileFromOperator
можно загрузить (открыть в браузере) соответствующий файл по ссылке, хранящейся в поле param
. Для получения ссылки, у объекта WMMessage
есть специальное поле, а также ссылка на параметры фаила (WMFileParams
). Для других типов сообщений эти поля — null
.
Кроме того в объекте WMMessage
содержатся данные об отправителе (пока что актуально только для сообщений оператора). Для получения имени отправителя у обьекта WMMessage
присутствует метод
public String getSenderName() Для получения ID отправителя можно вызвать метод у объекта сообщения:
public String getSenderId()
Для того, что бы получить ссылку на фото профиля отправителя необходимо вызвать статический метод у классса WMSession
, передав туда объект сообщения и строки ServerUrl
из объекта WMSession
:
public static String getSenderAvatarUrl(WMMessage messageItem, String serverUrl)
Также существует способ оценить оператора, вызвав у сессии метод
session.rateOperator(String senderId, WMOperatorRate rate, OnRateOperationListener listener)
где senderId
— значение ID оператора, которое можно получить из отправленного им сообщения (см. выше),
rate - enum
с возможными значениями оценки:
WMOperatorRateOneStar(-2),
WMOperatorRateTwoStars(-1),
WMOperatorRateThreeStars(0),
WMOperatorRateFourStars(1),
WMOperatorRateFiveStars(2);
Пример подобного использования см. в тестовом приложении WebimClient
.
Для отправки файла оператору можно вызвать метод у сессии:
session.sendFile(InputStream imageData, String name, String mimeType, final OnFileUploadListener listener);
Если объект чата инициализирован, то он может содержать ссылку на объект оператора. В случае, если оператор меняется или берёт посетителя в обработку, на делегате WMSessionDelegate
вызывается метод
void sessionDidUpdateOperator(WMSession session, WMOperator chatOperator);
По объекту WMOperator
можно определить имя оператора и путь для загрузки его аватара.
Для отправки статуса набора текста (а также текста для функции "шпион") у объекта сессии необходимо вызвать метод:
session.setComposingMessage(boolean isComposing, String draftMessage)
Метод содержит защиту от частых вызовов и срабатывает с задержкой в 2 секунды при последующем вызове, если ещё не был осуществлён текущий. Не забудьте сбросить флаг после того, как пользователь перестанет вводить текст.
Пример подобного использования см. в тестовом приложении WebimClient.
В случае, если оператор начинает или перестает набирать текст, на делегате WMSessionDelegate
вызывается метод:
void sessionDidChangeOperatorTyping(WMSession session, boolean isTyping);
При необходимости обновить чат, у сессии можно вызвать метод:
session.refreshSessionWithCompletionBlock(WMRefreshFinishDelegate delegate);
Который принимает параметром делегат WMRefreshFinishDelegate
, который исполнится после выполнения запроса обновления.
Для отслеживания ошибок при работе с чатом на делегате WMSessionDelegate
вызывается метод:
void sessionDidReceiveError(WMSession session, WMSessionError errorID);
который возвращает номер ошибки из перечисления WMSessionError
.
Если на устройстве нет сети, то при вызове методов API на делегат будет возвращаться константа WMSessionErrorNetworkError
.
При смене режимов работы сети библиотека сама возобновляет соединение с сервером. При этом на делегате будет вызываться метод:
void sessionDidChangeConnectionStatus(WMSession session, WMSessionConnectionStatus status);
Ожидаемая реакция приложения на переключение статуса сети - оповещение пользователя и, по необходимости, либо ограничение доступа к чату (вид, блокирующий деятельность), либо перехват соответствующих методов для дальнейшего восстановления данных. Для остановки общения с сервером и сервисом Webim необходимо вызвать метод
session.stopSession();
Другой способ — при выходе вызывать метод
session.fullUpdate();
который загрузит с сервера самые актуальные данные. 1
Кроме того, вызов метода session.stopSession()
позволит сэкономить время жизни батареи, так как в этом случае SDK прекращает общение с сервисом Webim.
Работа с push-уведомлениями
Для получения push-уведомлений от сервиса Webim пользователю Webim Mobile SDK необходимо реализовать в своем приложении базовую поимку push-уведомлений (не забудьте про uses-permission
).
Далее, при получении push-уведомления рекомендуется проверить, совпадает ли оправитель с вашим SENDER_ID
. Если нет, то скорее всего это push-уведомление принадлежит сервису Webim, и его необходимо передать для обработки в статичный метод класса WMSession
:
public static void onPushMessage(Context context, Bundle pushData, Class<? extends Activity> clazz)
где Class<? extends Activity> clazz
- класс, который должен быть открыт при открытии push-уведомления.
Также есть возможность самостоятельно обработать push-уведомления:
public static PushNotificationModel getPushNotificationModel(Bundle pushData) throws JsonSyntaxException
где PushNotificationModel
содержит в себе данные о типе push-уведомления (сообщение/файл/системное уведомление) и о необходимом действии (спрятать/показать).
Пример обработки из тестового приложения представлен ниже.
Bundle extras = intent.getExtras();
String senderId = intent.getStringExtra("from");
if (!senderId.equals("YOUR_SENDER_ID")) {
if(WebimSDKApplication.isInBackground()) {
//Webim push logic
WMSession.onPushMessage(this.getApplicationContext(), extras, MainActivity.class);
}
} else {
// Your app push logic
}
Пример подобного использования см. в тестовом приложении WebimClient.
Также, начиная с версии 2.2.7 у онлайн сесcии появилась возможность запрашивать историю сообщений для текущего пользователя (без локального сохранения).
Подробнее про метод запроса истории можно узнать в разделе Оффлайн-обращения.
Оффлайн-обращения
Обращения к оператору могут происходить в режиме "оффлайн". В этом режиме задержка ответа не критична, но важно время хранения и способ обращения с чатами на стороне сервера. За работу с таким типом чатов отвечает класс SDK WMOfflineSession
. Как и для обычных чатов, необходимо инициализировать его перед вызовом любых других методов работы с классом. Важно отметить, что в случае использования обеих сессий сразу пользователь должен инициализировать их последовательно, например, дожидаясь успешного старта онлайн сессии, или использовав специальный конструктор онлайн-сессии, который содержит слушателя на получение push-token
(после его успешного вызова можно однозначно сказать, что онлайн-сессия готова к использованию, и можно инициализировать оффлайн).
WMOfflineSession(Context context, String accountName, String location, String token, String platform, boolean enableLogging)
При использовании стандартного механизма push-уведомлений. Параметр token
может быть null
(или же вовсе не использоваться).
Свяжитесь со службой поддержки для получения более подробной информации об специальном механизме отправки push-уведомлений.
Параметр platform
, если установлен, используется для определения сервером механизма отсылки уведомлений - использование пользовательского сервера или стандартного механизма push-уведомлений. Для использования этого параметра необходимо связаться со службой поддержки Webim. Флаг enableLogging
используется для отладки приложения и позволяет скрыть все записи о работе SDK в журнале LogCat
при завершении разработки.
Данные о чатах хранятся в памяти и доступны через метод класса:
public List getOfflineChats()
Возвращаемый список хранит объекты типа WMChat
. Каждый чат имеет ссылку на относящиеся к нему сообщения. В общем случае чаты и сообщения отсортированы по дате создания.
Также, для уменьшения трафика, SDK сохраняют свое состояние в файле на диске. Предполагается, что клиентское приложение будет периодически опрашивать сервер на предмет появления новых сообщений в чатах. Это осуществляется методом класса WMOfflineMessage
:
public void getHistoryForced(boolean forced, OnHistoryResponceListener listener)
Флаг forced
заставляет SDK заново запросить всю историю. Не рекомендуется злоупотреблять этим флагом из-за увеличения трафика.
OnHistoryResponceListener
вызывается при завершении запроса.
Здесь и далее используется Listener
, вызываемый при завершении запроса. Он имеет следующую структуру:
-
флаг, сигнализирующий успех запроса;
-
один или несколько объектов, значения которых имеют значение при успешном завершении метода;
-
объект ошибки, являющийся действительным (valid) только при неуспешном завершении метода. Ошибка может быть нескольких типов - ошибки домена Webim определяются константой
WMWebimErrorDomain
. В случае такой ошибки имеет место её код — он будет одним из перечисленияWMSessionError
из классаWMBaseSession
.
Возвращаясь к методу запроса истории: объект WMHistoryChanges
в OnHistoryResponceListener
содержит в себе информацию о модификациях с предыдущего запроса. Извлечь эти данные можно при помощи публичных методов объекта:
public List getNewChats()
public List getModifiedChats()
public List getMessages()
С помощью возвращаемых списков можно определить, какие чаты были добавлены, изменены и какие сообщения были добавлены в эти чаты.
Для связи объектов WMMessage
и WMChat
можно использовать метод класса WMOfflineSession
public WMChat chatForMessage(WMMessage message)
Для создания нового чата и отправки сообщений в существующем со стороны клиента используется следующий метод:
public void sendMessage(String message, WMChat chat, String subject, String department, OnMessageSendListener listener)
-
Параметр
message
является обязательным. -
Если параметр
chat
является пустым (передаетсяnull
), то метод создаёт новый чат с одним новым сообщением. Если параметрchat
передан, то создастся новое сообщение в этом чате. -
Параметр
subject
задаёт тему обращения для нового чата, может быть пустым. -
Параметр
department
назначает отдел новому чату, может быть пустым.
OnMessageSendListener
вызывается сразу после ответа сервера и содержит объекты WMChat
и WMMessage
— новые объекты сообщения и чата, если было запрошено создание нового чата.
Аналогично работает метод отправки изображения:
public void sendFile(InputStream imageData, String nameWithExtension, String mimeType, final WMChat chat, String subject, String department, final OnMessageSendListener listener)
Сообщения WMMessage
, созданные данным методом будут иметь тип WMMessageKindFileFromVisitor
. Такие сообщения в поле text
содержат имя файла. Также в объекте присутствуют специальные поля содержащие в себе ссылку на файл, ссылку на предпросмотр, а также параметры файла (WMFileParams
).
SDK хранит прикреплённые к чату изображения до успешной отправки данных на сервер. Управление загрузкой и отображением файла целиком ложится на пользовательское приложение.
При появлении в истории ответа от оператора, соответствующий чат помечается как непрочитанный. Поэтому, после отображения чата пользователю необходимо пометить его прочитанным методом класса сессии:
public void markChatAsRead(WMChat chat, OnChangeReadedByVisitorListener listener)
public void deleteChat(WMChat chat, OnChatDeletedListener listener)
и
public void deleteChats(Collection chats, final OnChatDeletedListener listener)
public void sendUnsentRequests(OnSyncListener listener)
Метод сначала отправляет запросы на удаление удалённых оффлайн-чатов с сервера, затем отправляет сообщения и картинки, попутно создавая для них чаты, если необходимо.
Интерфейс OnSyncListener
содержит 2 метода (см ниже).
Первый срабатывает при отправке неотправленного сообщения на сервер.
Второй информирует пользователя SDK о смене ID локального(созданного в оффлайн) чата, на тот, что был присвоен чату на сервере Webim.
public void onMessageSend(boolean successful, WMChat chat, WMMessage message, WMSessionError error)
public void onChatIdChanged(String oldChatId, String newChatId);
Для достижения большей гибкости в архитектуре приложения использующего Webim SDK, были добавлены синхронные аналоги основных методов-действий:
public WMHistoryChanges getHistoryForcedSync(boolean forced) throws WMExeption
public WMMessage sendMessageSync(String message, WMChat chat, String subject, String department) throws WMExeption
public WMMessage sendFileSync(InputStream imageData, String nameWithExtension, String mimeType, final WMChat chat, String subject, String department) throws WMException
Методы могут работать в любом потоке, кроме главного. Исключение WMExeption
содержит публичный метод
public WMBaseSession.WMSessionError getError()
возвращающий перечисление WMSessionError
из класса WMBaseSession
, и выбрасывается в случае возникновения одной из ошибок аналогичной асинхронным методам.
Для принудительного удаления всех данных, относящихся к работе SDK с устройства, существует метод в WMOfflineSession
:
public void clearCachedUserData()
С его помощью можно сменить "текущего пользователя чата". В текущей реализации активной может быть только одна сессия, поэтому для того чтобы получить данные другого пользователя необходимо:
-
Перестать запрашивать историю для сессии А
-
Cделать очистку данных (метод
clearCachedUserData
у объектаWMSession
сессии А) -
Создать сессию В с другими желаемыми параметрами.
-
Для успешной и эффективной работы с сервисом Webim рекомендуется начинать и прекращать работу с сервером в методах
onStart()
иonStop()
классаActivity
соответственно (или при подключении и отключении кService
, как в тестовом приложении). Этим вы обеспечите себя самой актуальной информацией при обращении к сервису Webim. ↩↩