mirror of
https://github.com/oxen-io/session-android.git
synced 2025-04-20 07:31:29 +00:00
Move session restore prompt from message level to conversation level.
This commit is contained in:
parent
0caeb3a109
commit
97ffea040f
@ -51,6 +51,13 @@
|
|||||||
android:inflatedId="@+id/unverified_banner"
|
android:inflatedId="@+id/unverified_banner"
|
||||||
android:layout="@layout/conversation_activity_unverified_banner_stub" />
|
android:layout="@layout/conversation_activity_unverified_banner_stub" />
|
||||||
|
|
||||||
|
<ViewStub
|
||||||
|
android:id="@+id/session_restore_banner_stub"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:inflatedId="@+id/session_restore_banner"
|
||||||
|
android:layout="@layout/conversation_activity_unverified_banner_stub" />
|
||||||
|
|
||||||
<ViewStub
|
<ViewStub
|
||||||
android:id="@+id/reminder_stub"
|
android:id="@+id/reminder_stub"
|
||||||
android:layout_width="match_parent"
|
android:layout_width="match_parent"
|
||||||
|
@ -74,15 +74,6 @@
|
|||||||
android:textColor="?conversation_item_update_text_color"
|
android:textColor="?conversation_item_update_text_color"
|
||||||
tools:text="30 min ago" />
|
tools:text="30 min ago" />
|
||||||
|
|
||||||
<Button
|
|
||||||
android:id="@+id/conversation_update_button"
|
|
||||||
style="@style/Button.Borderless"
|
|
||||||
android:layout_width="match_parent"
|
|
||||||
android:layout_height="wrap_content"
|
|
||||||
android:layout_marginTop="8dp"
|
|
||||||
android:text="Button"
|
|
||||||
android:visibility="gone" />
|
|
||||||
|
|
||||||
</LinearLayout>
|
</LinearLayout>
|
||||||
|
|
||||||
</org.thoughtcrime.securesms.conversation.ConversationUpdateItem>
|
</org.thoughtcrime.securesms.conversation.ConversationUpdateItem>
|
||||||
|
66
res/layout/session_restore_banner.xml
Normal file
66
res/layout/session_restore_banner.xml
Normal file
@ -0,0 +1,66 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||||
|
xmlns:tools="http://schemas.android.com/tools"
|
||||||
|
android:id="@+id/session_restore_banner"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:background="@color/core_grey_60"
|
||||||
|
android:focusable="true"
|
||||||
|
android:nextFocusDown="@+id/cancel"
|
||||||
|
android:orientation="vertical"
|
||||||
|
android:paddingStart="8dp"
|
||||||
|
android:paddingTop="24dp"
|
||||||
|
android:paddingEnd="8dp"
|
||||||
|
android:paddingBottom="8dp"
|
||||||
|
android:visibility="gone"
|
||||||
|
tools:visibility="visible">
|
||||||
|
|
||||||
|
<TextView
|
||||||
|
android:id="@+id/restoreTitle"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:layout_marginStart="8dp"
|
||||||
|
android:layout_marginEnd="8dp"
|
||||||
|
android:layout_marginBottom="4dp"
|
||||||
|
android:textColor="@color/white"
|
||||||
|
android:textSize="18sp"
|
||||||
|
tools:text="@string/session_restore_banner_title" />
|
||||||
|
|
||||||
|
<TextView
|
||||||
|
android:id="@+id/restoreText"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:layout_marginStart="8dp"
|
||||||
|
android:layout_marginEnd="8dp"
|
||||||
|
android:fontFamily="sans-serif-light"
|
||||||
|
android:textColor="@color/white"
|
||||||
|
android:textSize="16sp"
|
||||||
|
tools:text="@string/session_restore_banner_message" />
|
||||||
|
|
||||||
|
<LinearLayout
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:layout_marginTop="12dp"
|
||||||
|
android:gravity="right"
|
||||||
|
android:orientation="horizontal">
|
||||||
|
|
||||||
|
<Button
|
||||||
|
android:id="@+id/dismissButton"
|
||||||
|
style="@style/Widget.AppCompat.Button.Borderless"
|
||||||
|
android:layout_width="wrap_content"
|
||||||
|
android:layout_height="36dp"
|
||||||
|
android:text="@string/session_restore_banner_dismiss_button_title" />
|
||||||
|
|
||||||
|
<android.support.v4.widget.Space
|
||||||
|
android:layout_width="8dp"
|
||||||
|
android:layout_height="wrap_content" />
|
||||||
|
|
||||||
|
<Button
|
||||||
|
android:id="@+id/restoreButton"
|
||||||
|
style="@style/Button.Borderless"
|
||||||
|
android:layout_width="wrap_content"
|
||||||
|
android:layout_height="36dp"
|
||||||
|
android:text="@string/session_restore_banner_restore_button_title" />
|
||||||
|
</LinearLayout>
|
||||||
|
|
||||||
|
</LinearLayout>
|
@ -735,9 +735,7 @@
|
|||||||
<!-- MessageDisplayHelper -->
|
<!-- MessageDisplayHelper -->
|
||||||
<string name="MessageDisplayHelper_bad_encrypted_message">Bad encrypted message</string>
|
<string name="MessageDisplayHelper_bad_encrypted_message">Bad encrypted message</string>
|
||||||
<string name="MessageDisplayHelper_message_encrypted_for_non_existing_session">Message encrypted for non-existing session</string>
|
<string name="MessageDisplayHelper_message_encrypted_for_non_existing_session">Message encrypted for non-existing session</string>
|
||||||
<string name="MessageRecord_session_restore_required">Could not decrypt an incoming message. Would you like to start a new session with %s?</string>
|
|
||||||
<string name="MessageRecord_session_restore_sent">You have sent a session restore request to %s</string>
|
<string name="MessageRecord_session_restore_sent">You have sent a session restore request to %s</string>
|
||||||
<string name="MessageRecord_session_restore_button_title">Restore session</string>
|
|
||||||
|
|
||||||
<!-- MmsMessageRecord -->
|
<!-- MmsMessageRecord -->
|
||||||
<string name="MmsMessageRecord_bad_encrypted_mms_message">Bad encrypted MMS message</string>
|
<string name="MmsMessageRecord_bad_encrypted_mms_message">Bad encrypted MMS message</string>
|
||||||
@ -1654,5 +1652,9 @@
|
|||||||
<!-- Device unlink dialog -->
|
<!-- Device unlink dialog -->
|
||||||
<string name="dialog_device_unlink_title">Device unlinked</string>
|
<string name="dialog_device_unlink_title">Device unlinked</string>
|
||||||
<string name="dialog_device_unlink_message">This device has been successfully unlinked</string>
|
<string name="dialog_device_unlink_message">This device has been successfully unlinked</string>
|
||||||
|
<!-- Session restore banner -->
|
||||||
|
<string name="session_restore_banner_title">Could not decrypt an incoming message.</string>
|
||||||
|
<string name="session_restore_banner_message">Would you like to start a new session with %s?</string>
|
||||||
|
<string name="session_restore_banner_restore_button_title">Restore session</string>
|
||||||
|
<string name="session_restore_banner_dismiss_button_title">Dismiss</string>
|
||||||
</resources>
|
</resources>
|
||||||
|
@ -139,6 +139,7 @@ import org.thoughtcrime.securesms.database.MessagingDatabase.MarkedMessageInfo;
|
|||||||
import org.thoughtcrime.securesms.database.MmsSmsColumns.Types;
|
import org.thoughtcrime.securesms.database.MmsSmsColumns.Types;
|
||||||
import org.thoughtcrime.securesms.database.RecipientDatabase;
|
import org.thoughtcrime.securesms.database.RecipientDatabase;
|
||||||
import org.thoughtcrime.securesms.database.RecipientDatabase.RegisteredState;
|
import org.thoughtcrime.securesms.database.RecipientDatabase.RegisteredState;
|
||||||
|
import org.thoughtcrime.securesms.database.SmsDatabase;
|
||||||
import org.thoughtcrime.securesms.database.ThreadDatabase;
|
import org.thoughtcrime.securesms.database.ThreadDatabase;
|
||||||
import org.thoughtcrime.securesms.database.identity.IdentityRecordList;
|
import org.thoughtcrime.securesms.database.identity.IdentityRecordList;
|
||||||
import org.thoughtcrime.securesms.database.model.MessageRecord;
|
import org.thoughtcrime.securesms.database.model.MessageRecord;
|
||||||
@ -154,7 +155,6 @@ import org.thoughtcrime.securesms.linkpreview.LinkPreviewRepository;
|
|||||||
import org.thoughtcrime.securesms.linkpreview.LinkPreviewUtil;
|
import org.thoughtcrime.securesms.linkpreview.LinkPreviewUtil;
|
||||||
import org.thoughtcrime.securesms.linkpreview.LinkPreviewViewModel;
|
import org.thoughtcrime.securesms.linkpreview.LinkPreviewViewModel;
|
||||||
import org.thoughtcrime.securesms.logging.Log;
|
import org.thoughtcrime.securesms.logging.Log;
|
||||||
import org.thoughtcrime.securesms.loki.ConversationUpdateItemViewDelegate;
|
|
||||||
import org.thoughtcrime.securesms.loki.FriendRequestViewDelegate;
|
import org.thoughtcrime.securesms.loki.FriendRequestViewDelegate;
|
||||||
import org.thoughtcrime.securesms.loki.LokiAPIUtilities;
|
import org.thoughtcrime.securesms.loki.LokiAPIUtilities;
|
||||||
import org.thoughtcrime.securesms.loki.LokiThreadDatabase;
|
import org.thoughtcrime.securesms.loki.LokiThreadDatabase;
|
||||||
@ -163,6 +163,7 @@ import org.thoughtcrime.securesms.loki.LokiThreadDatabaseDelegate;
|
|||||||
import org.thoughtcrime.securesms.loki.LokiUserDatabase;
|
import org.thoughtcrime.securesms.loki.LokiUserDatabase;
|
||||||
import org.thoughtcrime.securesms.loki.MentionCandidateSelectionView;
|
import org.thoughtcrime.securesms.loki.MentionCandidateSelectionView;
|
||||||
import org.thoughtcrime.securesms.loki.MultiDeviceUtilities;
|
import org.thoughtcrime.securesms.loki.MultiDeviceUtilities;
|
||||||
|
import org.thoughtcrime.securesms.loki.SessionRestoreBannerView;
|
||||||
import org.thoughtcrime.securesms.mediasend.Media;
|
import org.thoughtcrime.securesms.mediasend.Media;
|
||||||
import org.thoughtcrime.securesms.mediasend.MediaSendActivity;
|
import org.thoughtcrime.securesms.mediasend.MediaSendActivity;
|
||||||
import org.thoughtcrime.securesms.mms.AttachmentManager;
|
import org.thoughtcrime.securesms.mms.AttachmentManager;
|
||||||
@ -242,6 +243,7 @@ import java.util.Date;
|
|||||||
import java.util.LinkedList;
|
import java.util.LinkedList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
|
import java.util.Set;
|
||||||
import java.util.concurrent.ExecutionException;
|
import java.util.concurrent.ExecutionException;
|
||||||
import java.util.concurrent.atomic.AtomicBoolean;
|
import java.util.concurrent.atomic.AtomicBoolean;
|
||||||
import java.util.concurrent.atomic.AtomicInteger;
|
import java.util.concurrent.atomic.AtomicInteger;
|
||||||
@ -249,7 +251,6 @@ import java.util.concurrent.atomic.AtomicInteger;
|
|||||||
import kotlin.Unit;
|
import kotlin.Unit;
|
||||||
import network.loki.messenger.R;
|
import network.loki.messenger.R;
|
||||||
|
|
||||||
import static nl.komponents.kovenant.KovenantApi.task;
|
|
||||||
import static org.thoughtcrime.securesms.TransportOption.Type;
|
import static org.thoughtcrime.securesms.TransportOption.Type;
|
||||||
import static org.thoughtcrime.securesms.database.GroupDatabase.GroupRecord;
|
import static org.thoughtcrime.securesms.database.GroupDatabase.GroupRecord;
|
||||||
import static org.whispersystems.libsignal.SessionCipher.SESSION_LOCK;
|
import static org.whispersystems.libsignal.SessionCipher.SESSION_LOCK;
|
||||||
@ -273,8 +274,7 @@ public class ConversationActivity extends PassphraseRequiredActionBarActivity
|
|||||||
ConversationSearchBottomBar.EventListener,
|
ConversationSearchBottomBar.EventListener,
|
||||||
StickerKeyboardProvider.StickerEventListener,
|
StickerKeyboardProvider.StickerEventListener,
|
||||||
LokiThreadDatabaseDelegate,
|
LokiThreadDatabaseDelegate,
|
||||||
FriendRequestViewDelegate,
|
FriendRequestViewDelegate
|
||||||
ConversationUpdateItemViewDelegate
|
|
||||||
{
|
{
|
||||||
private static final String TAG = ConversationActivity.class.getSimpleName();
|
private static final String TAG = ConversationActivity.class.getSimpleName();
|
||||||
|
|
||||||
@ -358,6 +358,9 @@ public class ConversationActivity extends PassphraseRequiredActionBarActivity
|
|||||||
// Multi Device
|
// Multi Device
|
||||||
private boolean isFriendsWithAnyDevice = false;
|
private boolean isFriendsWithAnyDevice = false;
|
||||||
|
|
||||||
|
// Restoration
|
||||||
|
protected Stub<SessionRestoreBannerView> sessionRestoreBannerView;
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected void onPreCreate() {
|
protected void onPreCreate() {
|
||||||
dynamicTheme.onCreate(this);
|
dynamicTheme.onCreate(this);
|
||||||
@ -378,7 +381,6 @@ public class ConversationActivity extends PassphraseRequiredActionBarActivity
|
|||||||
|
|
||||||
fragment = initFragment(R.id.fragment_content, new ConversationFragment(), dynamicLanguage.getCurrentLocale());
|
fragment = initFragment(R.id.fragment_content, new ConversationFragment(), dynamicLanguage.getCurrentLocale());
|
||||||
fragment.friendRequestViewDelegate = this;
|
fragment.friendRequestViewDelegate = this;
|
||||||
fragment.conversationUpdateItemViewDelegate = this;
|
|
||||||
|
|
||||||
initializeReceivers();
|
initializeReceivers();
|
||||||
initializeActionBar();
|
initializeActionBar();
|
||||||
@ -1492,6 +1494,16 @@ public class ConversationActivity extends PassphraseRequiredActionBarActivity
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected void updateSessionRestoreBanner() {
|
||||||
|
Set<String> devices = DatabaseFactory.getLokiThreadDatabase(this).getSessionRestoreDevices(threadId);
|
||||||
|
SessionRestoreBannerView view = sessionRestoreBannerView.get();
|
||||||
|
if (devices.size() > 0) {
|
||||||
|
view.show();
|
||||||
|
} else {
|
||||||
|
view.hide();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void updateDefaultSubscriptionId(Optional<Integer> defaultSubscriptionId) {
|
private void updateDefaultSubscriptionId(Optional<Integer> defaultSubscriptionId) {
|
||||||
Log.i(TAG, "updateDefaultSubscriptionId(" + defaultSubscriptionId.orNull() + ")");
|
Log.i(TAG, "updateDefaultSubscriptionId(" + defaultSubscriptionId.orNull() + ")");
|
||||||
sendButton.setDefaultSubscriptionId(defaultSubscriptionId);
|
sendButton.setDefaultSubscriptionId(defaultSubscriptionId);
|
||||||
@ -1588,6 +1600,18 @@ public class ConversationActivity extends PassphraseRequiredActionBarActivity
|
|||||||
inputPanel = ViewUtil.findById(this, R.id.bottom_panel);
|
inputPanel = ViewUtil.findById(this, R.id.bottom_panel);
|
||||||
searchNav = ViewUtil.findById(this, R.id.conversation_search_nav);
|
searchNav = ViewUtil.findById(this, R.id.conversation_search_nav);
|
||||||
mentionCandidateSelectionView = ViewUtil.findById(this, R.id.userSelectionView);
|
mentionCandidateSelectionView = ViewUtil.findById(this, R.id.userSelectionView);
|
||||||
|
sessionRestoreBannerView = ViewUtil.findStubById(this, R.id.session_restore_banner_stub);
|
||||||
|
sessionRestoreBannerView.get().setRecipient(recipient);
|
||||||
|
sessionRestoreBannerView.get().setOnRestore(() -> {
|
||||||
|
this.restoreSession();
|
||||||
|
return Unit.INSTANCE;
|
||||||
|
});
|
||||||
|
sessionRestoreBannerView.get().setOnDismiss(() -> {
|
||||||
|
// TODO: Maybe silence for x minutes?
|
||||||
|
// TODO: Remove devices?
|
||||||
|
sessionRestoreBannerView.get().hide();
|
||||||
|
return Unit.INSTANCE;
|
||||||
|
});
|
||||||
|
|
||||||
ImageButton quickCameraToggle = ViewUtil.findById(this, R.id.quick_camera_toggle);
|
ImageButton quickCameraToggle = ViewUtil.findById(this, R.id.quick_camera_toggle);
|
||||||
ImageButton inlineAttachmentButton = ViewUtil.findById(this, R.id.inline_attachment_button);
|
ImageButton inlineAttachmentButton = ViewUtil.findById(this, R.id.inline_attachment_button);
|
||||||
@ -2206,6 +2230,13 @@ public class ConversationActivity extends PassphraseRequiredActionBarActivity
|
|||||||
this.updateInputPanel();
|
this.updateInputPanel();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void handleSessionRestoreDevicesChanged(long threadId) {
|
||||||
|
if (threadId == this.threadId) {
|
||||||
|
updateSessionRestoreBanner();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void updateInputPanel() {
|
private void updateInputPanel() {
|
||||||
/*
|
/*
|
||||||
isFriendsWithAnyDevice caches whether we are friends with any of the other users device.
|
isFriendsWithAnyDevice caches whether we are friends with any of the other users device.
|
||||||
@ -3083,14 +3114,19 @@ public class ConversationActivity extends PassphraseRequiredActionBarActivity
|
|||||||
}
|
}
|
||||||
// endregion
|
// endregion
|
||||||
|
|
||||||
@Override
|
public void restoreSession() {
|
||||||
public void updateItemButtonPressed(@NonNull MessageRecord messageRecord) {
|
|
||||||
// Loki - User clicked restore session
|
// Loki - User clicked restore session
|
||||||
Recipient recipient = messageRecord.getRecipient();
|
if (!recipient.isGroupRecipient()) {
|
||||||
if (!recipient.isGroupRecipient() && messageRecord.isNoRemoteSession() && !messageRecord.isLokiSessionRestoreSent()) {
|
LokiThreadDatabase lokiThreadDatabase = DatabaseFactory.getLokiThreadDatabase(this);
|
||||||
MessageSender.sendRestoreSessionMessage(this, recipient.getAddress().serialize());
|
SmsDatabase database = DatabaseFactory.getSmsDatabase(this);
|
||||||
DatabaseFactory.getSmsDatabase(this).markAsLokiSessionRestoreSent(messageRecord.id);
|
Set<String> devices = lokiThreadDatabase.getSessionRestoreDevices(threadId);
|
||||||
TextSecurePreferences.setShowingSessionRestorePrompt(this, messageRecord.getIndividualRecipient().getAddress().serialize(), false);
|
for (String device : devices) { MessageSender.sendRestoreSessionMessage(this, device); }
|
||||||
|
long messageId = database.insertMessageOutbox(threadId, new OutgoingTextMessage(recipient,"", 0, 0), false, System.currentTimeMillis(), null);
|
||||||
|
if (messageId > -1) {
|
||||||
|
database.markAsLokiSessionRestoreSent(messageId);
|
||||||
|
}
|
||||||
|
lokiThreadDatabase.removeAllSessionRestoreDevices(threadId);
|
||||||
|
updateSessionRestoreBanner();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -41,7 +41,6 @@ import org.thoughtcrime.securesms.database.MmsSmsDatabase;
|
|||||||
import org.thoughtcrime.securesms.database.model.MessageRecord;
|
import org.thoughtcrime.securesms.database.model.MessageRecord;
|
||||||
import org.thoughtcrime.securesms.database.model.MmsMessageRecord;
|
import org.thoughtcrime.securesms.database.model.MmsMessageRecord;
|
||||||
import org.thoughtcrime.securesms.logging.Log;
|
import org.thoughtcrime.securesms.logging.Log;
|
||||||
import org.thoughtcrime.securesms.loki.ConversationUpdateItemViewDelegate;
|
|
||||||
import org.thoughtcrime.securesms.loki.FriendRequestViewDelegate;
|
import org.thoughtcrime.securesms.loki.FriendRequestViewDelegate;
|
||||||
import org.thoughtcrime.securesms.mms.GlideRequests;
|
import org.thoughtcrime.securesms.mms.GlideRequests;
|
||||||
import org.thoughtcrime.securesms.mms.SlideDeck;
|
import org.thoughtcrime.securesms.mms.SlideDeck;
|
||||||
@ -109,7 +108,6 @@ public class ConversationAdapter <V extends View & BindableConversationItem>
|
|||||||
private String searchQuery;
|
private String searchQuery;
|
||||||
|
|
||||||
public FriendRequestViewDelegate friendRequestViewDelegate; // Loki
|
public FriendRequestViewDelegate friendRequestViewDelegate; // Loki
|
||||||
public ConversationUpdateItemViewDelegate conversationUpdateItemViewDelegate;
|
|
||||||
|
|
||||||
protected static class ViewHolder extends RecyclerView.ViewHolder {
|
protected static class ViewHolder extends RecyclerView.ViewHolder {
|
||||||
public <V extends View & BindableConversationItem> ViewHolder(final @NonNull V itemView) {
|
public <V extends View & BindableConversationItem> ViewHolder(final @NonNull V itemView) {
|
||||||
@ -206,9 +204,8 @@ public class ConversationAdapter <V extends View & BindableConversationItem>
|
|||||||
BindableConversationItem conversationItem = viewHolder.getView();
|
BindableConversationItem conversationItem = viewHolder.getView();
|
||||||
if (conversationItem instanceof ConversationItem) {
|
if (conversationItem instanceof ConversationItem) {
|
||||||
((ConversationItem)conversationItem).friendRequestViewDelegate = this.friendRequestViewDelegate;
|
((ConversationItem)conversationItem).friendRequestViewDelegate = this.friendRequestViewDelegate;
|
||||||
} else if (conversationItem instanceof ConversationUpdateItem) {
|
|
||||||
((ConversationUpdateItem)conversationItem).delegate = this.conversationUpdateItemViewDelegate;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
conversationItem.bind(messageRecord,
|
conversationItem.bind(messageRecord,
|
||||||
Optional.fromNullable(previousRecord),
|
Optional.fromNullable(previousRecord),
|
||||||
Optional.fromNullable(nextRecord),
|
Optional.fromNullable(nextRecord),
|
||||||
|
@ -79,7 +79,6 @@ import org.thoughtcrime.securesms.database.model.MmsMessageRecord;
|
|||||||
import org.thoughtcrime.securesms.jobs.DirectoryRefreshJob;
|
import org.thoughtcrime.securesms.jobs.DirectoryRefreshJob;
|
||||||
import org.thoughtcrime.securesms.linkpreview.LinkPreview;
|
import org.thoughtcrime.securesms.linkpreview.LinkPreview;
|
||||||
import org.thoughtcrime.securesms.logging.Log;
|
import org.thoughtcrime.securesms.logging.Log;
|
||||||
import org.thoughtcrime.securesms.loki.ConversationUpdateItemViewDelegate;
|
|
||||||
import org.thoughtcrime.securesms.loki.FriendRequestViewDelegate;
|
import org.thoughtcrime.securesms.loki.FriendRequestViewDelegate;
|
||||||
import org.thoughtcrime.securesms.longmessage.LongMessageActivity;
|
import org.thoughtcrime.securesms.longmessage.LongMessageActivity;
|
||||||
import org.thoughtcrime.securesms.mediasend.Media;
|
import org.thoughtcrime.securesms.mediasend.Media;
|
||||||
@ -153,7 +152,6 @@ public class ConversationFragment extends Fragment
|
|||||||
private View scrollToBottomButton;
|
private View scrollToBottomButton;
|
||||||
private TextView scrollDateHeader;
|
private TextView scrollDateHeader;
|
||||||
public FriendRequestViewDelegate friendRequestViewDelegate; // Loki
|
public FriendRequestViewDelegate friendRequestViewDelegate; // Loki
|
||||||
public ConversationUpdateItemViewDelegate conversationUpdateItemViewDelegate;
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onCreate(Bundle icicle) {
|
public void onCreate(Bundle icicle) {
|
||||||
@ -362,8 +360,7 @@ public class ConversationFragment extends Fragment
|
|||||||
if (messageRecord.isGroupAction() || messageRecord.isCallLog() ||
|
if (messageRecord.isGroupAction() || messageRecord.isCallLog() ||
|
||||||
messageRecord.isJoined() || messageRecord.isExpirationTimerUpdate() ||
|
messageRecord.isJoined() || messageRecord.isExpirationTimerUpdate() ||
|
||||||
messageRecord.isEndSession() || messageRecord.isIdentityUpdate() ||
|
messageRecord.isEndSession() || messageRecord.isIdentityUpdate() ||
|
||||||
messageRecord.isIdentityVerified() || messageRecord.isIdentityDefault() ||
|
messageRecord.isIdentityVerified() || messageRecord.isIdentityDefault() || messageRecord.isLokiSessionRestoreSent())
|
||||||
messageRecord.isNoRemoteSession() || messageRecord.isLokiSessionRestoreSent())
|
|
||||||
{
|
{
|
||||||
actionMessage = true;
|
actionMessage = true;
|
||||||
}
|
}
|
||||||
@ -708,7 +705,6 @@ public class ConversationFragment extends Fragment
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
adapter.friendRequestViewDelegate = this.friendRequestViewDelegate;
|
adapter.friendRequestViewDelegate = this.friendRequestViewDelegate;
|
||||||
adapter.conversationUpdateItemViewDelegate = this.conversationUpdateItemViewDelegate;
|
|
||||||
|
|
||||||
if (cursor.getCount() >= PARTIAL_CONVERSATION_LIMIT && loader.hasLimit()) {
|
if (cursor.getCount() >= PARTIAL_CONVERSATION_LIMIT && loader.hasLimit()) {
|
||||||
adapter.setFooterView(topLoadMoreView);
|
adapter.setFooterView(topLoadMoreView);
|
||||||
|
@ -87,7 +87,6 @@ import org.thoughtcrime.securesms.jobs.SmsSendJob;
|
|||||||
import org.thoughtcrime.securesms.linkpreview.LinkPreview;
|
import org.thoughtcrime.securesms.linkpreview.LinkPreview;
|
||||||
import org.thoughtcrime.securesms.linkpreview.LinkPreviewUtil;
|
import org.thoughtcrime.securesms.linkpreview.LinkPreviewUtil;
|
||||||
import org.thoughtcrime.securesms.logging.Log;
|
import org.thoughtcrime.securesms.logging.Log;
|
||||||
import org.thoughtcrime.securesms.loki.ConversationUpdateItemViewDelegate;
|
|
||||||
import org.thoughtcrime.securesms.loki.FriendRequestView;
|
import org.thoughtcrime.securesms.loki.FriendRequestView;
|
||||||
import org.thoughtcrime.securesms.loki.FriendRequestViewDelegate;
|
import org.thoughtcrime.securesms.loki.FriendRequestViewDelegate;
|
||||||
import org.thoughtcrime.securesms.loki.LokiMessageDatabase;
|
import org.thoughtcrime.securesms.loki.LokiMessageDatabase;
|
||||||
|
@ -9,7 +9,6 @@ import android.support.annotation.NonNull;
|
|||||||
import android.support.annotation.Nullable;
|
import android.support.annotation.Nullable;
|
||||||
import android.util.AttributeSet;
|
import android.util.AttributeSet;
|
||||||
import android.view.View;
|
import android.view.View;
|
||||||
import android.widget.Button;
|
|
||||||
import android.widget.ImageView;
|
import android.widget.ImageView;
|
||||||
import android.widget.LinearLayout;
|
import android.widget.LinearLayout;
|
||||||
import android.widget.TextView;
|
import android.widget.TextView;
|
||||||
@ -22,7 +21,6 @@ import org.thoughtcrime.securesms.database.IdentityDatabase;
|
|||||||
import org.thoughtcrime.securesms.database.IdentityDatabase.IdentityRecord;
|
import org.thoughtcrime.securesms.database.IdentityDatabase.IdentityRecord;
|
||||||
import org.thoughtcrime.securesms.database.model.MessageRecord;
|
import org.thoughtcrime.securesms.database.model.MessageRecord;
|
||||||
import org.thoughtcrime.securesms.logging.Log;
|
import org.thoughtcrime.securesms.logging.Log;
|
||||||
import org.thoughtcrime.securesms.loki.ConversationUpdateItemViewDelegate;
|
|
||||||
import org.thoughtcrime.securesms.mms.GlideRequests;
|
import org.thoughtcrime.securesms.mms.GlideRequests;
|
||||||
import org.thoughtcrime.securesms.recipients.Recipient;
|
import org.thoughtcrime.securesms.recipients.Recipient;
|
||||||
import org.thoughtcrime.securesms.recipients.RecipientModifiedListener;
|
import org.thoughtcrime.securesms.recipients.RecipientModifiedListener;
|
||||||
@ -49,13 +47,10 @@ public class ConversationUpdateItem extends LinearLayout
|
|||||||
private TextView title;
|
private TextView title;
|
||||||
private TextView body;
|
private TextView body;
|
||||||
private TextView date;
|
private TextView date;
|
||||||
private Button button;
|
|
||||||
private Recipient sender;
|
private Recipient sender;
|
||||||
private MessageRecord messageRecord;
|
private MessageRecord messageRecord;
|
||||||
private Locale locale;
|
private Locale locale;
|
||||||
|
|
||||||
public ConversationUpdateItemViewDelegate delegate;
|
|
||||||
|
|
||||||
public ConversationUpdateItem(Context context) {
|
public ConversationUpdateItem(Context context) {
|
||||||
super(context);
|
super(context);
|
||||||
}
|
}
|
||||||
@ -72,12 +67,6 @@ public class ConversationUpdateItem extends LinearLayout
|
|||||||
this.title = findViewById(R.id.conversation_update_title);
|
this.title = findViewById(R.id.conversation_update_title);
|
||||||
this.body = findViewById(R.id.conversation_update_body);
|
this.body = findViewById(R.id.conversation_update_body);
|
||||||
this.date = findViewById(R.id.conversation_update_date);
|
this.date = findViewById(R.id.conversation_update_date);
|
||||||
this.button = findViewById(R.id.conversation_update_button);
|
|
||||||
this.button.setOnClickListener(view -> {
|
|
||||||
if (delegate != null && messageRecord != null) {
|
|
||||||
delegate.updateItemButtonPressed(messageRecord);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
this.setOnClickListener(new InternalClickListener(null));
|
this.setOnClickListener(new InternalClickListener(null));
|
||||||
}
|
}
|
||||||
@ -123,8 +112,7 @@ public class ConversationUpdateItem extends LinearLayout
|
|||||||
else if (messageRecord.isIdentityUpdate()) setIdentityRecord(messageRecord);
|
else if (messageRecord.isIdentityUpdate()) setIdentityRecord(messageRecord);
|
||||||
else if (messageRecord.isIdentityVerified() ||
|
else if (messageRecord.isIdentityVerified() ||
|
||||||
messageRecord.isIdentityDefault()) setIdentityVerifyUpdate(messageRecord);
|
messageRecord.isIdentityDefault()) setIdentityVerifyUpdate(messageRecord);
|
||||||
else if (messageRecord.isNoRemoteSession() ||
|
else if (messageRecord.isLokiSessionRestoreSent()) setTextMessageRecord(messageRecord);
|
||||||
messageRecord.isLokiSessionRestoreSent()) setTextMessageRecord(messageRecord);
|
|
||||||
else throw new AssertionError("Neither group nor log nor joined.");
|
else throw new AssertionError("Neither group nor log nor joined.");
|
||||||
|
|
||||||
if (batchSelected.contains(messageRecord)) setSelected(true);
|
if (batchSelected.contains(messageRecord)) setSelected(true);
|
||||||
@ -217,12 +205,6 @@ public class ConversationUpdateItem extends LinearLayout
|
|||||||
|
|
||||||
private void setTextMessageRecord(MessageRecord messageRecord) {
|
private void setTextMessageRecord(MessageRecord messageRecord) {
|
||||||
body.setText(messageRecord.getDisplayBody(getContext()));
|
body.setText(messageRecord.getDisplayBody(getContext()));
|
||||||
if (messageRecord.isNoRemoteSession() && !messageRecord.isLokiSessionRestoreSent()) {
|
|
||||||
button.setVisibility(VISIBLE);
|
|
||||||
button.setText(R.string.MessageRecord_session_restore_button_title);
|
|
||||||
} else {
|
|
||||||
button.setVisibility(GONE);
|
|
||||||
}
|
|
||||||
|
|
||||||
icon.setVisibility(GONE);
|
icon.setVisibility(GONE);
|
||||||
title.setVisibility(GONE);
|
title.setVisibility(GONE);
|
||||||
|
@ -103,11 +103,7 @@ public abstract class DisplayRecord {
|
|||||||
return SmsDatabase.Types.isKeyExchangeType(type);
|
return SmsDatabase.Types.isKeyExchangeType(type);
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isEndSession() {
|
public boolean isEndSession() { return SmsDatabase.Types.isEndSessionType(type); }
|
||||||
return SmsDatabase.Types.isEndSessionType(type);
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isNoRemoteSession() { return SmsDatabase.Types.isNoRemoteSessionType(type); }
|
|
||||||
|
|
||||||
public boolean isLokiSessionRestoreSent() { return SmsDatabase.Types.isLokiSessionRestoreSentType(type); }
|
public boolean isLokiSessionRestoreSent() { return SmsDatabase.Types.isLokiSessionRestoreSentType(type); }
|
||||||
|
|
||||||
|
@ -180,7 +180,7 @@ public abstract class MessageRecord extends DisplayRecord {
|
|||||||
|
|
||||||
public boolean isUpdate() {
|
public boolean isUpdate() {
|
||||||
return isGroupAction() || isJoined() || isExpirationTimerUpdate() || isCallLog() ||
|
return isGroupAction() || isJoined() || isExpirationTimerUpdate() || isCallLog() ||
|
||||||
isEndSession() || isIdentityUpdate() || isIdentityVerified() || isIdentityDefault() || isNoRemoteSession() || isLokiSessionRestoreSent();
|
isEndSession() || isIdentityUpdate() || isIdentityVerified() || isIdentityDefault() || isLokiSessionRestoreSent();
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean isMediaPending() {
|
public boolean isMediaPending() {
|
||||||
|
@ -99,14 +99,10 @@ public class SmsMessageRecord extends MessageRecord {
|
|||||||
return emphasisAdded(context.getString(R.string.ConversationItem_received_key_exchange_message_tap_to_process));
|
return emphasisAdded(context.getString(R.string.ConversationItem_received_key_exchange_message_tap_to_process));
|
||||||
} else if (SmsDatabase.Types.isDuplicateMessageType(type)) {
|
} else if (SmsDatabase.Types.isDuplicateMessageType(type)) {
|
||||||
return emphasisAdded(context.getString(R.string.SmsMessageRecord_duplicate_message));
|
return emphasisAdded(context.getString(R.string.SmsMessageRecord_duplicate_message));
|
||||||
|
} else if (SmsDatabase.Types.isNoRemoteSessionType(type)) {
|
||||||
|
return emphasisAdded(context.getString(R.string.MessageDisplayHelper_message_encrypted_for_non_existing_session));
|
||||||
} else if (isLokiSessionRestoreSent()) {
|
} else if (isLokiSessionRestoreSent()) {
|
||||||
return emphasisAdded(context.getString(R.string.MessageRecord_session_restore_sent, recipient.toShortString()));
|
return emphasisAdded(context.getString(R.string.MessageRecord_session_restore_sent, recipient.toShortString()));
|
||||||
} else if (isNoRemoteSession()) {
|
|
||||||
if (recipient.isGroupRecipient()) {
|
|
||||||
return emphasisAdded(context.getString(R.string.MessageDisplayHelper_message_encrypted_for_non_existing_session));
|
|
||||||
} else {
|
|
||||||
return emphasisAdded(context.getString(R.string.MessageRecord_session_restore_required, recipient.toShortString()));
|
|
||||||
}
|
|
||||||
} else if (isEndSession() && isOutgoing()) {
|
} else if (isEndSession() && isOutgoing()) {
|
||||||
return emphasisAdded(context.getString(R.string.SmsMessageRecord_secure_session_reset));
|
return emphasisAdded(context.getString(R.string.SmsMessageRecord_secure_session_reset));
|
||||||
} else if (isEndSession()) {
|
} else if (isEndSession()) {
|
||||||
|
@ -80,14 +80,10 @@ public class ThreadRecord extends DisplayRecord {
|
|||||||
return emphasisAdded(context.getString(R.string.ConversationListItem_key_exchange_message));
|
return emphasisAdded(context.getString(R.string.ConversationListItem_key_exchange_message));
|
||||||
} else if (SmsDatabase.Types.isFailedDecryptType(type)) {
|
} else if (SmsDatabase.Types.isFailedDecryptType(type)) {
|
||||||
return emphasisAdded(context.getString(R.string.MessageDisplayHelper_bad_encrypted_message));
|
return emphasisAdded(context.getString(R.string.MessageDisplayHelper_bad_encrypted_message));
|
||||||
|
} else if (SmsDatabase.Types.isNoRemoteSessionType(type)) {
|
||||||
|
return emphasisAdded(context.getString(R.string.MessageDisplayHelper_message_encrypted_for_non_existing_session));
|
||||||
} else if (isLokiSessionRestoreSent()) {
|
} else if (isLokiSessionRestoreSent()) {
|
||||||
return emphasisAdded(context.getString(R.string.MessageRecord_session_restore_sent, recipient.toShortString()));
|
return emphasisAdded(context.getString(R.string.MessageRecord_session_restore_sent, recipient.toShortString()));
|
||||||
} else if (isNoRemoteSession()) {
|
|
||||||
if (recipient.isGroupRecipient()) {
|
|
||||||
return emphasisAdded(context.getString(R.string.MessageDisplayHelper_message_encrypted_for_non_existing_session));
|
|
||||||
} else {
|
|
||||||
return emphasisAdded(context.getString(R.string.MessageRecord_session_restore_required, recipient.toShortString()));
|
|
||||||
}
|
|
||||||
} else if (SmsDatabase.Types.isEndSessionType(type)) {
|
} else if (SmsDatabase.Types.isEndSessionType(type)) {
|
||||||
return emphasisAdded(context.getString(R.string.ThreadRecord_secure_session_reset));
|
return emphasisAdded(context.getString(R.string.ThreadRecord_secure_session_reset));
|
||||||
} else if (MmsSmsColumns.Types.isLegacyType(type)) {
|
} else if (MmsSmsColumns.Types.isLegacyType(type)) {
|
||||||
|
@ -42,6 +42,7 @@ import org.thoughtcrime.securesms.crypto.storage.SignalProtocolStoreImpl;
|
|||||||
import org.thoughtcrime.securesms.crypto.storage.TextSecureSessionStore;
|
import org.thoughtcrime.securesms.crypto.storage.TextSecureSessionStore;
|
||||||
import org.thoughtcrime.securesms.database.Address;
|
import org.thoughtcrime.securesms.database.Address;
|
||||||
import org.thoughtcrime.securesms.database.AttachmentDatabase;
|
import org.thoughtcrime.securesms.database.AttachmentDatabase;
|
||||||
|
import org.thoughtcrime.securesms.database.Database;
|
||||||
import org.thoughtcrime.securesms.database.DatabaseFactory;
|
import org.thoughtcrime.securesms.database.DatabaseFactory;
|
||||||
import org.thoughtcrime.securesms.database.GroupDatabase;
|
import org.thoughtcrime.securesms.database.GroupDatabase;
|
||||||
import org.thoughtcrime.securesms.database.GroupReceiptDatabase;
|
import org.thoughtcrime.securesms.database.GroupReceiptDatabase;
|
||||||
@ -74,7 +75,6 @@ import org.thoughtcrime.securesms.loki.LokiPreKeyBundleDatabase;
|
|||||||
import org.thoughtcrime.securesms.loki.LokiPreKeyRecordDatabase;
|
import org.thoughtcrime.securesms.loki.LokiPreKeyRecordDatabase;
|
||||||
import org.thoughtcrime.securesms.loki.LokiThreadDatabase;
|
import org.thoughtcrime.securesms.loki.LokiThreadDatabase;
|
||||||
import org.thoughtcrime.securesms.loki.MultiDeviceUtilities;
|
import org.thoughtcrime.securesms.loki.MultiDeviceUtilities;
|
||||||
import org.thoughtcrime.securesms.loki.DebouncerCache;
|
|
||||||
import org.thoughtcrime.securesms.mms.IncomingMediaMessage;
|
import org.thoughtcrime.securesms.mms.IncomingMediaMessage;
|
||||||
import org.thoughtcrime.securesms.mms.MmsException;
|
import org.thoughtcrime.securesms.mms.MmsException;
|
||||||
import org.thoughtcrime.securesms.mms.OutgoingExpirationUpdateMessage;
|
import org.thoughtcrime.securesms.mms.OutgoingExpirationUpdateMessage;
|
||||||
@ -95,7 +95,6 @@ import org.thoughtcrime.securesms.sms.OutgoingEncryptedMessage;
|
|||||||
import org.thoughtcrime.securesms.sms.OutgoingEndSessionMessage;
|
import org.thoughtcrime.securesms.sms.OutgoingEndSessionMessage;
|
||||||
import org.thoughtcrime.securesms.sms.OutgoingTextMessage;
|
import org.thoughtcrime.securesms.sms.OutgoingTextMessage;
|
||||||
import org.thoughtcrime.securesms.stickers.StickerLocator;
|
import org.thoughtcrime.securesms.stickers.StickerLocator;
|
||||||
import org.thoughtcrime.securesms.util.Debouncer;
|
|
||||||
import org.thoughtcrime.securesms.util.GroupUtil;
|
import org.thoughtcrime.securesms.util.GroupUtil;
|
||||||
import org.thoughtcrime.securesms.util.Hex;
|
import org.thoughtcrime.securesms.util.Hex;
|
||||||
import org.thoughtcrime.securesms.util.IdentityUtil;
|
import org.thoughtcrime.securesms.util.IdentityUtil;
|
||||||
@ -276,9 +275,11 @@ public class PushDecryptJob extends BaseJob implements InjectableType {
|
|||||||
LokiServiceCipher cipher = new LokiServiceCipher(localAddress, axolotlStore, lokiThreadDatabase, lokiPreKeyRecordDatabase, UnidentifiedAccessUtil.getCertificateValidator());
|
LokiServiceCipher cipher = new LokiServiceCipher(localAddress, axolotlStore, lokiThreadDatabase, lokiPreKeyRecordDatabase, UnidentifiedAccessUtil.getCertificateValidator());
|
||||||
|
|
||||||
// Loki - Handle session reset logic
|
// Loki - Handle session reset logic
|
||||||
|
/*
|
||||||
if (!envelope.isFriendRequest() && cipher.getSessionStatus(envelope) == null && envelope.isPreKeySignalMessage()) {
|
if (!envelope.isFriendRequest() && cipher.getSessionStatus(envelope) == null && envelope.isPreKeySignalMessage()) {
|
||||||
cipher.validateBackgroundMessage(envelope, envelope.getContent());
|
cipher.validateBackgroundMessage(envelope, envelope.getContent());
|
||||||
}
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
// Loki - Ignore any friend requests that we got before restoration
|
// Loki - Ignore any friend requests that we got before restoration
|
||||||
if (envelope.isFriendRequest() && envelope.getTimestamp() < TextSecurePreferences.getRestorationTime(context)) {
|
if (envelope.isFriendRequest() && envelope.getTimestamp() < TextSecurePreferences.getRestorationTime(context)) {
|
||||||
@ -1394,51 +1395,38 @@ public class PushDecryptJob extends BaseJob implements InjectableType {
|
|||||||
|
|
||||||
if (insertResult.isPresent()) {
|
if (insertResult.isPresent()) {
|
||||||
smsDatabase.markAsDecryptFailed(insertResult.get().getMessageId());
|
smsDatabase.markAsDecryptFailed(insertResult.get().getMessageId());
|
||||||
MessageNotifier.updateNotification(context, insertResult.get().getThreadId());
|
// MessageNotifier.updateNotification(context, insertResult.get().getThreadId());
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
smsDatabase.markAsDecryptFailed(smsMessageId.get());
|
smsDatabase.markAsDecryptFailed(smsMessageId.get());
|
||||||
}
|
}
|
||||||
|
triggerSessionRestorePrompt(sender);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void handleNoSessionMessage(@NonNull String sender, int senderDevice, long timestamp,
|
private void handleNoSessionMessage(@NonNull String sender, int senderDevice, long timestamp,
|
||||||
@NonNull Optional<Long> smsMessageId)
|
@NonNull Optional<Long> smsMessageId)
|
||||||
{
|
{
|
||||||
Recipient recipient = Recipient.from(context, Address.fromSerialized(sender), false);
|
SmsDatabase smsDatabase = DatabaseFactory.getSmsDatabase(context);
|
||||||
if (recipient.isGroupRecipient()) { return; }
|
|
||||||
|
|
||||||
long threadID = DatabaseFactory.getThreadDatabase(context).getThreadIdIfExistsFor(recipient);
|
if (!smsMessageId.isPresent()) {
|
||||||
LokiThreadFriendRequestStatus friendRequestStatus = DatabaseFactory.getLokiThreadDatabase(context).getFriendRequestStatus(threadID);
|
Optional<InsertResult> insertResult = insertPlaceholder(sender, senderDevice, timestamp);
|
||||||
/*
|
|
||||||
If we are friends with the user or we sent a friend request to them and we got a message back with no session then we want to try and restore the session automatically.
|
|
||||||
otherwise if we're not friends or our friend request expired then we need to prompt the user for action
|
|
||||||
*/
|
|
||||||
if (friendRequestStatus == LokiThreadFriendRequestStatus.FRIENDS || friendRequestStatus == LokiThreadFriendRequestStatus.REQUEST_SENT) {
|
|
||||||
autoRestoreSession(sender);
|
|
||||||
} else if (friendRequestStatus == LokiThreadFriendRequestStatus.NONE || friendRequestStatus == LokiThreadFriendRequestStatus.REQUEST_EXPIRED) {
|
|
||||||
SmsDatabase smsDatabase = DatabaseFactory.getSmsDatabase(context);
|
|
||||||
|
|
||||||
if (!smsMessageId.isPresent()) {
|
if (insertResult.isPresent()) {
|
||||||
if (!TextSecurePreferences.isShowingSessionRestorePrompt(context, sender)) {
|
smsDatabase.markAsNoSession(insertResult.get().getMessageId());
|
||||||
Optional<InsertResult> insertResult = insertPlaceholder(sender, senderDevice, timestamp);
|
// MessageNotifier.updateNotification(context, insertResult.get().getThreadId());
|
||||||
|
|
||||||
if (insertResult.isPresent()) {
|
|
||||||
smsDatabase.markAsNoSession(insertResult.get().getMessageId());
|
|
||||||
TextSecurePreferences.setShowingSessionRestorePrompt(context, sender, true);
|
|
||||||
//MessageNotifier.updateNotification(context, insertResult.get().getThreadId());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
smsDatabase.markAsNoSession(smsMessageId.get());
|
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
smsDatabase.markAsNoSession(smsMessageId.get());
|
||||||
}
|
}
|
||||||
|
triggerSessionRestorePrompt(sender);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void autoRestoreSession(@NonNull String sender) {
|
private void triggerSessionRestorePrompt(@NonNull String sender) {
|
||||||
// We don't want to keep spamming the user for an auto restore
|
Recipient primaryRecipient = getPrimaryDeviceRecipient(sender);
|
||||||
String key = "restore_session_" + sender;
|
if (!primaryRecipient.isGroupRecipient()) {
|
||||||
Debouncer debouncer = DebouncerCache.getDebouncer(key, 10000);
|
long threadID = DatabaseFactory.getThreadDatabase(context).getThreadIdFor(primaryRecipient);
|
||||||
debouncer.publish(() -> MessageSender.sendRestoreSessionMessage(context, sender));
|
DatabaseFactory.getLokiThreadDatabase(context).addSessionRestoreDevice(threadID, sender);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void handleLegacyMessage(@NonNull String sender, int senderDevice, long timestamp,
|
private void handleLegacyMessage(@NonNull String sender, int senderDevice, long timestamp,
|
||||||
|
@ -1,7 +0,0 @@
|
|||||||
package org.thoughtcrime.securesms.loki
|
|
||||||
|
|
||||||
import org.thoughtcrime.securesms.database.model.MessageRecord
|
|
||||||
|
|
||||||
interface ConversationUpdateItemViewDelegate {
|
|
||||||
fun updateItemButtonPressed(message: MessageRecord)
|
|
||||||
}
|
|
@ -29,12 +29,7 @@ object FriendRequestHandler {
|
|||||||
DatabaseFactory.getLokiThreadDatabase(context).setFriendRequestStatus(threadId, threadFriendStatus)
|
DatabaseFactory.getLokiThreadDatabase(context).setFriendRequestStatus(threadId, threadFriendStatus)
|
||||||
// If we sent a friend request then we need to hide the session restore prompt
|
// If we sent a friend request then we need to hide the session restore prompt
|
||||||
if (type == ActionType.Sent) {
|
if (type == ActionType.Sent) {
|
||||||
val smsDatabase = DatabaseFactory.getSmsDatabase(context)
|
// TODO: Hide prompt
|
||||||
smsDatabase.getMessages(threadId)
|
|
||||||
.filter { it.isNoRemoteSession && !it.isLokiSessionRestoreSent }
|
|
||||||
.forEach {
|
|
||||||
smsDatabase.markAsLokiSessionRestoreSent(it.id)
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -8,6 +8,7 @@ import org.thoughtcrime.securesms.database.Database
|
|||||||
import org.thoughtcrime.securesms.database.DatabaseFactory
|
import org.thoughtcrime.securesms.database.DatabaseFactory
|
||||||
import org.thoughtcrime.securesms.database.helpers.SQLCipherOpenHelper
|
import org.thoughtcrime.securesms.database.helpers.SQLCipherOpenHelper
|
||||||
import org.thoughtcrime.securesms.recipients.Recipient
|
import org.thoughtcrime.securesms.recipients.Recipient
|
||||||
|
import org.thoughtcrime.securesms.util.TextSecurePreferences
|
||||||
import org.whispersystems.signalservice.internal.util.JsonUtil
|
import org.whispersystems.signalservice.internal.util.JsonUtil
|
||||||
import org.whispersystems.signalservice.loki.api.LokiPublicChat
|
import org.whispersystems.signalservice.loki.api.LokiPublicChat
|
||||||
import org.whispersystems.signalservice.loki.messaging.LokiThreadDatabaseProtocol
|
import org.whispersystems.signalservice.loki.messaging.LokiThreadDatabaseProtocol
|
||||||
@ -140,4 +141,23 @@ class LokiThreadDatabase(context: Context, helper: SQLCipherOpenHelper) : Databa
|
|||||||
override fun removePublicChat(threadID: Long) {
|
override fun removePublicChat(threadID: Long) {
|
||||||
databaseHelper.writableDatabase.delete(publicChatTableName, "${Companion.threadID} = ?", arrayOf( threadID.toString() ))
|
databaseHelper.writableDatabase.delete(publicChatTableName, "${Companion.threadID} = ?", arrayOf( threadID.toString() ))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// region Session Restore
|
||||||
|
fun addSessionRestoreDevice(threadID: Long, hexEncodedPublicKey: String) {
|
||||||
|
val devices = getSessionRestoreDevices(threadID).toMutableSet()
|
||||||
|
if (devices.add(hexEncodedPublicKey)) {
|
||||||
|
TextSecurePreferences.setStringPreference(context, "session_restore_devices_$threadID", devices.joinToString(","))
|
||||||
|
delegate?.handleSessionRestoreDevicesChanged(threadID)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
fun getSessionRestoreDevices(threadID: Long): Set<String> {
|
||||||
|
return TextSecurePreferences.getStringPreference(context, "session_restore_devices_$threadID", "").split(",").toSet()
|
||||||
|
}
|
||||||
|
|
||||||
|
fun removeAllSessionRestoreDevices(threadID: Long) {
|
||||||
|
TextSecurePreferences.setStringPreference(context, "session_restore_devices_$threadID", "")
|
||||||
|
delegate?.handleSessionRestoreDevicesChanged(threadID)
|
||||||
|
}
|
||||||
|
// endregion
|
||||||
}
|
}
|
@ -3,4 +3,5 @@ package org.thoughtcrime.securesms.loki
|
|||||||
interface LokiThreadDatabaseDelegate {
|
interface LokiThreadDatabaseDelegate {
|
||||||
|
|
||||||
fun handleThreadFriendRequestStatusChanged(threadID: Long)
|
fun handleThreadFriendRequestStatusChanged(threadID: Long)
|
||||||
|
fun handleSessionRestoreDevicesChanged(threadID: Long)
|
||||||
}
|
}
|
@ -0,0 +1,55 @@
|
|||||||
|
package org.thoughtcrime.securesms.loki
|
||||||
|
|
||||||
|
import org.thoughtcrime.securesms.components.reminder.Reminder
|
||||||
|
|
||||||
|
import android.annotation.TargetApi
|
||||||
|
import android.content.Context
|
||||||
|
import android.os.Build.VERSION_CODES
|
||||||
|
import android.text.TextUtils
|
||||||
|
import android.util.AttributeSet
|
||||||
|
import android.view.LayoutInflater
|
||||||
|
import android.view.View
|
||||||
|
import android.view.ViewGroup
|
||||||
|
import android.widget.ImageButton
|
||||||
|
import android.widget.LinearLayout
|
||||||
|
import android.widget.TextView
|
||||||
|
import kotlinx.android.synthetic.main.session_restore_banner.view.*
|
||||||
|
|
||||||
|
import network.loki.messenger.R
|
||||||
|
import org.thoughtcrime.securesms.recipients.Recipient
|
||||||
|
import org.thoughtcrime.securesms.util.ViewUtil
|
||||||
|
|
||||||
|
/**
|
||||||
|
* View to display actionable reminders to the user
|
||||||
|
*/
|
||||||
|
class SessionRestoreBannerView private constructor(context: Context, attrs: AttributeSet?, defStyleAttr: Int) : LinearLayout(context, attrs, defStyleAttr) {
|
||||||
|
private var container: ViewGroup? = null
|
||||||
|
private var closeButton: ImageButton? = null
|
||||||
|
private var title: TextView? = null
|
||||||
|
private var text: TextView? = null
|
||||||
|
lateinit var recipient: Recipient
|
||||||
|
var onDismiss: (() -> Unit)? = null
|
||||||
|
var onRestore: (() -> Unit)? = null
|
||||||
|
|
||||||
|
constructor(context: Context) : this(context, null)
|
||||||
|
private constructor(context: Context, attrs: AttributeSet?) : this(context, attrs, 0)
|
||||||
|
|
||||||
|
init {
|
||||||
|
LayoutInflater.from(context).inflate(R.layout.session_restore_banner, this, true)
|
||||||
|
restoreButton.setOnClickListener { onRestore?.invoke() }
|
||||||
|
dismissButton.setOnClickListener { onDismiss?.invoke() }
|
||||||
|
}
|
||||||
|
|
||||||
|
fun update(recipient: Recipient) {
|
||||||
|
this.recipient = recipient
|
||||||
|
restoreText.text = context.getString(R.string.session_restore_banner_message, recipient.toShortString())
|
||||||
|
}
|
||||||
|
|
||||||
|
fun show() {
|
||||||
|
container!!.visibility = View.VISIBLE;
|
||||||
|
}
|
||||||
|
|
||||||
|
fun hide() {
|
||||||
|
container!!.visibility = View.GONE
|
||||||
|
}
|
||||||
|
}
|
@ -1228,14 +1228,6 @@ public class TextSecurePreferences {
|
|||||||
public static long getRestorationTime(Context context) {
|
public static long getRestorationTime(Context context) {
|
||||||
return getLongPreference(context, "restoration_time", 0);
|
return getLongPreference(context, "restoration_time", 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void setShowingSessionRestorePrompt(Context context, String sender, boolean showingPrompt) {
|
|
||||||
setBooleanPreference(context, sender + "_showing_session_reset", showingPrompt);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static boolean isShowingSessionRestorePrompt(Context context, String sender) {
|
|
||||||
return getBooleanPreference(context, sender + "_showing_session_reset", false);
|
|
||||||
}
|
|
||||||
// endregion
|
// endregion
|
||||||
|
|
||||||
public static void clearAll(Context context) {
|
public static void clearAll(Context context) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user