Сообщения XMPP, потерянные на Android при переключении передачи данных (например, поворот Wi-Fi, GSM ↔ Wifi-переключатель)
Я разрабатываю приложение чата в Android. Использование сервера XMPP. PHP-сервер перенесен в ejabber.
Мое уведомление работает правильно во всех сценариях. Но в одном случае я теряю сообщения XMPP. На самом деле я не получаю уведомления.
В частности, я отключу Wi-Fi или подключение к данным. и после отключения Wi-Fi или подключения к данным любое уведомление, отправленное мне, которое не получает. после того, как я включу Wi-Fi или соединение с данными, я не могу получить сообщения, которые были отправлены мне.
Я реализовал сервис в фоновом режиме. что делает соединение xmpp всегда живым.
Я получаю эту ошибку, пока я отключу WiFi-соединение.
java.net.SocketException: sendto failed: EPIPE (Broken pipe)
java.net.SocketException: recvfrom failed: ETIMEDOUT (Connection timed out)
at libcore.io.IoBridge.maybeThrowAfterSendto(IoBridge.java:506)
at libcore.io.IoBridge.sendto(IoBridge.java:475)
at java.net.PlainSocketImpl.write(PlainSocketImpl.java:508)
at java.net.PlainSocketImpl.access$100(PlainSocketImpl.java:46)
at java.net.PlainSocketImpl$PlainSocketOutputStream.write(PlainSocketImpl.java:270)
at java.io.OutputStreamWriter.flushBytes(OutputStreamWriter.java:167)
at java.io.OutputStreamWriter.flush(OutputStreamWriter.java:158)
at java.io.BufferedWriter.flush(BufferedWriter.java:124)
at org.jivesoftware.smack.PacketWriter.writePackets(PacketWriter.java:286)
at org.jivesoftware.smack.PacketWriter.access$12(PacketWriter.java:270)
at org.jivesoftware.smack.PacketWriter$1.run(PacketWriter.java:137)
Caused by: libcore.io.ErrnoException: sendto failed: EPIPE (Broken pipe)
at libcore.io.Posix.sendtoBytes(Native Method)
at libcore.io.Posix.sendto(Posix.java:146)
at libcore.io.BlockGuardOs.sendto(BlockGuardOs.java:177)
at libcore.io.IoBridge.sendto(IoBridge.java:473)
... 9 more
at libcore.io.IoBridge.maybeThrowAfterRecvfrom(IoBridge.java:552)
at libcore.io.IoBridge.recvfrom(IoBridge.java:516)
at java.net.PlainSocketImpl.read(PlainSocketImpl.java:489)
at java.net.PlainSocketImpl.access$000(PlainSocketImpl.java:46)
at java.net.PlainSocketImpl$PlainSocketInputStream.read(PlainSocketImpl.java:241)
at java.io.InputStreamReader.read(InputStreamReader.java:244)
at java.io.BufferedReader.read(BufferedReader.java:310)
at org.jivesoftware.smack.XMPPConnection$AliveReader.read(XMPPConnection.java:1122)
at org.kxml2.io.KXmlParser.fillBuffer(KXmlParser.java:1496)
at org.kxml2.io.KXmlParser.peekType(KXmlParser.java:979)
at org.kxml2.io.KXmlParser.next(KXmlParser.java:346)
at org.kxml2.io.KXmlParser.next(KXmlParser.java:310)
at org.jivesoftware.smack.PacketReader.parsePackets(PacketReader.java:321)
at org.jivesoftware.smack.PacketReader.access$1(PacketReader.java:216)
at org.jivesoftware.smack.PacketReader$1.run(PacketReader.java:70)
Caused by: libcore.io.ErrnoException: recvfrom failed: ETIMEDOUT (Connection timed out)
at libcore.io.Posix.recvfromBytes(Native Method)
at libcore.io.Posix.recvfrom(Posix.java:131)
at libcore.io.BlockGuardOs.recvfrom(BlockGuardOs.java:164)
at libcore.io.IoBridge.recvfrom(IoBridge.java:513)
... 13 more
Ответы
Ответ 1
Итак, чтобы установить mod_archive, мне нужно сделать это, типичное:
Напишите следующую строку в cmd. (Для ц. Ос)
Войти как root
Создать новый каталог:
mkdir ejabberd_archive_plugin
cd ejabberd_archive_plugin
теперь получите последние модули ejabberd, используя следующую команду
yum https://svn.process-one.net/ejabberd-modules
cd ejabberd-modules/mod_archive/trunk
./build.sh
Теперь перейдите в каталог ebin, используя следующий cmd и получите список всех *.beam файлов для плагинов архива ejabberd.
[email protected] [/ejabberd_archive_plugin/ejabberd-modules/mod_archive/trunk/ebin]# ls –l
Используя следующий cmd, вы получите список всех файлов ejabberd *.beam при настройке и настройке ejabberd.
[email protected] [/usr/lib64/ejabberd/ebin]# ls -l
Теперь скопируйте все файлы *.beam(архивные плагины) в каталог ejabberd ebin, используя следующий cmd
[email protected] [/]# cp /ejabberd_archive_plugin/ejabberd-modules/mod_archive/trunk/ebin /usr/lib64/ejabberd/ebin
Теперь перейдите по следующему URL-адресу и скопируйте все запросы sql-таблицы и запустите в phpmyadmin (база данных ejabberd)
https://svn.process-one.net/ejabberd-modules/mod_archive/trunk/src/mod_archive_odbc_mysql.sql
Теперь настройте ejjaberd.cfg, используя следующий cmd
[email protected] [/etc/ejabberd]# vi ejabberd.cfg
Add the following line into ejabberd.cfg file in modules configuration section
{mod_archive_odbc, [{database_type, "mysql"}, {default_auto_save, true}, {enforce_default_auto_save, true}]},
Теперь перезапустите службу ejabberd.
[email protected] [/etc/ejabberd]# sudo service ejabberd restart
Ответ 2
Для этого вам нужно "Управление потоком" XEP-198. Георг написал хорошую запись в блоге по этой теме: http://op-co.de/blog/posts/XEP-0198/
В основном это позволяет подтверждение подтверждения строфы и возобновления потока, что является чрезмерным тем, что вы хотите сделать в случае, например, переключателя Wifi ↔ GSM.
Из stacktrace я заключаю, что вы используете aSmack (который Smack портирован на Android). Существует открытый запрос функции для реализации Stream Management в Smack: SMACK-333. Фактически, я недавно начал работать над реализацией, но не могу назвать ETA.
Ответ 3
Для этого вам необходимо создать отдельный веб-сервис. поэтому мы можем обрабатывать историю отправленного сообщения. мы можем управлять автономным сообщением.
XEP-198 - единственное решение. сделайте плагин для своего сервера и упростите управление потерянным сообщением. может быть другое решение, но AFAIK, это было бы решением.
Ответ 4
вы можете изменить плагин архива, чтобы сохранить в нем идентификаторы сообщений.
Когда пользователь приходит в Интернет, вызывается веб-служба с полученным последним сообщением. сервер может получить все последующие сообщения, сохраненные на сервере. Я создал его так же и отлично работал.
Ответ 5
Вы должны переучиваться после повторного подключения к Интернету каждый раз. Но имейте в виду, что если вы переходите с помощью одного и того же ресурса и того же пользователя, даже если он находится в сети, тогда сервер будет бросать ошибку потока (заменяется новым соединением), что сделает вас в автономном режиме, и вы не получите никаких сообщение. Для этого сначала отключите себя перед переходом. Попробуйте выполнить поиск в модуле mod amp.