From 94933e21cd08c53a23e5ec6c12bc1dc383b1f3ce Mon Sep 17 00:00:00 2001 From: Christian Schneppe Date: Fri, 29 Jul 2016 19:52:37 +0200 Subject: changed package id inside manifest and project --- .../de/pixart/messenger/parser/PresenceParser.java | 274 +++++++++++++++++++++ 1 file changed, 274 insertions(+) create mode 100644 src/main/java/de/pixart/messenger/parser/PresenceParser.java (limited to 'src/main/java/de/pixart/messenger/parser/PresenceParser.java') diff --git a/src/main/java/de/pixart/messenger/parser/PresenceParser.java b/src/main/java/de/pixart/messenger/parser/PresenceParser.java new file mode 100644 index 000000000..c2e1f3c70 --- /dev/null +++ b/src/main/java/de/pixart/messenger/parser/PresenceParser.java @@ -0,0 +1,274 @@ +package de.pixart.messenger.parser; + +import android.util.Log; + +import java.text.ParseException; +import java.util.ArrayList; +import java.util.List; + +import de.pixart.messenger.Config; +import de.pixart.messenger.crypto.PgpEngine; +import de.pixart.messenger.entities.Account; +import de.pixart.messenger.entities.Contact; +import de.pixart.messenger.entities.Conversation; +import de.pixart.messenger.entities.Message; +import de.pixart.messenger.entities.MucOptions; +import de.pixart.messenger.entities.Presence; +import de.pixart.messenger.generator.IqGenerator; +import de.pixart.messenger.generator.PresenceGenerator; +import de.pixart.messenger.services.XmppConnectionService; +import de.pixart.messenger.xml.Element; +import de.pixart.messenger.xmpp.OnPresencePacketReceived; +import de.pixart.messenger.xmpp.jid.Jid; +import de.pixart.messenger.xmpp.pep.Avatar; +import de.pixart.messenger.xmpp.stanzas.PresencePacket; + +public class PresenceParser extends AbstractParser implements + OnPresencePacketReceived { + + public PresenceParser(XmppConnectionService service) { + super(service); + } + + public void parseConferencePresence(PresencePacket packet, Account account) { + final Conversation conversation = packet.getFrom() == null ? null : mXmppConnectionService.find(account, packet.getFrom().toBareJid()); + if (conversation != null) { + final MucOptions mucOptions = conversation.getMucOptions(); + boolean before = mucOptions.online(); + int count = mucOptions.getUserCount(); + final List tileUserBefore = mucOptions.getUsers(5); + processConferencePresence(packet, mucOptions); + final List tileUserAfter = mucOptions.getUsers(5); + if (!tileUserAfter.equals(tileUserBefore)) { + mXmppConnectionService.getAvatarService().clear(mucOptions); + } + if (before != mucOptions.online() || (mucOptions.online() && count != mucOptions.getUserCount())) { + mXmppConnectionService.updateConversationUi(); + } else if (mucOptions.online()) { + mXmppConnectionService.updateMucRosterUi(); + } + } + } + + private void processConferencePresence(PresencePacket packet, MucOptions mucOptions) { + final Jid from = packet.getFrom(); + if (!from.isBareJid()) { + final String type = packet.getAttribute("type"); + final Element x = packet.findChild("x", "http://jabber.org/protocol/muc#user"); + Avatar avatar = Avatar.parsePresence(packet.findChild("x", "vcard-temp:x:update")); + final List codes = getStatusCodes(x); + if (type == null) { + if (x != null) { + Element item = x.findChild("item"); + if (item != null && !from.isBareJid()) { + mucOptions.setError(MucOptions.Error.NONE); + MucOptions.User user = new MucOptions.User(mucOptions, from); + user.setAffiliation(item.getAttribute("affiliation")); + user.setRole(item.getAttribute("role")); + user.setRealJid(item.getAttributeAsJid("jid")); + if (codes.contains(MucOptions.STATUS_CODE_SELF_PRESENCE) || packet.getFrom().equals(mucOptions.getConversation().getJid())) { + mucOptions.setOnline(); + mucOptions.setSelf(user); + if (mucOptions.mNickChangingInProgress) { + if (mucOptions.onRenameListener != null) { + mucOptions.onRenameListener.onSuccess(); + } + mucOptions.mNickChangingInProgress = false; + } + } else { + mucOptions.addUser(user); + } + if (codes.contains(MucOptions.STATUS_CODE_ROOM_CREATED) && mucOptions.autoPushConfiguration()) { + Log.d(Config.LOGTAG,mucOptions.getAccount().getJid().toBareJid() + +": room '" + +mucOptions.getConversation().getJid().toBareJid() + +"' created. pushing default configuration"); + mXmppConnectionService.pushConferenceConfiguration(mucOptions.getConversation(), + IqGenerator.defaultRoomConfiguration(), + null); + } + if (mXmppConnectionService.getPgpEngine() != null) { + Element signed = packet.findChild("x", "jabber:x:signed"); + if (signed != null) { + Element status = packet.findChild("status"); + String msg = status == null ? "" : status.getContent(); + long keyId = mXmppConnectionService.getPgpEngine().fetchKeyId(mucOptions.getAccount(), msg, signed.getContent()); + if (keyId != 0) { + user.setPgpKeyId(keyId); + } + } + } + if (avatar != null) { + avatar.owner = from; + if (mXmppConnectionService.getFileBackend().isAvatarCached(avatar)) { + if (user.setAvatar(avatar)) { + mXmppConnectionService.getAvatarService().clear(user); + } + } else { + mXmppConnectionService.fetchAvatar(mucOptions.getAccount(), avatar); + } + } + } + } + } else if (type.equals("unavailable")) { + if (codes.contains(MucOptions.STATUS_CODE_SELF_PRESENCE) || + packet.getFrom().equals(mucOptions.getConversation().getJid())) { + if (codes.contains(MucOptions.STATUS_CODE_CHANGED_NICK)) { + mucOptions.mNickChangingInProgress = true; + } else if (codes.contains(MucOptions.STATUS_CODE_KICKED)) { + mucOptions.setError(MucOptions.Error.KICKED); + } else if (codes.contains(MucOptions.STATUS_CODE_BANNED)) { + mucOptions.setError(MucOptions.Error.BANNED); + } else if (codes.contains(MucOptions.STATUS_CODE_LOST_MEMBERSHIP)) { + mucOptions.setError(MucOptions.Error.MEMBERS_ONLY); + } else if (codes.contains(MucOptions.STATUS_CODE_AFFILIATION_CHANGE)) { + mucOptions.setError(MucOptions.Error.MEMBERS_ONLY); + } else if (codes.contains(MucOptions.STATUS_CODE_SHUTDOWN)) { + mucOptions.setError(MucOptions.Error.SHUTDOWN); + } else { + mucOptions.setError(MucOptions.Error.UNKNOWN); + Log.d(Config.LOGTAG, "unknown error in conference: " + packet); + } + } else if (!from.isBareJid()){ + MucOptions.User user = mucOptions.deleteUser(from); + if (user != null) { + mXmppConnectionService.getAvatarService().clear(user); + } + } + } else if (type.equals("error")) { + Element error = packet.findChild("error"); + if (error != null && error.hasChild("conflict")) { + if (mucOptions.online()) { + if (mucOptions.onRenameListener != null) { + mucOptions.onRenameListener.onFailure(); + } + } else { + mucOptions.setError(MucOptions.Error.NICK_IN_USE); + } + } else if (error != null && error.hasChild("not-authorized")) { + mucOptions.setError(MucOptions.Error.PASSWORD_REQUIRED); + } else if (error != null && error.hasChild("forbidden")) { + mucOptions.setError(MucOptions.Error.BANNED); + } else if (error != null && error.hasChild("registration-required")) { + mucOptions.setError(MucOptions.Error.MEMBERS_ONLY); + } + } + } + } + + private static List getStatusCodes(Element x) { + List codes = new ArrayList<>(); + if (x != null) { + for (Element child : x.getChildren()) { + if (child.getName().equals("status")) { + String code = child.getAttribute("code"); + if (code != null) { + codes.add(code); + } + } + } + } + return codes; + } + + public void parseContactPresence(final PresencePacket packet, final Account account) { + final PresenceGenerator mPresenceGenerator = mXmppConnectionService.getPresenceGenerator(); + final Jid from = packet.getFrom(); + if (from == null || from.equals(account.getJid())) { + return; + } + final String type = packet.getAttribute("type"); + final Contact contact = account.getRoster().getContact(from); + if (type == null) { + final String resource = from.isBareJid() ? "" : from.getResourcepart(); + contact.setPresenceName(packet.findChildContent("nick", "http://jabber.org/protocol/nick")); + Avatar avatar = Avatar.parsePresence(packet.findChild("x", "vcard-temp:x:update")); + if (avatar != null && !contact.isSelf()) { + avatar.owner = from.toBareJid(); + if (mXmppConnectionService.getFileBackend().isAvatarCached(avatar)) { + if (contact.setAvatar(avatar)) { + mXmppConnectionService.getAvatarService().clear(contact); + mXmppConnectionService.updateConversationUi(); + mXmppConnectionService.updateRosterUi(); + } + } else { + mXmppConnectionService.fetchAvatar(account, avatar); + } + } + int sizeBefore = contact.getPresences().size(); + + final String show = packet.findChildContent("show"); + final Element caps = packet.findChild("c", "http://jabber.org/protocol/caps"); + final String message = packet.findChildContent("status"); + final Presence presence = Presence.parse(show, caps, message); + contact.updatePresence(resource, presence); + if (presence.hasCaps()) { + mXmppConnectionService.fetchCaps(account, from, presence); + } + + final Element idle = packet.findChild("idle","urn:xmpp:idle:1"); + if (idle != null) { + contact.flagInactive(); + String since = idle.getAttribute("since"); + try { + contact.setLastseen(AbstractParser.parseTimestamp(since)); + } catch (NullPointerException | ParseException e) { + contact.setLastseen(System.currentTimeMillis()); + } + } else { + contact.flagActive(); + contact.setLastseen(AbstractParser.parseTimestamp(packet)); + } + + PgpEngine pgp = mXmppConnectionService.getPgpEngine(); + Element x = packet.findChild("x", "jabber:x:signed"); + if (pgp != null && x != null) { + Element status = packet.findChild("status"); + String msg = status != null ? status.getContent() : ""; + contact.setPgpKeyId(pgp.fetchKeyId(account, msg, x.getContent())); + } + boolean online = sizeBefore < contact.getPresences().size(); + mXmppConnectionService.onContactStatusChanged.onContactStatusChanged(contact, online); + } else if (type.equals("unavailable")) { + if (from.isBareJid()) { + contact.clearPresences(); + } else { + contact.removePresence(from.getResourcepart()); + } + mXmppConnectionService.onContactStatusChanged.onContactStatusChanged(contact, false); + } else if (type.equals("subscribe")) { + if (contact.getOption(Contact.Options.PREEMPTIVE_GRANT)) { + mXmppConnectionService.sendPresencePacket(account, + mPresenceGenerator.sendPresenceUpdatesTo(contact)); + } else { + contact.setOption(Contact.Options.PENDING_SUBSCRIPTION_REQUEST); + final Conversation conversation = mXmppConnectionService.findOrCreateConversation( + account, contact.getJid().toBareJid(), false); + final String statusMessage = packet.findChildContent("status"); + if (statusMessage != null + && !statusMessage.isEmpty() + && conversation.countMessages() == 0) { + conversation.add(new Message( + conversation, + statusMessage, + Message.ENCRYPTION_NONE, + Message.STATUS_RECEIVED + )); + } + } + } + mXmppConnectionService.updateRosterUi(); + } + + @Override + public void onPresencePacketReceived(Account account, PresencePacket packet) { + if (packet.hasChild("x", "http://jabber.org/protocol/muc#user")) { + this.parseConferencePresence(packet, account); + } else if (packet.hasChild("x", "http://jabber.org/protocol/muc")) { + this.parseConferencePresence(packet, account); + } else { + this.parseContactPresence(packet, account); + } + } + +} -- cgit v1.2.3