experimental mam legacy compat layer

Daniel Gultsch created

Change summary

src/main/java/eu/siacs/conversations/entities/MucOptions.java            |  6 
src/main/java/eu/siacs/conversations/generator/IqGenerator.java          |  5 
src/main/java/eu/siacs/conversations/parser/MessageParser.java           | 10 
src/main/java/eu/siacs/conversations/services/MessageArchiveService.java | 19 
src/main/java/eu/siacs/conversations/services/XmppConnectionService.java |  5 
src/main/java/eu/siacs/conversations/utils/Xmlns.java                    |  1 
src/main/java/eu/siacs/conversations/xmpp/XmppConnection.java            |  8 
7 files changed, 44 insertions(+), 10 deletions(-)

Detailed changes

src/main/java/eu/siacs/conversations/entities/MucOptions.java 🔗

@@ -374,7 +374,11 @@ public class MucOptions {
 	}
 
 	public boolean mamSupport() {
-		return hasFeature(Xmlns.MAM);
+		return hasFeature(Xmlns.MAM) || hasFeature(Xmlns.MAM_LAGECY);
+	}
+
+	public boolean mamLegacy() {
+		return hasFeature(Xmlns.MAM_LAGECY) && !hasFeature(Xmlns.MAM);
 	}
 
 	public boolean nonanonymous() {

src/main/java/eu/siacs/conversations/generator/IqGenerator.java 🔗

@@ -10,7 +10,6 @@ import org.whispersystems.libaxolotl.ecc.ECPublicKey;
 import org.whispersystems.libaxolotl.state.PreKeyRecord;
 import org.whispersystems.libaxolotl.state.SignedPreKeyRecord;
 
-import java.math.BigInteger;
 import java.nio.ByteBuffer;
 import java.security.cert.CertificateEncodingException;
 import java.security.cert.X509Certificate;
@@ -230,10 +229,10 @@ public class IqGenerator extends AbstractGenerator {
 
 	public IqPacket queryMessageArchiveManagement(final MessageArchiveService.Query mam) {
 		final IqPacket packet = new IqPacket(IqPacket.TYPE.SET);
-		final Element query = packet.query(Xmlns.MAM);
+		final Element query = packet.query(mam.isLegacy() ? Xmlns.MAM_LAGECY : Xmlns.MAM);
 		query.setAttribute("queryid", mam.getQueryId());
 		final Data data = new Data();
-		data.setFormType(Xmlns.MAM);
+		data.setFormType(mam.isLegacy() ? Xmlns.MAM_LAGECY : Xmlns.MAM);
 		if (mam.muc()) {
 			packet.setTo(mam.getWith());
 		} else if (mam.getWith()!=null) {

src/main/java/eu/siacs/conversations/parser/MessageParser.java 🔗

@@ -300,10 +300,16 @@ public class MessageParser extends AbstractParser implements OnMessagePacketRece
 		final boolean isForwarded;
 		boolean isCarbon = false;
 		String serverMsgId = null;
-		final Element result = original.findChild("result",Xmlns.MAM);
+		final Element fin = original.findChild("fin", Xmlns.MAM_LAGECY);
+		if (fin != null) {
+			mXmppConnectionService.getMessageArchiveService().processFinLagecy(fin,original.getFrom());
+			return;
+		}
+		final boolean mamLagecy = original.hasChild("result",Xmlns.MAM_LAGECY);
+		final Element result = original.findChild("result",mamLagecy ? Xmlns.MAM_LAGECY : Xmlns.MAM);
 		final MessageArchiveService.Query query = result == null ? null : mXmppConnectionService.getMessageArchiveService().findQuery(result.getAttribute("queryid"));
 		if (query != null && query.validFrom(original.getFrom())) {
-			Pair<MessagePacket, Long> f = original.getForwardedMessagePacket("result", Xmlns.MAM);
+			Pair<MessagePacket, Long> f = original.getForwardedMessagePacket("result", mamLagecy ? Xmlns.MAM_LAGECY : Xmlns.MAM);
 			if (f == null) {
 				return;
 			}

src/main/java/eu/siacs/conversations/services/MessageArchiveService.java 🔗

@@ -164,8 +164,10 @@ public class MessageArchiveService implements OnAdvancedStreamFeaturesLoaded {
 								query.callback(false);
 							}
 						}
-					} else if (packet.getType() == IqPacket.TYPE.RESULT && fin != null) {
+					} else if (packet.getType() == IqPacket.TYPE.RESULT && fin != null ) {
 						processFin(fin);
+					} else if (packet.getType() == IqPacket.TYPE.RESULT && query.isLegacy()) {
+						//do nothing
 					} else {
 						Log.d(Config.LOGTAG, account.getJid().toBareJid().toString() + ": error executing mam: " + packet.toString());
 						finalizeQuery(query, true);
@@ -219,6 +221,13 @@ public class MessageArchiveService implements OnAdvancedStreamFeaturesLoaded {
 		return queryInProgress(conversation, null);
 	}
 
+	public void processFinLagecy(Element fin, Jid from) {
+		Query query = findQuery(fin.getAttribute("queryid"));
+		if (query != null && query.validFrom(from)) {
+			processFin(fin);
+		}
+	}
+
 	public void processFin(Element fin) {
 		Query query = findQuery(fin.getAttribute("queryid"));
 		if (query == null) {
@@ -319,6 +328,14 @@ public class MessageArchiveService implements OnAdvancedStreamFeaturesLoaded {
 			return query;
 		}
 
+		public boolean isLegacy() {
+			if (conversation == null || conversation.getMode() == Conversation.MODE_SINGLE) {
+				return account.getXmppConnection().getFeatures().mamLegacy();
+			} else {
+				return conversation.getMucOptions().mamLegacy();
+			}
+		}
+
 		public Query next(String reference) {
 			Query query = page(reference);
 			query.pagingOrder = PagingOrder.NORMAL;

src/main/java/eu/siacs/conversations/services/XmppConnectionService.java 🔗

@@ -3711,12 +3711,13 @@ public class XmppConnectionService extends Service {
 	}
 
 	public void fetchMamPreferences(Account account, final OnMamPreferencesFetched callback) {
+		final boolean lagecy = account.getXmppConnection().getFeatures().mamLegacy();
 		IqPacket request = new IqPacket(IqPacket.TYPE.GET);
-		request.addChild("prefs",Xmlns.MAM);
+		request.addChild("prefs",lagecy ? Xmlns.MAM_LAGECY : Xmlns.MAM);
 		sendIqPacket(account, request, new OnIqPacketReceived() {
 			@Override
 			public void onIqPacketReceived(Account account, IqPacket packet) {
-				Element prefs = packet.findChild("prefs",Xmlns.MAM);
+				Element prefs = packet.findChild("prefs",lagecy ? Xmlns.MAM_LAGECY : Xmlns.MAM);
 				if (packet.getType() == IqPacket.TYPE.RESULT && prefs != null) {
 					callback.onPreferencesFetched(prefs);
 				} else {

src/main/java/eu/siacs/conversations/utils/Xmlns.java 🔗

@@ -8,4 +8,5 @@ public final class Xmlns {
 	public static final String HTTP_UPLOAD = "urn:xmpp:http:upload";
 	public static final String STANZA_IDS = "urn:xmpp:sid:0";
 	public static final String MAM = "urn:xmpp:mam:1";
+	public static final String MAM_LAGECY = "urn:xmpp:mam:0";
 }

src/main/java/eu/siacs/conversations/xmpp/XmppConnection.java 🔗

@@ -1628,7 +1628,13 @@ public class XmppConnection implements Runnable {
 		}
 
 		public boolean mam() {
-			return hasDiscoFeature(account.getJid().toBareJid(), Xmlns.MAM);
+			return hasDiscoFeature(account.getJid().toBareJid(), Xmlns.MAM)
+					|| hasDiscoFeature(account.getJid().toBareJid(), Xmlns.MAM_LAGECY);
+		}
+
+		public boolean mamLegacy() {
+			return !hasDiscoFeature(account.getJid().toBareJid(),Xmlns.MAM)
+					&& hasDiscoFeature(account.getJid().toBareJid(),Xmlns.MAM_LAGECY);
 		}
 
 		public boolean push() {