From d8076ddcacab48da00222a34c6dc00907383b22a Mon Sep 17 00:00:00 2001 From: Paul Schaub Date: Wed, 24 Jun 2020 22:50:26 +0200 Subject: [PATCH] Fix message adapter --- .../android/ui/chat/AndroidChatViewModel.java | 2 +- .../roster/contacts/ContactListViewModel.java | 4 +- build.gradle | 1 + .../messenger/data/di/MappingModule.java | 16 +----- .../data/mapping/MessageMapping.java | 10 +--- .../MessagePayloadContainerMapping.java | 57 ------------------- .../data/mapping/MessagePayloadMapping.java | 47 --------------- .../model/AbstractDirectMessagesRelation.java | 26 --------- .../model/AbstractGroupMessagesRelation.java | 27 --------- .../data/model/AbstractMessageModel.java | 12 ++-- .../AbstractMessagePayloadContainerModel.java | 24 -------- .../model/AbstractMessagePayloadModel.java | 27 --------- .../data/repository/RxMessageRepository.java | 53 +++++------------ .../data/repository/RxPeerRepository.java | 16 +++--- .../data/repository/dao/MessageDao.java | 21 +------ .../mercury_im/messenger/core/Messenger.java | 8 --- .../core/crypto/MercuryOpenPgpManager.java | 18 +++++- .../store/message/MercuryMessageStore.java | 25 +++++++- .../messenger/core/xmpp/CsiManager.java | 6 ++ .../core/xmpp/MercuryConnection.java | 13 +++-- libs/Smack | 2 +- 21 files changed, 94 insertions(+), 321 deletions(-) delete mode 100644 data/src/main/java/org/mercury_im/messenger/data/mapping/MessagePayloadContainerMapping.java delete mode 100644 data/src/main/java/org/mercury_im/messenger/data/mapping/MessagePayloadMapping.java delete mode 100644 data/src/main/java/org/mercury_im/messenger/data/model/AbstractDirectMessagesRelation.java delete mode 100644 data/src/main/java/org/mercury_im/messenger/data/model/AbstractGroupMessagesRelation.java delete mode 100644 data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessagePayloadContainerModel.java delete mode 100644 data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessagePayloadModel.java diff --git a/app/src/main/java/org/mercury_im/messenger/android/ui/chat/AndroidChatViewModel.java b/app/src/main/java/org/mercury_im/messenger/android/ui/chat/AndroidChatViewModel.java index 6be1b2f..6f4ef3f 100644 --- a/app/src/main/java/org/mercury_im/messenger/android/ui/chat/AndroidChatViewModel.java +++ b/app/src/main/java/org/mercury_im/messenger/android/ui/chat/AndroidChatViewModel.java @@ -85,7 +85,7 @@ public class AndroidChatViewModel extends ViewModel implements MercuryAndroidVie .doOnNext(m -> LOGGER.log(Level.INFO, "NEW MESSAGES.")) .subscribe(messageList -> { - AndroidChatViewModel.this.messages.setValue(messageList); + AndroidChatViewModel.this.messages.postValue(messageList); }, error -> LOGGER.log(Level.SEVERE, "Error subscribing to messages", error))); } diff --git a/app/src/main/java/org/mercury_im/messenger/android/ui/roster/contacts/ContactListViewModel.java b/app/src/main/java/org/mercury_im/messenger/android/ui/roster/contacts/ContactListViewModel.java index bd42b15..c29ab5a 100644 --- a/app/src/main/java/org/mercury_im/messenger/android/ui/roster/contacts/ContactListViewModel.java +++ b/app/src/main/java/org/mercury_im/messenger/android/ui/roster/contacts/ContactListViewModel.java @@ -43,9 +43,9 @@ public class ContactListViewModel extends ViewModel { Log.d("ContactListViewModel", "Start observing database"); // Subscribe to changes to the contacts table and update the LiveData object for the UI. compositeDisposable.add(xmppContactRepository.observeAllPeers() - .subscribe(rosterEntryList::setValue)); + .subscribe(rosterEntryList::postValue)); compositeDisposable.add(accountRepository.observeAllAccounts() - .subscribe(accounts::setValue)); + .subscribe(accounts::postValue)); } @Override diff --git a/build.gradle b/build.gradle index ba1be77..f263c07 100644 --- a/build.gradle +++ b/build.gradle @@ -37,6 +37,7 @@ allprojects { // https://stackoverflow.com/questions/48488563/gradle-xpp3-error/48746294#48746294 all { exclude group: 'xpp3', module: 'xpp3_min' + exclude group: 'xpp3', module: 'xpp3' } } } diff --git a/data/src/main/java/org/mercury_im/messenger/data/di/MappingModule.java b/data/src/main/java/org/mercury_im/messenger/data/di/MappingModule.java index e1aa7d8..28085ff 100644 --- a/data/src/main/java/org/mercury_im/messenger/data/di/MappingModule.java +++ b/data/src/main/java/org/mercury_im/messenger/data/di/MappingModule.java @@ -4,9 +4,7 @@ import org.mercury_im.messenger.data.mapping.AccountMapping; import org.mercury_im.messenger.data.mapping.DirectChatMapping; import org.mercury_im.messenger.data.mapping.EntityCapsMapping; import org.mercury_im.messenger.data.mapping.GroupChatMapping; -import org.mercury_im.messenger.data.mapping.MessagePayloadMapping; import org.mercury_im.messenger.data.mapping.MessageMapping; -import org.mercury_im.messenger.data.mapping.MessagePayloadContainerMapping; import org.mercury_im.messenger.data.mapping.PeerMapping; import javax.inject.Singleton; @@ -44,19 +42,7 @@ public class MappingModule { @Provides @Singleton static MessageMapping provideMessageMapping() { - return new MessageMapping(provideMessagePayloadMapping()); - } - - @Provides - @Singleton - static MessagePayloadContainerMapping provideMessagePayloadMapping() { - return new MessagePayloadContainerMapping(provideMessageContentMapping()); - } - - @Provides - @Singleton - static MessagePayloadMapping provideMessageContentMapping() { - return new MessagePayloadMapping(); + return new MessageMapping(); } @Provides diff --git a/data/src/main/java/org/mercury_im/messenger/data/mapping/MessageMapping.java b/data/src/main/java/org/mercury_im/messenger/data/mapping/MessageMapping.java index 7938d64..72966b0 100644 --- a/data/src/main/java/org/mercury_im/messenger/data/mapping/MessageMapping.java +++ b/data/src/main/java/org/mercury_im/messenger/data/mapping/MessageMapping.java @@ -1,22 +1,16 @@ package org.mercury_im.messenger.data.mapping; import org.mercury_im.messenger.data.model.MessageModel; -import org.mercury_im.messenger.data.model.MessagePayloadContainerModel; import org.mercury_im.messenger.entity.message.Message; -import org.mercury_im.messenger.entity.message.PayloadContainer; -import java.util.ArrayList; -import java.util.List; import javax.inject.Inject; public class MessageMapping extends AbstractMapping { - private final MessagePayloadContainerMapping messagePayloadContainerMapping; - @Inject - public MessageMapping(MessagePayloadContainerMapping messagePayloadContainerMapping) { - this.messagePayloadContainerMapping = messagePayloadContainerMapping; + public MessageMapping() { + } @Override diff --git a/data/src/main/java/org/mercury_im/messenger/data/mapping/MessagePayloadContainerMapping.java b/data/src/main/java/org/mercury_im/messenger/data/mapping/MessagePayloadContainerMapping.java deleted file mode 100644 index d40d20f..0000000 --- a/data/src/main/java/org/mercury_im/messenger/data/mapping/MessagePayloadContainerMapping.java +++ /dev/null @@ -1,57 +0,0 @@ -package org.mercury_im.messenger.data.mapping; - -import org.mercury_im.messenger.data.model.MessagePayloadModel; -import org.mercury_im.messenger.data.model.MessagePayloadContainerModel; -import org.mercury_im.messenger.entity.message.PayloadContainer; -import org.mercury_im.messenger.entity.message.content.Payload; - -import java.util.ArrayList; -import java.util.List; - -import javax.inject.Inject; - -public class MessagePayloadContainerMapping extends AbstractMapping { - - private final MessagePayloadMapping messagePayloadMapping; - - @Inject - public MessagePayloadContainerMapping(MessagePayloadMapping messagePayloadMapping) { - this.messagePayloadMapping = messagePayloadMapping; - } - - @Override - public PayloadContainer newEntity(MessagePayloadContainerModel model) { - return new PayloadContainer(); - } - - @Override - public MessagePayloadContainerModel newModel(PayloadContainer entity) { - return new MessagePayloadContainerModel(); - } - - @Override - public MessagePayloadContainerModel mapToModel(PayloadContainer entity, MessagePayloadContainerModel model) { - model.getContents().clear(); - for (Payload contentEntity : entity.getMessageContents()) { - MessagePayloadModel contentModel = messagePayloadMapping.toModel(contentEntity, new MessagePayloadModel()); - contentModel.setPayloadContainer(model); - model.getContents().add(contentModel); - } - - return model; - } - - @Override - public PayloadContainer mapToEntity(MessagePayloadContainerModel model, PayloadContainer entity) { - entity.setId(model.getId()); - - List contents = new ArrayList<>(model.getContents().size()); - for (MessagePayloadModel contentModel : model.getContents()) { - Payload contentEntity = messagePayloadMapping.toEntity(contentModel, null); - contents.add(contentEntity); - } - entity.setMessageContents(contents); - - return entity; - } -} diff --git a/data/src/main/java/org/mercury_im/messenger/data/mapping/MessagePayloadMapping.java b/data/src/main/java/org/mercury_im/messenger/data/mapping/MessagePayloadMapping.java deleted file mode 100644 index 3328dc9..0000000 --- a/data/src/main/java/org/mercury_im/messenger/data/mapping/MessagePayloadMapping.java +++ /dev/null @@ -1,47 +0,0 @@ -package org.mercury_im.messenger.data.mapping; - -import org.mercury_im.messenger.data.model.MessagePayloadModel; -import org.mercury_im.messenger.entity.message.content.Payload; -import org.mercury_im.messenger.entity.message.content.TextPayload; - -import static org.mercury_im.messenger.data.enums.MessageContentType.body; - -public class MessagePayloadMapping extends AbstractMapping { - - @Override - public Payload newEntity(MessagePayloadModel model) { - switch (model.getType()) { - case body: - return new TextPayload(); - default: - return null; - } - } - - @Override - public MessagePayloadModel newModel(Payload entity) { - return new MessagePayloadModel(); - } - - @Override - public MessagePayloadModel mapToModel(Payload entity, MessagePayloadModel model) { - if (entity instanceof TextPayload) { - model.setType(body); - model.setBody(((TextPayload) entity).getBody()); - } - // else if (...) - return model; - } - - @Override - public Payload mapToEntity(MessagePayloadModel model, Payload entity) { - entity.setId(model.getId()); - switch (model.getType()) { - case body: - TextPayload body = (TextPayload) entity; - body.setBody(model.getBody()); - break; - } - return entity; - } -} diff --git a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractDirectMessagesRelation.java b/data/src/main/java/org/mercury_im/messenger/data/model/AbstractDirectMessagesRelation.java deleted file mode 100644 index 6ecbf2f..0000000 --- a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractDirectMessagesRelation.java +++ /dev/null @@ -1,26 +0,0 @@ -package org.mercury_im.messenger.data.model; - -import io.requery.CascadeAction; -import io.requery.Entity; -import io.requery.ForeignKey; -import io.requery.Generated; -import io.requery.Key; -import io.requery.ManyToOne; -import io.requery.ReferentialAction; -import io.requery.Table; - -@Entity -@Table(name = "direct_messages") -public abstract class AbstractDirectMessagesRelation { - - @Key @Generated - long id; - - @ManyToOne(cascade = {CascadeAction.SAVE}) - @ForeignKey(referencedColumn = "id", delete = ReferentialAction.CASCADE) - DirectChatModel chat; - - @ManyToOne(cascade = {CascadeAction.SAVE, CascadeAction.DELETE}) - @ForeignKey(referencedColumn = "id", delete = ReferentialAction.CASCADE) - MessageModel message; -} diff --git a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractGroupMessagesRelation.java b/data/src/main/java/org/mercury_im/messenger/data/model/AbstractGroupMessagesRelation.java deleted file mode 100644 index f673a09..0000000 --- a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractGroupMessagesRelation.java +++ /dev/null @@ -1,27 +0,0 @@ -package org.mercury_im.messenger.data.model; - -import io.requery.CascadeAction; -import io.requery.Entity; -import io.requery.ForeignKey; -import io.requery.Generated; -import io.requery.Key; -import io.requery.ManyToOne; -import io.requery.OneToOne; -import io.requery.ReferentialAction; -import io.requery.Table; - -@Entity -@Table(name = "group_messages") -public abstract class AbstractGroupMessagesRelation { - - @Key @Generated - long id; - - @ManyToOne(cascade = {CascadeAction.SAVE}) - @ForeignKey(referencedColumn = "id", delete = ReferentialAction.CASCADE) - GroupChatModel chat; - - @ManyToOne(cascade = {CascadeAction.SAVE, CascadeAction.DELETE}) - @ForeignKey(referencedColumn = "id", delete = ReferentialAction.CASCADE) - MessageModel message; -} diff --git a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessageModel.java b/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessageModel.java index edfebfb..480e3a0 100644 --- a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessageModel.java +++ b/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessageModel.java @@ -2,17 +2,15 @@ package org.mercury_im.messenger.data.model; import org.mercury_im.messenger.data.converter.MessageDirectionConverter; import org.mercury_im.messenger.entity.message.MessageDirection; +import org.pgpainless.key.OpenPgpV4Fingerprint; import java.util.Date; -import java.util.Set; import java.util.UUID; import io.requery.Column; import io.requery.Convert; import io.requery.Entity; -import io.requery.Generated; import io.requery.Key; -import io.requery.OneToMany; import io.requery.Persistable; import io.requery.Table; import io.requery.converter.UUIDConverter; @@ -25,6 +23,9 @@ public abstract class AbstractMessageModel implements Persistable { @Convert(UUIDConverter.class) UUID id; + @Column(nullable = false) + UUID chatId; + @Column(nullable = false) String sender; @@ -44,7 +45,7 @@ public abstract class AbstractMessageModel implements Persistable { @Column String legacyId; - @Column + @Column(unique = true) String originId; @Column @@ -52,4 +53,7 @@ public abstract class AbstractMessageModel implements Persistable { @Column String stanzaIdBy; + + @Column + OpenPgpV4Fingerprint senderOXFingerprint; } diff --git a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessagePayloadContainerModel.java b/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessagePayloadContainerModel.java deleted file mode 100644 index 8bd4a74..0000000 --- a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessagePayloadContainerModel.java +++ /dev/null @@ -1,24 +0,0 @@ -package org.mercury_im.messenger.data.model; - -import java.util.Set; - -import io.requery.Entity; -import io.requery.Generated; -import io.requery.Key; -import io.requery.ManyToOne; -import io.requery.OneToMany; -import io.requery.Table; - -@Entity -@Table(name = "msg_payload_containers") -public abstract class AbstractMessagePayloadContainerModel { - - @Key @Generated - long id; - - @ManyToOne - MessageModel message; - - @OneToMany - Set contents; -} diff --git a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessagePayloadModel.java b/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessagePayloadModel.java deleted file mode 100644 index 00a7d76..0000000 --- a/data/src/main/java/org/mercury_im/messenger/data/model/AbstractMessagePayloadModel.java +++ /dev/null @@ -1,27 +0,0 @@ -package org.mercury_im.messenger.data.model; - -import org.mercury_im.messenger.data.enums.MessageContentType; - -import io.requery.Column; -import io.requery.Entity; -import io.requery.Generated; -import io.requery.Key; -import io.requery.ManyToOne; -import io.requery.Table; - -@Entity -@Table(name = "msg_payloads") -public abstract class AbstractMessagePayloadModel { - - @Key @Generated - long id; - - @ManyToOne - MessagePayloadContainerModel payloadContainer; - - @Column - String body; - - @Column(nullable = false) - MessageContentType type; -} diff --git a/data/src/main/java/org/mercury_im/messenger/data/repository/RxMessageRepository.java b/data/src/main/java/org/mercury_im/messenger/data/repository/RxMessageRepository.java index 54f5989..946e1c7 100644 --- a/data/src/main/java/org/mercury_im/messenger/data/repository/RxMessageRepository.java +++ b/data/src/main/java/org/mercury_im/messenger/data/repository/RxMessageRepository.java @@ -4,10 +4,6 @@ import org.mercury_im.messenger.core.data.repository.MessageRepository; import org.mercury_im.messenger.data.mapping.DirectChatMapping; import org.mercury_im.messenger.data.mapping.GroupChatMapping; import org.mercury_im.messenger.data.mapping.MessageMapping; -import org.mercury_im.messenger.data.model.DirectChatModel; -import org.mercury_im.messenger.data.model.DirectMessagesRelation; -import org.mercury_im.messenger.data.model.GroupChatModel; -import org.mercury_im.messenger.data.model.GroupMessagesRelation; import org.mercury_im.messenger.data.model.MessageModel; import org.mercury_im.messenger.data.repository.dao.DirectChatDao; import org.mercury_im.messenger.data.repository.dao.GroupChatDao; @@ -60,9 +56,12 @@ public class RxMessageRepository public Single insertMessage(DirectChat chat, Message message) { return directChatDao.get(chat.getId()).maybe() .switchIfEmpty(directChatDao.insert(directChatMapping.toModel(chat))) - .map(chatModel -> toRelation(chatModel, messageMapping.toModel(message))) - .flatMap(data()::insert) - .map(DirectMessagesRelation::getMessage) + .map(chatModel -> { + MessageModel messageModel = messageMapping.toModel(message); + messageModel.setChatId(chat.getId()); + return messageModel; + }) + .flatMap(messageModel -> data().upsert(messageModel)) .map(messageModel -> messageMapping.toEntity(messageModel, message)); } @@ -70,9 +69,12 @@ public class RxMessageRepository public Single insertMessage(GroupChat chat, Message message) { return groupChatDao.get(chat.getId()).maybe() .switchIfEmpty(groupChatDao.insert(groupChatMapping.toModel(chat))) - .map(chatModel -> toRelation(chatModel, messageMapping.toModel(message))) - .flatMap(data()::insert) - .map(GroupMessagesRelation::getMessage) + .map(chatModel -> { + MessageModel messageModel = messageMapping.toModel(message); + messageModel.setChatId(chat.getId()); + return messageModel; + }) + .flatMap(data()::upsert) .map(messageModel -> messageMapping.toEntity(messageModel, message)); } @@ -80,9 +82,6 @@ public class RxMessageRepository public Observable> observeMessages(DirectChat chat) { return data().select(MessageModel.class) .from(MessageModel.class) - .join(DirectMessagesRelation.class) - .on(DirectMessagesRelation.MESSAGE_ID.eq(MessageModel.ID)) - .where(DirectMessagesRelation.CHAT_ID.eq(chat.getId())) .get().observableResult() .map(ResultDelegate::toList) .map(this::messageModelsToEntities); @@ -100,9 +99,6 @@ public class RxMessageRepository public Observable> observeMessages(GroupChat chat) { return data().select(MessageModel.class) .from(MessageModel.class) - .join(GroupMessagesRelation.class) - .on(GroupMessagesRelation.MESSAGE_ID.eq(MessageModel.ID)) - .where(GroupMessagesRelation.CHAT_ID.eq(chat.getId())) .get().observableResult() .map(ResultDelegate::toList) .map(this::messageModelsToEntities); @@ -123,11 +119,9 @@ public class RxMessageRepository return data().select(MessageModel.class) .from(MessageModel.class) - .join(DirectMessagesRelation.class) - .on(DirectMessagesRelation.MESSAGE_ID.eq(MessageModel.ID)) - .where(MessageModel.BODY.eq(body)) - .and(DirectMessagesRelation.CHAT_ID.eq(chat.getId())) + .and(MessageModel.SENDER.eq(chat.getPeer().getAddress()) + .or(MessageModel.RECIPIENT.eq(chat.getPeer().getAddress()))) .get().observableResult() .map(ResultDelegate::toList) .map(this::messageModelsToEntities); @@ -138,11 +132,8 @@ public class RxMessageRepository return data().select(MessageModel.class) .from(MessageModel.class) - .join(GroupMessagesRelation.class) - .on(GroupMessagesRelation.MESSAGE_ID.eq(MessageModel.ID)) - .where(MessageModel.BODY.eq(body)) - .and(GroupMessagesRelation.CHAT_ID.eq(chat.getId())) + .and(MessageModel.SENDER.eq(chat.getRoomName())) .get().observableResult() .map(ResultDelegate::toList) .map(this::messageModelsToEntities); @@ -173,20 +164,6 @@ public class RxMessageRepository .get().single().ignoreElement(); } - private DirectMessagesRelation toRelation(DirectChatModel chat, MessageModel message) { - DirectMessagesRelation relation = new DirectMessagesRelation(); - relation.setChat(chat); - relation.setMessage(message); - return relation; - } - - private GroupMessagesRelation toRelation(GroupChatModel chat, MessageModel message) { - GroupMessagesRelation relation = new GroupMessagesRelation(); - relation.setChat(chat); - relation.setMessage(message); - return relation; - } - private List messageModelsToEntities(List models) { List entities = new ArrayList<>(models.size()); for (MessageModel model : models) { diff --git a/data/src/main/java/org/mercury_im/messenger/data/repository/RxPeerRepository.java b/data/src/main/java/org/mercury_im/messenger/data/repository/RxPeerRepository.java index 35309b8..b303485 100644 --- a/data/src/main/java/org/mercury_im/messenger/data/repository/RxPeerRepository.java +++ b/data/src/main/java/org/mercury_im/messenger/data/repository/RxPeerRepository.java @@ -88,14 +88,14 @@ public class RxPeerRepository @Override public Single getOrCreatePeer(Account account, String address) { return getPeerByAddress(account, address) - .switchIfEmpty(Single - .just(new Peer()) - .map(peer -> { - peer.setAccount(account); - peer.setAddress(address); - return peer; - }) - .flatMap(this::insertPeer)); + .switchIfEmpty( + Single.just(new Peer()) + .map(peer -> { + peer.setAccount(account); + peer.setAddress(address); + return peer; + }) + .flatMap(this::upsertPeer)); } @Override diff --git a/data/src/main/java/org/mercury_im/messenger/data/repository/dao/MessageDao.java b/data/src/main/java/org/mercury_im/messenger/data/repository/dao/MessageDao.java index c9c6a5f..8c7815c 100644 --- a/data/src/main/java/org/mercury_im/messenger/data/repository/dao/MessageDao.java +++ b/data/src/main/java/org/mercury_im/messenger/data/repository/dao/MessageDao.java @@ -1,13 +1,13 @@ package org.mercury_im.messenger.data.repository.dao; import org.mercury_im.messenger.data.model.DirectChatModel; -import org.mercury_im.messenger.data.model.DirectMessagesRelation; import org.mercury_im.messenger.data.model.GroupChatModel; -import org.mercury_im.messenger.data.model.GroupMessagesRelation; import org.mercury_im.messenger.data.model.MessageModel; import java.util.UUID; +import javax.inject.Inject; + import io.reactivex.Single; import io.requery.Persistable; import io.requery.reactivex.ReactiveEntityStore; @@ -18,6 +18,7 @@ public class MessageDao extends RequeryDao { private final DirectChatDao directChatDao; private final GroupChatDao groupChatDao; + @Inject public MessageDao(ReactiveEntityStore data) { super(data); this.directChatDao = new DirectChatDao(data); @@ -33,20 +34,4 @@ public class MessageDao extends RequeryDao { .where(MessageModel.ID.eq(messageId)) .get(); } - - - - private DirectMessagesRelation toRelation(DirectChatModel chat, MessageModel message) { - DirectMessagesRelation relation = new DirectMessagesRelation(); - relation.setChat(chat); - relation.setMessage(message); - return relation; - } - - private GroupMessagesRelation toRelation(GroupChatModel chat, MessageModel message) { - GroupMessagesRelation relation = new GroupMessagesRelation(); - relation.setChat(chat); - relation.setMessage(message); - return relation; - } } diff --git a/domain/src/main/java/org/mercury_im/messenger/core/Messenger.java b/domain/src/main/java/org/mercury_im/messenger/core/Messenger.java index bc43826..88b8f2a 100644 --- a/domain/src/main/java/org/mercury_im/messenger/core/Messenger.java +++ b/domain/src/main/java/org/mercury_im/messenger/core/Messenger.java @@ -44,20 +44,12 @@ public class Messenger { this.repositories = repositories; this.connectionManager = connectionManager; this.schedulers = schedulers; - performInitialLogin(); } public MercuryConnectionManager getConnectionManager() { return connectionManager; } - public void performInitialLogin() { - LOGGER.log(Level.INFO, "Perform initial login."); - disposable.add(repositories.getAccountRepository().observeAllAccounts().firstOrError() - .subscribeOn(schedulers.getIoScheduler()) - .subscribe(connectionManager::doRegisterConnections)); - } - public Completable addContact(UUID accountId, String contactAddress) { return Completable.fromAction(() -> doAddContact(accountId, contactAddress)); } diff --git a/domain/src/main/java/org/mercury_im/messenger/core/crypto/MercuryOpenPgpManager.java b/domain/src/main/java/org/mercury_im/messenger/core/crypto/MercuryOpenPgpManager.java index cbe3c04..db84d04 100644 --- a/domain/src/main/java/org/mercury_im/messenger/core/crypto/MercuryOpenPgpManager.java +++ b/domain/src/main/java/org/mercury_im/messenger/core/crypto/MercuryOpenPgpManager.java @@ -8,11 +8,14 @@ import org.jivesoftware.smackx.ox.crypto.PainlessOpenPgpProvider; import org.jivesoftware.smackx.ox.exception.InvalidBackupCodeException; import org.jivesoftware.smackx.ox.exception.NoBackupFoundException; import org.jivesoftware.smackx.ox.store.definition.OpenPgpStore; +import org.jivesoftware.smackx.ox.util.SecretKeyBackupHelper; import org.jivesoftware.smackx.ox_im.OXInstantMessagingManager; import org.jivesoftware.smackx.pubsub.PubSubException; import org.mercury_im.messenger.core.SchedulersFacade; import org.mercury_im.messenger.core.data.repository.OpenPgpRepository; +import org.mercury_im.messenger.core.data.repository.Repositories; import org.mercury_im.messenger.core.store.crypto.MercuryOpenPgpStore; +import org.mercury_im.messenger.core.store.message.MercuryMessageStore; import org.mercury_im.messenger.core.xmpp.MercuryConnection; import java.util.logging.Level; @@ -24,13 +27,17 @@ public class MercuryOpenPgpManager { private static final Logger LOGGER = Logger.getLogger(MercuryOpenPgpManager.class.getName()); + private final Repositories repositories; private final OpenPgpRepository openPgpRepository; private final SchedulersFacade schedulers; @Inject - public MercuryOpenPgpManager(OpenPgpRepository openPgpRepository, SchedulersFacade schedulers) { + public MercuryOpenPgpManager(OpenPgpRepository openPgpRepository, + SchedulersFacade schedulers, + Repositories repositories) { this.openPgpRepository = openPgpRepository; this.schedulers = schedulers; + this.repositories = repositories; } public void initialize(MercuryConnection connection) { @@ -51,9 +58,12 @@ public class MercuryOpenPgpManager { private void setup(MercuryConnection connection) { OpenPgpStore store = new MercuryOpenPgpStore(connection.getAccountId(), openPgpRepository, schedulers); OpenPgpProvider provider = new PainlessOpenPgpProvider(store); + OpenPgpManager oxManager = OpenPgpManager.getInstanceFor(connection.getConnection()); + oxManager.setOpenPgpProvider(provider); + SecretKeyBackupHelper.setBackupCodeGenerator( + () -> "71ZA-Y416-UA7A-7NCE-3SNM-88EF" + ); try { - OpenPgpManager oxManager = OpenPgpManager.getInstanceFor(connection.getConnection()); - oxManager.setOpenPgpProvider(provider); if (!oxManager.hasSecretKeysAvailable()) { try { oxManager.restoreSecretKeyServerBackup( @@ -71,7 +81,9 @@ public class MercuryOpenPgpManager { } oxManager.announceSupportAndPublish(); OXInstantMessagingManager oximManager = OXInstantMessagingManager.getInstanceFor(connection.getConnection()); + oximManager.addOxMessageListener(new MercuryMessageStore(connection.getAccount(), repositories.getPeerRepository(), repositories.getDirectChatRepository(), repositories.getMessageRepository(), schedulers)); oximManager.announceSupportForOxInstantMessaging(); + oxManager.stopMetadataListener(); } catch (Exception e) { e.printStackTrace(); } diff --git a/domain/src/main/java/org/mercury_im/messenger/core/store/message/MercuryMessageStore.java b/domain/src/main/java/org/mercury_im/messenger/core/store/message/MercuryMessageStore.java index b95aea8..7aa9010 100644 --- a/domain/src/main/java/org/mercury_im/messenger/core/store/message/MercuryMessageStore.java +++ b/domain/src/main/java/org/mercury_im/messenger/core/store/message/MercuryMessageStore.java @@ -4,6 +4,9 @@ import org.jivesoftware.smack.chat2.IncomingChatMessageListener; import org.jivesoftware.smack.chat2.OutgoingChatMessageListener; import org.jivesoftware.smack.packet.MessageBuilder; import org.jivesoftware.smackx.delay.packet.DelayInformation; +import org.jivesoftware.smackx.ox.OpenPgpContact; +import org.jivesoftware.smackx.ox.element.SigncryptElement; +import org.jivesoftware.smackx.ox_im.OxMessageListener; import org.jxmpp.jid.EntityBareJid; import org.mercury_im.messenger.core.SchedulersFacade; import org.mercury_im.messenger.core.data.repository.DirectChatRepository; @@ -12,6 +15,7 @@ import org.mercury_im.messenger.core.data.repository.PeerRepository; import org.mercury_im.messenger.entity.Account; import org.mercury_im.messenger.entity.message.Message; import org.mercury_im.messenger.entity.message.MessageDirection; +import org.pgpainless.decryption_verification.OpenPgpMetadata; import java.util.Date; import java.util.logging.Level; @@ -24,7 +28,7 @@ import io.reactivex.disposables.CompositeDisposable; import io.reactivex.disposables.Disposable; @Singleton -public class MercuryMessageStore implements IncomingChatMessageListener, OutgoingChatMessageListener { +public class MercuryMessageStore implements IncomingChatMessageListener, OutgoingChatMessageListener, OxMessageListener { private static final Logger LOGGER = Logger.getLogger(MercuryMessageStore.class.getName()); @@ -88,4 +92,23 @@ public class MercuryMessageStore implements IncomingChatMessageListener, Outgoin .subscribeOn(schedulers.getIoScheduler()) .subscribe(m -> LOGGER.log(Level.INFO, "Message written"), e -> LOGGER.log(Level.SEVERE, "Error: ", e)); } + + @Override + public void newIncomingOxMessage(OpenPgpContact contact, + org.jivesoftware.smack.packet.Message smackMessage, + SigncryptElement decryptedPayload, + OpenPgpMetadata metadata) { + Message message = new Message(); + message.setDirection(MessageDirection.incoming); + DelayInformation delayInformation = DelayInformation.from(smackMessage); + message.setTimestamp(delayInformation != null ? delayInformation.getStamp() : new Date()); + message.setSender(contact.getJid().toString()); + message.setRecipient(smackMessage.getTo().asBareJid().toString()); + org.jivesoftware.smack.packet.Message.Body body = decryptedPayload.getExtension(org.jivesoftware.smack.packet.Message.Body.ELEMENT, + org.jivesoftware.smack.packet.Message.Body.NAMESPACE); + if (body != null) { + message.setBody(body.getMessage()); + } + disposable.add(writeMessageToStore(contact.getJid().toString(), message)); + } } diff --git a/domain/src/main/java/org/mercury_im/messenger/core/xmpp/CsiManager.java b/domain/src/main/java/org/mercury_im/messenger/core/xmpp/CsiManager.java index 3881ba0..bf8d741 100644 --- a/domain/src/main/java/org/mercury_im/messenger/core/xmpp/CsiManager.java +++ b/domain/src/main/java/org/mercury_im/messenger/core/xmpp/CsiManager.java @@ -34,6 +34,9 @@ public class CsiManager implements ClientStateListener { } private void tryCsiActive(MercuryConnection connection) { + if (!connection.getConnection().isAuthenticated()) { + return; + } try { ClientStateIndicationManager.active(connection.getConnection()); } catch (SmackException.NotConnectedException | InterruptedException | IllegalArgumentException e) { @@ -42,6 +45,9 @@ public class CsiManager implements ClientStateListener { } private void tryCsiInactive(MercuryConnection connection) { + if (!connection.getConnection().isAuthenticated()) { + return; + } try { ClientStateIndicationManager.inactive(connection.getConnection()); } catch (SmackException.NotConnectedException | InterruptedException | IllegalArgumentException e) { diff --git a/domain/src/main/java/org/mercury_im/messenger/core/xmpp/MercuryConnection.java b/domain/src/main/java/org/mercury_im/messenger/core/xmpp/MercuryConnection.java index 8f56dce..d7ba3c5 100644 --- a/domain/src/main/java/org/mercury_im/messenger/core/xmpp/MercuryConnection.java +++ b/domain/src/main/java/org/mercury_im/messenger/core/xmpp/MercuryConnection.java @@ -54,9 +54,6 @@ public class MercuryConnection { } public Completable connect() { - if (getConnection().isConnected()) { - return Completable.complete(); - } return Completable.fromAction(this::doConnect) .doOnError(error -> LOGGER.log(Level.WARNING, "Connection error for account " + account, error)); } @@ -64,7 +61,11 @@ public class MercuryConnection { private void doConnect() throws ServerUnreachableException { state.onNext(state.getValue().withConnectivity(ConnectivityState.connecting)); AbstractXMPPConnection connection = (AbstractXMPPConnection) getConnection(); + if (connection.isConnected()) { + return; + } try { + LOGGER.log(Level.INFO, "Connected!"); connection.connect(); } catch (SmackException.EndpointConnectionException e) { connection.disconnect(); @@ -75,14 +76,14 @@ public class MercuryConnection { } public Completable login() { - if (getConnection().isAuthenticated()) { - return Completable.complete(); - } return Completable.fromAction(this::doLogin) .doOnError(error -> LOGGER.log(Level.WARNING, "Login error for account " + account, error)); } private void doLogin() throws InvalidCredentialsException { + if (connection.isAuthenticated()) { + return; + } try { ((AbstractXMPPConnection) getConnection()).login(); } catch (SASLErrorException e) { diff --git a/libs/Smack b/libs/Smack index 58ce1dd..218403c 160000 --- a/libs/Smack +++ b/libs/Smack @@ -1 +1 @@ -Subproject commit 58ce1dd62f11b40a7063802fa079d827c90b0f84 +Subproject commit 218403c362d306d38ea791d528f165fc64eb8189