Merge branch 'dev' into sync-everything

This commit is contained in:
andrew
2023-05-30 11:34:17 +09:30
60 changed files with 466 additions and 285 deletions

View File

@@ -106,10 +106,13 @@ interface StorageProtocol {
fun getAttachmentsForMessage(messageID: Long): List<DatabaseAttachment>
fun getMessageIdInDatabase(timestamp: Long, author: String): Long? // TODO: This is a weird name
fun updateSentTimestamp(messageID: Long, isMms: Boolean, openGroupSentTimestamp: Long, threadId: Long)
fun markAsResyncing(timestamp: Long, author: String)
fun markAsSyncing(timestamp: Long, author: String)
fun markAsSending(timestamp: Long, author: String)
fun markAsSent(timestamp: Long, author: String)
fun markUnidentified(timestamp: Long, author: String)
fun setErrorMessage(timestamp: Long, author: String, error: Exception)
fun markAsSyncFailed(timestamp: Long, author: String, error: Exception)
fun markAsSentFailed(timestamp: Long, author: String, error: Exception)
fun clearErrorMessage(messageID: Long)
fun setMessageServerHash(messageID: Long, serverHash: String)

View File

@@ -7,13 +7,13 @@ import org.session.libsignal.utilities.toHexString
sealed class Destination {
class Contact(var publicKey: String) : Destination() {
data class Contact(var publicKey: String) : Destination() {
internal constructor(): this("")
}
class ClosedGroup(var groupPublicKey: String) : Destination() {
data class ClosedGroup(var groupPublicKey: String) : Destination() {
internal constructor(): this("")
}
class LegacyOpenGroup(var roomToken: String, var server: String) : Destination() {
data class LegacyOpenGroup(var roomToken: String, var server: String) : Destination() {
internal constructor(): this("", "")
}

View File

@@ -11,20 +11,22 @@ import org.session.libsignal.protos.SignalServiceProtos
import org.session.libsignal.utilities.Log
import org.session.libsession.messaging.sending_receiving.attachments.Attachment as SignalAttachment
class VisibleMessage : Message() {
/** In the case of a sync message, the public key of the person the message was targeted at.
*
* **Note:** `nil` if this isn't a sync message.
*/
var syncTarget: String? = null
var text: String? = null
val attachmentIDs: MutableList<Long> = mutableListOf()
var quote: Quote? = null
var linkPreview: LinkPreview? = null
var profile: Profile? = null
var openGroupInvitation: OpenGroupInvitation? = null
var reaction: Reaction? = null
/**
* @param syncTarget In the case of a sync message, the public key of the person the message was targeted at.
*
* **Note:** `nil` if this isn't a sync message.
*/
class VisibleMessage(
var syncTarget: String? = null,
var text: String? = null,
val attachmentIDs: MutableList<Long> = mutableListOf(),
var quote: Quote? = null,
var linkPreview: LinkPreview? = null,
var profile: Profile? = null,
var openGroupInvitation: OpenGroupInvitation? = null,
var reaction: Reaction? = null,
var hasMention: Boolean = false
) : Message() {
override val isSelfSendValid: Boolean = true

View File

@@ -61,11 +61,11 @@ object MessageSender {
}
// Convenience
fun send(message: Message, destination: Destination): Promise<Unit, Exception> {
fun send(message: Message, destination: Destination, isSyncMessage: Boolean = false): Promise<Unit, Exception> {
return if (destination is Destination.LegacyOpenGroup || destination is Destination.OpenGroup || destination is Destination.OpenGroupInbox) {
sendToOpenGroupDestination(destination, message)
} else {
sendToSnodeDestination(destination, message)
sendToSnodeDestination(destination, message, isSyncMessage)
}
}
@@ -86,7 +86,7 @@ object MessageSender {
val isSelfSend = (message.recipient == userPublicKey)
// Set the failure handler (need it here already for precondition failure handling)
fun handleFailure(error: Exception) {
handleFailedMessageSend(message, error)
handleFailedMessageSend(message, error, isSyncMessage)
if (destination is Destination.Contact && message is VisibleMessage && !isSelfSend) {
SnodeModule.shared.broadcaster.broadcast("messageFailed", message.sentTimestamp!!)
}
@@ -374,16 +374,23 @@ object MessageSender {
// • the destination was a contact
// • we didn't sync it already
if (destination is Destination.Contact && !isSyncMessage) {
if (message is VisibleMessage) { message.syncTarget = destination.publicKey }
if (message is ExpirationTimerUpdate) { message.syncTarget = destination.publicKey }
if (message is VisibleMessage) message.syncTarget = destination.publicKey
if (message is ExpirationTimerUpdate) message.syncTarget = destination.publicKey
storage.markAsSyncing(message.sentTimestamp!!, userPublicKey)
sendToSnodeDestination(Destination.Contact(userPublicKey), message, true)
}
}
fun handleFailedMessageSend(message: Message, error: Exception) {
fun handleFailedMessageSend(message: Message, error: Exception, isSyncMessage: Boolean = false) {
val storage = MessagingModuleConfiguration.shared.storage
val userPublicKey = storage.getUserPublicKey()!!
storage.setErrorMessage(message.sentTimestamp!!, message.sender?:userPublicKey, error)
val timestamp = message.sentTimestamp!!
val author = message.sender ?: userPublicKey
if (isSyncMessage) storage.markAsSyncFailed(timestamp, author, error)
else storage.markAsSentFailed(timestamp, author, error)
}
// Convenience

View File

@@ -7,16 +7,17 @@ import org.session.libsession.messaging.calls.CallMessageType
import org.session.libsession.messaging.contacts.Contact
import org.session.libsession.messaging.sending_receiving.data_extraction.DataExtractionNotificationInfoMessage
import org.session.libsession.utilities.ExpirationUtil
import org.session.libsession.utilities.truncateIdForDisplay
object UpdateMessageBuilder {
fun buildGroupUpdateMessage(context: Context, updateMessageData: UpdateMessageData, sender: String? = null, isOutgoing: Boolean = false): String {
fun buildGroupUpdateMessage(context: Context, updateMessageData: UpdateMessageData, senderId: String? = null, isOutgoing: Boolean = false): String {
var message = ""
val updateData = updateMessageData.kind ?: return message
if (!isOutgoing && sender == null) return message
if (!isOutgoing && senderId == null) return message
val storage = MessagingModuleConfiguration.shared.storage
val senderName: String = if (!isOutgoing) {
storage.getContactWithSessionID(sender!!)?.displayName(Contact.ContactContext.REGULAR) ?: sender
storage.getContactWithSessionID(senderId!!)?.displayName(Contact.ContactContext.REGULAR) ?: truncateIdForDisplay(senderId)
} else { context.getString(R.string.MessageRecord_you) }
when (updateData) {
@@ -77,11 +78,11 @@ object UpdateMessageBuilder {
return message
}
fun buildExpirationTimerMessage(context: Context, duration: Long, sender: String? = null, isOutgoing: Boolean = false): String {
if (!isOutgoing && sender == null) return ""
fun buildExpirationTimerMessage(context: Context, duration: Long, senderId: String? = null, isOutgoing: Boolean = false): String {
if (!isOutgoing && senderId == null) return ""
val storage = MessagingModuleConfiguration.shared.storage
val senderName: String? = if (!isOutgoing) {
storage.getContactWithSessionID(sender!!)?.displayName(Contact.ContactContext.REGULAR) ?: sender
storage.getContactWithSessionID(senderId!!)?.displayName(Contact.ContactContext.REGULAR) ?: truncateIdForDisplay(senderId)
} else { context.getString(R.string.MessageRecord_you) }
return if (duration <= 0) {
if (isOutgoing) context.getString(R.string.MessageRecord_you_disabled_disappearing_messages)
@@ -93,9 +94,9 @@ object UpdateMessageBuilder {
}
}
fun buildDataExtractionMessage(context: Context, kind: DataExtractionNotificationInfoMessage.Kind, sender: String? = null): String {
fun buildDataExtractionMessage(context: Context, kind: DataExtractionNotificationInfoMessage.Kind, senderId: String? = null): String {
val storage = MessagingModuleConfiguration.shared.storage
val senderName = storage.getContactWithSessionID(sender!!)?.displayName(Contact.ContactContext.REGULAR) ?: sender!!
val senderName = storage.getContactWithSessionID(senderId!!)?.displayName(Contact.ContactContext.REGULAR) ?: truncateIdForDisplay(senderId)
return when (kind) {
DataExtractionNotificationInfoMessage.Kind.SCREENSHOT ->
context.getString(R.string.MessageRecord_s_took_a_screenshot, senderName)

View File

@@ -0,0 +1,4 @@
package org.session.libsession.utilities
fun truncateIdForDisplay(id: String): String =
id.takeIf { it.length > 8 }?.apply{ "${take(4)}${takeLast(4)}" } ?: id

View File

@@ -4,6 +4,7 @@ import android.content.Context
import android.util.TypedValue
import androidx.annotation.AttrRes
import androidx.annotation.ColorInt
import androidx.recyclerview.widget.RecyclerView
@ColorInt
fun Context.getColorFromAttr(
@@ -13,4 +14,7 @@ fun Context.getColorFromAttr(
): Int {
theme.resolveAttribute(attrColor, typedValue, resolveRefs)
return typedValue.data
}
}
val RecyclerView.isScrolledToBottom: Boolean
get() = computeVerticalScrollOffset() + computeVerticalScrollExtent() >= computeVerticalScrollRange()