Android websocket client пример

Learn to use WebSockets on Android with OkHttp

Feb 14, 2017 · 3 min read

Like you should know, WebSocket is a computer communications protocol, providing full-duplex communication channels over a single TCP connection. It is supported in HTML 5. Since the version 3.5 of the OkHttp library, you can also use WebSockets connection in your Android applications. In this tutorial, you are going to learn how to create a simple chat application with the Echo WebSocket Server which is available at the following address : http://www.websocket.org/echo.html .

Note that you can also discover this tutorial in video on Youtube :

First step is to add the OkHttp dependency in your Gradle build file

D o n’t forget to add the Internet permission in your Android manifest since the application will use the network to create a WebSocket connection to the Echo WebSocket server. For this tutorial, we will need a simple layout with a Button to start the connection and the exchange with the server and a TextView which will be used as a console output for the messages received from the server :

Then, we can write the Java code of the application. The main part will be the method used to create the connection to the WebSocket connection and the WebSocketListener object used to exchange with the server :

We send messages to the server in the onOpen method. The messages received from the Echo WebSocket server are displayed inside the onMessage method. Note that you can send text or hexadecimal messages. Lastly, we close the connection by using the close method of the WebSocket object. To create the WebSocket connection with OkHttp, we need to build a Request object with the URL of the Echo WebSocket server in parameter, then calling the newWebSocket method of the OkHttpClient object.

The code will have the following form :

Finally, you have just to run your application and enjoy the result :

Источник

Чаты на вебсокетах, когда на бэкенде WAMP. Теперь про Android

Мой коллега уже писал про наш опыт разработки чатов на вебсокетах для iOS, поэтому часть про особенности бэкенда с точки зрения клиента у нас общая. А вот реализация на Android, конечно, отличается. И ещё мне не приходилось, как в первой статье, искать библиотеку для поддержки старых версий операционной системы, потому что на Android каких-то глобальных изменений в сетевой части не было, всё работало и так.

К реализации вернёмся чуть ниже, а начнём с ответов на вопросы про бэкенд, которые появились после первой статьи: почему WAMP, какой брокер используем и некоторые другие моменты.

На время передам слово нашему бэкенд-разработчику @antoha-gs, а если хочется сразу почитать про клиент-серверное общение и декодирование, то первый раздел можно пропустить.

Что там на бэкенде

Почему WAMP. Изначально искал открытый протокол, который мог бы работать поверх WebSocket с поддержкой функционала PubSub и RPC и с потенциалом масштабирования. Лучше всего подошёл WAMP — одни плюсы, разве что не нашёл реализации протокола на Java/Kotlin, которая бы меня устраивала.

Какой брокер мы используем. Продолжая предыдущий пункт, это, собственно, и послужило написанию собственной реализации протокола. Плюсы — экспертиза в своём коде и гибкость, то есть при надобности всегда можно отойти от стандарта в нужную сторону. Каких-то серьёзных минусов не выявил.

К небольшим проблемам реализации проекта чатов можно отнести то, что нужно было ресёрчить и ревёрсить то, как работает реализация на Sendbird — сервисе, который мы использовали. То есть какими возможностями мы там пользовались и какой дополнительный функционал был реализован поверх. Также к сложностям отнёс бы перенос данных из Sendbird в свою базу.

Читайте также:  Как ускорить работу android studio

Ещё был такой момент в комментариях:

«Правильно, что не стали использовать Socket.IO, так как рано или поздно столкнулись бы с двумя проблемами: 1) Пропуск сообщений. 2) Дублирование сообщений. WAMP — к сожалению — также не решает эти вопросы. Поэтому для чатов лучше использовать что-то вроде MQTT».

Насколько я могу судить, протокол не решает таких проблем магическим образом, всё упирается в реализацию. Да, на уровне протокола может поддерживаться дополнительная информация/настройки для указания уровня обслуживания (at most/at least/exactly), но ответственность за её реализацию всё равно лежит на конкретной имплементации. В нашем случае, учитывая специфику, достаточно гарантировать надёжную запись в базу и доставку на клиенты at most once, что WAMP вполне позволяет реализовать. Также он легко расширяем.

MQTT — отличный протокол, никаких вопросов, но в данном сравнении у него меньше фич, чем у WAMP, которые могли бы пригодиться нам для сервиса чатов. В качестве альтернативы можно было бы рассмотреть XMPP (aka Jabber), потому что, в отличие от MQTT и WAMP, он предназначен для мессенджеров, но и там без «допилов» бы не обошлось. Ещё можно создать свой собственный протокол, что нередко делают в компаниях, но это, в том числе, дополнительные временные затраты.

Это были основные вопросы касательно бэкенда после предыдущей статьи, и, думаю, мы ещё вернёмся к нашей реализации в отдельном материале. А сейчас возвращаю слово Сергею.

Клиент-сервер

Начну с того, что WAMP означает для клиента.

В целом протокол предусматривает почти всё. Это облегчает взаимодействие разработчиков клиентской части и бэка.

Кодирование всех типов событий в числах (PUBLISH — это 16, SUBSCRIBE — 32 и так далее). Это усложняет чтение логов разработчику и QA (сразу не догадаться, что значит прилетевшее сообщение [33,11,5862354]).

Механизм подписок на события (например, новые сообщения в чат или обновление количества участников) реализован через получение от бэкенда уникального id подписки. Его надо где-то хранить и ни в коем случае не терять во избежание утечек. Как это сделано (было бы сильно проще и подписываться и отписываться просто по id чата):client → подписываемся на новые сообщения в чате [32,18,<>,»co.fun.chat.testChatId»]backend → [33,18,5868752 (id подписки)]client → после выхода из чата отписываемся по id [34,20,5868752]

Для работы с сокетом использовали OkHttp (стильно, надёжно, современно, реализация ping-pong таймаутов из коробки) и RxJava, потому что сама концепция чата — практически идеальный пример того самого event-based programming, ради которого Rx, в общем, и задумывался.

Теперь рассмотрим пример коннекта к серверу, использующему WAMP-протокол через OkHttpClient:

Пример реализации ChatWebSocketListener:

Здесь мы видим, что все сообщения от сокета приходят в виде обычного String, представляющего собой JSON, закодированный по правилам WAMP протокола и имеющий структуру:

Декодирование и отправка сообщений

Для декодинга сообщений в объекты мы использовали библиотеку Gson. Все модели ответа отписываются обычными data-классами вида:

А декодирование происходит с помощью следующего кода:

Теперь рассмотрим базовый пример отправки сообщения по сокету. Для удобства мы сделали обёртку для всех базовых типов WAMP сообщений:

А также добавили фабрику для формирования этих сообщений:

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

Сопоставление отправленного сообщения и ответа на него в WAMP происходит с помощью уникального идентификатора seq, отправляемого клиентом, который потом кладётся в ответ.

В клиенте генерация идентификатора делается следующим образом:

Взаимодействие с WAMP Subscriptions

Подписки в протоколе WAMP — концепт, по которому подписчик (клиент) подписывается на какие-либо события, приходящие от бэкенда. В нашей реализации мы использовали:

обновление списка чатов;

новые сообщения в конкретном чате;

изменение онлайн-статуса собеседника;

изменение в составе участников чата;

смена роли юзера (например, когда его назначают модератором);

Клиент сообщает серверу о желании получать события с помощью следующего сообщения:

Где topic — это скоуп событий, которые нужны подписчику.

Для формирования базового события подписки используется код:

Разумеется, при выходе с экрана (например, списка чатов), необходимо соответствующую подписку корректно отменять. И вот тут выявляется одно из свойств протокола WAMP: при отправке subscribe-сообщения бэкенд возвращает числовой id подписки, и выходит, что отписаться от конкретного топика нельзя — нужно запоминать и хранить этот id, чтобы использовать его при необходимости.

Читайте также:  Лучший стилус для андроид планшета

А так как хочется оградить пользователей API подписок от лишнего менеджмента айдишников, было сделано следующее:

Так клиент ничего не будет знать об id, и для отписки ему будет достаточно указать имя подписки, которую необходимо отменить:

Это то, что я хотел рассказать про реализацию на Android, но если есть вопросы — постараюсь ответить на них в комментариях. Напомню, что про чаты на вебсокетах в iOS мы уже писали вот здесь, а также готовим отдельную часть про бэкенд.

Источник

Java WebSocket Programming with Android and Spring Boot

Free up to 1MM monthly messages. No credit card required.

The WebSocket protocol provides an always-on connection between a client and a server for bi-directional communication. This is great for applications that require a real-time connection, such as multiplayer games, internet of things applications, and chat apps. In this tutorial, we are going to set up a simple Android client that will connect to a WebSocket server using Spring Boot.

Android WebSocket Client

For the Android client, we are going to make a simple demo app that contains four image buttons of cute animals. To get started, initialize a new project on Android Studio, with a Basic Activity, called JavaWebSocketClient. We are going to use a lightweight WebSocket client library for the app, which can be found in this repo. In order to use this library, we have to add it to the build.gradle file in the app directory. Add the following to the dependencies and sync the project:

Make sure to include the internet access permission in the manifest file:

Connect the Client to the Server

Go to MainActivity.java, import the following packages and set up onCreate():

Next, create a new method createWebSocketClient():

This may look like a lot, but really, we are doing four key things in this method:

  1. Starting a new connection to the localhost “ws://10.0.2.2:8080/websocket”.
  2. Sending a message to the server once a connection is opened.
  3. Displaying the messages sent from the server on the app.
  4. Setting timeouts and automatic reconnection.

Now that we connected the client to the server, let’s set up the method to send messages to the server.

Send Messages to the Server

In MainActivity.java, add the following to sendMessage():

When a button is pressed, the button id is sent to the server. This method is called from the file animal_sounds.xml, which you can get from my Java WebSocket Programming Repo. Make sure to modify the file strings.xml under the values directory so you won’t get any errors in the XML file.

The last thing to do on the client-side is to add the images for the animals in the drawable directory. The images are made by Freepik from www.flaticon.com.

Run the Android app in your emulator:

Nothing happens right now because the server is not set up. Let’s do that right now!

Spring Boot WebSocket Server

For our server, we will use Spring Boot which makes it easy to create production-grade Spring applications with minimum configurations. To quickly bootstrap our project, we will use Spring Initializr. We will generate a Gradle project, but you can also generate a Maven project if you prefer. Configure the Initializr like the screenshot below and make sure to add WebSocket as a dependency:

Generate the project to download a zip file. Once you unzip the file, go to the src directory and keep on clicking the subdirectories until you get to the JavaWebSocketServerApplication.java file.

Add two files to the directory: WebSocketHandler.java and WebSocketConfiguration.java.

Handle the WebSocket Messages

We have to handle the incoming messages that arrive in the server. To do so, in WebSocketHandler.java inherit the class to implement the method handleTextMessage(). Add the following code to the file:

Inside the method, we simply get the string value of the message payload and do a switch expression to check the value of the message with the value of each case. A unique message with the animal sound is sent to the client.

Читайте также:  Андроид для nissan pathfinder r51

Configure the WebSocket Request Handling

In WebSocketConfiguration.java, implement the interface WebSocketConfigurer and add the following code to the file:

We set up the method registerWebSocketHandlers to configure the WebSocketHandler to the path “/websocket“.

That is all for the server-side. Now that we have everything set up, let’s start the WebSocket server and run the app!

Send Data between Server and Client

In the terminal, go to the root directory of your Spring Boot project and run the following command to start the server:

Next, run the Android client in Android Studio and once the app loads, click any of the four buttons.


Play around with the Android app and see how messages are sent from client-to-server with WebSockets!

Update the Android Client to Pub/Sub

Sending data client-to-server or server-to-client is not difficult and can be done pretty fast. But what if you want to send data client-to-client? You can’t directly connect clients without implementing some routing and broker logic on the server.

There are several tools we can use to make this task less time-consuming. One such tool is Socket.IO, which sets up a real-time, bidirectional connection between clients. This is a great open-source tool to use, but we still need to set up a server and connect the client to the server. Is there an easier way to securely and reliably send data between clients without manually setting up a server? With PubNub, we can.

PubNub provides the real-time infrastructure to power any device that speaks TCP. We can stream data from client-to-client, client-to-server or server-to-client using PubNub’s Global Data Stream Network in under 100 ms! With PubNub, an always-on connection is made between the devices connected to the channel, similar to WebSockets. The best part is that you don’t have to worry about setting up a server and maintaining the server because PubNub is serverless and is infinitely scalable.

To see how PubNub simplifies the process of sending data from client-to-client, we will modify the Android app we built earlier. But first, sign up for a free PubNub account to get your free Pub/Sub API keys. Sign up and log in using the form below:

Modify the Android Client

To differentiate the updated app from the old app, create a new Android project called PubNubJavaClient. In order to use PubNub’s Android SDK, add the following to the build.gradle file in the app directory and sync the project:

Include the following permissions to the manifest file:

Everything else, except MainActivity.java, is the same. From the previous app, add the following files to the updated app: animal_sounds.xml, strings.xml and the images from the drawable directory. Once you finish this, go to MainActivity.java to add the new code. Import the following packages and set up onCreate():

Make a call to initPubNub() to initialize PubNub:

We do three key things in this method:

  1. Initialize the PubNub client API. Make sure to replace “ENTER_YOUR_PUB_KEY” and “ENTER_YOUR_SUB_KEY” with your Pub/Sub keys.
  2. Set up a listener to get notified of messages that arrive on the channel. As we did earlier, display the message on the app for the client to see.
  3. Subscribe to the global channel where messages will be published.

When the user presses a button, the method sendMessage() is called:

This method is similar to what we did earlier, except now we publish the actual message, the animal sound, to the global channel and not the server. We use publishMessage() as a helper function to publish the message.

That is all we need to get the app up-and-running!

Send Data Between Clients

Run the Android app in two emulators to see messages appear in real time.

Источник

Оцените статью